kwo pushed a commit to branch master.

http://git.enlightenment.org/legacy/imlib2.git/commit/?id=59dc04fe563656543b056c1996e48d37b6ce4445

commit 59dc04fe563656543b056c1996e48d37b6ce4445
Author: Kim Woelders <[email protected]>
Date:   Fri Oct 1 13:23:16 2021 +0200

    PNM loader: Use mmap() for loading
---
 src/modules/loaders/loader_pnm.c | 117 +++++++++++++++++++++++++++++++++------
 1 file changed, 100 insertions(+), 17 deletions(-)

diff --git a/src/modules/loaders/loader_pnm.c b/src/modules/loaders/loader_pnm.c
index 4f251c6..b78228a 100644
--- a/src/modules/loaders/loader_pnm.c
+++ b/src/modules/loaders/loader_pnm.c
@@ -1,10 +1,82 @@
 #include "loader_common.h"
+
 #include <ctype.h>
+#include <sys/mman.h>
+
+static struct {
+   const unsigned char *data, *dptr;
+   unsigned int        size;
+} mdata;
+
+static void
+mm_init(void *src, unsigned int size)
+{
+   mdata.data = mdata.dptr = src;
+   mdata.size = size;
+}
+
+static int
+mm_read(void *dst, unsigned int len)
+{
+   if (mdata.dptr + len > mdata.data + mdata.size)
+      return 1;                 /* Out of data */
+
+   memcpy(dst, mdata.dptr, len);
+   mdata.dptr += len;
+
+   return 0;
+}
+
+static int
+mm_getc(void)
+{
+   int                 ch;
+
+   if (mdata.dptr + 1 > mdata.data + mdata.size)
+      return -1;                /* Out of data */
+
+   ch = *mdata.dptr++;
+
+   return ch;
+}
+
+static int
+mm_getu(unsigned int *pui)
+{
+   int                 ch;
+   int                 uval;
+
+   for (;;)
+     {
+        ch = mm_getc();
+        if (ch < 0)
+           return ch;
+        if (!isspace(ch))
+           break;
+     }
+
+   if (!isdigit(ch))
+      return -1;
+
+   for (uval = 0;;)
+     {
+        uval = 10 * uval + ch - '0';
+        ch = mm_getc();
+        if (ch < 0)
+           return ch;
+        if (!isdigit(ch))
+           break;
+     }
+
+   *pui = uval;
+   return 0;                    /* Ok */
+}
 
 int
 load2(ImlibImage * im, int load_data)
 {
    int                 rc;
+   void               *fdata;
    char                p = ' ', numbers = 3, count = 0;
    int                 w = 0, h = 0, v = 255, c = 0;
    char                buf[256];
@@ -14,15 +86,23 @@ load2(ImlibImage * im, int load_data)
    DATA32             *ptr2, rval, gval, bval;
    int                 i, j, x, y;
 
+   rc = LOAD_FAIL;
+
+   fdata = mmap(NULL, im->fsize, PROT_READ, MAP_SHARED, fileno(im->fp), 0);
+   if (fdata == MAP_FAILED)
+      return rc;
+
+   mm_init(fdata, im->fsize);
+
    /* read the header info */
 
    rc = LOAD_FAIL;
 
-   c = fgetc(im->fp);
+   c = mm_getc();
    if (c != 'P')
       goto quit;
 
-   p = fgetc(im->fp);
+   p = mm_getc();
    if (p == '1' || p == '4')
       numbers = 2;              /* bitimages don't have max value */
 
@@ -32,19 +112,19 @@ load2(ImlibImage * im, int load_data)
    count = 0;
    while (count < numbers)
      {
-        c = fgetc(im->fp);
+        c = mm_getc();
 
         if (c == EOF)
            goto quit;
 
         /* eat whitespace */
         while (isspace(c))
-           c = fgetc(im->fp);
+           c = mm_getc();
         /* if comment, eat that */
         if (c == '#')
           {
              do
-                c = fgetc(im->fp);
+                c = mm_getc();
              while (c != '\n' && c != EOF);
           }
         /* no comment -> proceed */
@@ -56,7 +136,7 @@ load2(ImlibImage * im, int load_data)
              while (c != EOF && !isspace(c) && (i < 255))
                {
                   buf[i++] = c;
-                  c = fgetc(im->fp);
+                  c = mm_getc();
                }
              if (i)
                {
@@ -113,8 +193,7 @@ load2(ImlibImage * im, int load_data)
           {
              for (x = 0; x < w; x++)
                {
-                  j = fscanf(im->fp, "%u", &gval);
-                  if (j <= 0)
+                  if (mm_getu(&gval))
                      goto quit;
 
                   if (gval == 1)
@@ -134,8 +213,7 @@ load2(ImlibImage * im, int load_data)
           {
              for (x = 0; x < w; x++)
                {
-                  j = fscanf(im->fp, "%u", &gval);
-                  if (j <= 0)
+                  if (mm_getu(&gval))
                      goto quit;
 
                   if (v == 0 || v == 255)
@@ -159,8 +237,11 @@ load2(ImlibImage * im, int load_data)
           {
              for (x = 0; x < w; x++)
                {
-                  j = fscanf(im->fp, "%u %u %u", &rval, &gval, &bval);
-                  if (j <= 2)
+                  if (mm_getu(&rval))
+                     goto quit;
+                  if (mm_getu(&gval))
+                     goto quit;
+                  if (mm_getu(&bval))
                      goto quit;
 
                   if (v == 0 || v == 255)
@@ -188,7 +269,7 @@ load2(ImlibImage * im, int load_data)
         ptr2 = im->data;
         for (y = 0; y < h; y++)
           {
-             if (!fread(data, (w + 7) / 8, 1, im->fp))
+             if (mm_read(data, (w + 7) / 8))
                 goto quit;
 
              ptr = data;
@@ -218,7 +299,7 @@ load2(ImlibImage * im, int load_data)
         ptr2 = im->data;
         for (y = 0; y < h; y++)
           {
-             if (!fread(data, w * 1, 1, im->fp))
+             if (mm_read(data, w * 1))
                 goto quit;
 
              ptr = data;
@@ -257,7 +338,7 @@ load2(ImlibImage * im, int load_data)
         ptr2 = im->data;
         for (y = 0; y < h; y++)
           {
-             if (!fread(data, w * 3, 1, im->fp))
+             if (mm_read(data, w * 3))
                 goto quit;
 
              ptr = data;
@@ -296,7 +377,7 @@ load2(ImlibImage * im, int load_data)
         ptr2 = im->data;
         for (y = 0; y < h; y++)
           {
-             if (!fread(data, w * 1, 1, im->fp))
+             if (mm_read(data, w * 1))
                 goto quit;
 
              ptr = data;
@@ -328,7 +409,7 @@ load2(ImlibImage * im, int load_data)
         ptr2 = im->data;
         for (y = 0; y < h; y++)
           {
-             if (!fread(data, w * 4, 1, im->fp))
+             if (mm_read(data, w * 4))
                 goto quit;
 
              ptr = data;
@@ -370,6 +451,8 @@ load2(ImlibImage * im, int load_data)
  quit:
    free(idata);
    free(data);
+   if (fdata != MAP_FAILED)
+      munmap(fdata, im->fsize);
 
    if (rc == 0)
       __imlib_FreeData(im);

-- 


Reply via email to