better late than never
authorvolpol <volpol@packet-gain.de>
Sat, 7 Sep 2013 10:14:32 +0000 (10:14 +0000)
committervolpol <volpol@packet-gain.de>
Sat, 7 Sep 2013 10:14:32 +0000 (10:14 +0000)
memfile.c [new file with mode: 0644]
memfile.h [new file with mode: 0644]

diff --git a/memfile.c b/memfile.c
new file mode 100644 (file)
index 0000000..c935a92
--- /dev/null
+++ b/memfile.c
@@ -0,0 +1,121 @@
+#include <malloc.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "memfile.h"
+#include "log.h"
+
+struct _MFILE {
+    void *pm;
+    size_t rpos;
+    size_t wpos;
+    size_t length;
+    int flags;
+};
+
+#define M_RD 1
+#define M_WR 2
+#define M_FREE 4
+
+int mclose(MFILE *mf){
+    WHOAMI;
+    if (mf->flags & M_FREE) free(mf->pm);
+    free(mf);
+    return 0;
+}
+
+//p could point a memmapped file
+MFILE *mopen(void *p, size_t sz, const char *mode){
+    WHOAMI;
+    MFILE* r = malloc(sizeof (MFILE));
+    if (NULL != r){
+        r->pm = p;
+        r->length = sz;
+        r->wpos = r->rpos = r->flags = 0;
+        switch (mode[0]){
+            case 'r':
+                r->flags |= M_RD;
+                if ('+' == mode[1]) r->flags |= M_WR;
+                break;
+            case 'w':
+                r->flags |= M_WR;
+                if ('+' == mode[1]) r->flags |= M_RD;
+                break;
+            case 'a':
+                r->flags |= M_WR;
+                break;
+        }
+        if (NULL == r->pm) r->flags |= M_FREE;
+    }
+
+    return r;
+}
+
+int mputc(int c, MFILE *mf){
+        WHOAMI;
+    if ((mf->flags & M_WR) == 0) return -1;
+    if (mf->wpos + 1 > mf->length){
+        mf->pm = realloc(mf->pm, mf->length + 1);
+        mf->length++;
+    }
+    ((unsigned char *)(mf->pm))[mf->wpos++] = c;
+    return 0;
+}
+
+int mgetc(MFILE *mf){
+        WHOAMI;
+    if (mf->rpos >= mf->length) return -1;
+    return ((unsigned char*)(mf->pm))[mf->rpos++];
+}
+
+int mputs(const char *s, MFILE *mf){
+        WHOAMI;
+    size_t slen = strlen(s);
+    size_t bw = mwrite(s, 1, slen, mf);
+    if (bw == slen) return 0;
+    return -1;
+}
+
+char *mgets(char *s, int size, MFILE *mf){
+        WHOAMI;
+    size_t p = mf->rpos;
+    int c,slen = 0;
+    do { c = mgetc(mf); } while ( (c != -1) && (++slen <= size-1) && (c != '\n'));
+    if (0 == slen) return NULL;
+
+    memcpy(s, mf->pm+p, slen);
+    s[slen] = 0;
+
+    return s;
+}
+
+int meof( MFILE *f){
+        WHOAMI;
+    return (f->rpos>=f->length);
+}
+
+//do some roar cheging
+size_t mwrite(const void *ptr, size_t size, size_t nmemb, MFILE *mf){
+    size_t tot = 0;
+    void *npf;
+    WHOAMI;
+    if ((mf->flags & M_WR) == 0) return -1;
+    while (nmemb){
+        if (mf->wpos + size > mf->length){
+          npf = realloc(mf->pm, mf->wpos + size );
+          if (NULL == npf) goto no_mem;
+          mf->pm = npf;
+          mf->length=mf->wpos + size;
+        }
+        memcpy(mf->pm + mf->wpos, ptr+tot*size, size);
+        mf->wpos += size;
+        tot++; nmemb--;
+    }
+no_mem:
+    return tot;
+}
+
+void mdump(MFILE *m){
+    WHOAMI;
+    write(1, m->pm, m->length);
+}
diff --git a/memfile.h b/memfile.h
new file mode 100644 (file)
index 0000000..28bdfb1
--- /dev/null
+++ b/memfile.h
@@ -0,0 +1,22 @@
+#ifndef MEMFILE_H_
+#define MEMFILE_H_
+
+struct _MFILE;
+
+typedef struct _MFILE MFILE;
+
+MFILE *mopen(void *p, size_t sz, const char *mode);
+int mclose(MFILE *fp);
+
+char *mgets(char *s, int size, MFILE *mf);
+int mputs(const char *s, MFILE *mf);
+
+int mgetc(MFILE *mf);
+int mputc(int c, MFILE *mf);
+
+size_t mread(void *ptr, size_t size, size_t nmemb, MFILE *mf);
+size_t mwrite(const void *ptr, size_t size, size_t nmemb, MFILE *mf);
+
+void mdump(MFILE *m);
+
+#endif /* MEMFILE_H_ */