aboutsummaryrefslogtreecommitdiff
path: root/blaze822.c
diff options
context:
space:
mode:
authorChristian Neukirchen <chneukirchen@gmail.com>2016-07-14 15:21:37 +0200
committerChristian Neukirchen <chneukirchen@gmail.com>2016-07-14 15:21:37 +0200
commitf101b728d9315f430d900df1e4afbb2da4da8252 (patch)
tree1b7164a23bac978f4d56529ca311b704b19b7477 /blaze822.c
parent13eefbba7234ad1596e6d308d41846daa9d31594 (diff)
downloadmblaze-f101b728d9315f430d900df1e4afbb2da4da8252.tar.gz
blaze822: add mmap-based mail reader
Diffstat (limited to 'blaze822.c')
-rw-r--r--blaze822.c57
1 files changed, 54 insertions, 3 deletions
diff --git a/blaze822.c b/blaze822.c
index 7794301..53fc2e4 100644
--- a/blaze822.c
+++ b/blaze822.c
@@ -6,6 +6,7 @@
#include <stdint.h>
#include <sys/types.h>
#include <sys/stat.h>
+#include <sys/mman.h>
#include <fcntl.h>
#include <unistd.h>
#include <ctype.h>
@@ -364,7 +365,6 @@ blaze822(char *file)
return mesg;
}
-
struct message *
blaze822_mem(char *src, size_t len)
{
@@ -411,8 +411,12 @@ blaze822_free(struct message *mesg)
{
if (!mesg)
return;
- free(mesg->msg);
- free(mesg->bodychunk);
+ if (mesg->bodychunk == mesg->msg) {
+ munmap(mesg->bodychunk, mesg->bodyend - mesg->msg);
+ } else {
+ free(mesg->msg);
+ free(mesg->bodychunk);
+ }
free(mesg);
}
@@ -495,6 +499,53 @@ error:
return 0;
}
+struct message *
+blaze822_mmap(char *file)
+{
+ int fd = open(file, O_RDONLY);
+ if (fd < 0)
+ return 0;
+
+ struct stat st;
+ if (fstat(fd, &st) < 0)
+ goto error;
+
+ size_t len = st.st_size;
+
+ struct message *mesg = malloc(sizeof (struct message));
+ if (!mesg)
+ goto error;
+
+ char *buf = mmap(0, len+1, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0);
+ if (buf == MAP_FAILED) {
+ perror("mmap");
+ goto error;
+ }
+ close(fd);
+
+ char *end;
+ if ((end = memmem(buf, len, "\n\n", 2))) {
+ mesg->body = end+2;
+ } else if ((end = memmem(buf, len, "\r\n\r\n", 4))) {
+ mesg->body = end+4;
+ } else {
+ end = buf + len;
+ mesg->body = end;
+ }
+
+ unfold_hdr(buf, end);
+
+ mesg->msg = mesg->bodychunk = buf;
+ mesg->end = end;
+ mesg->bodyend = buf + len;
+
+ return mesg;
+
+error:
+ close(fd);
+ return 0;
+}
+
char *
blaze822_body(struct message *mesg)
{