changeset 1069:b20922f4746f

Comments, cleanups.
author Matti Hamalainen <ccr@tnsp.org>
date Mon, 02 Mar 2015 02:56:37 +0200
parents 01114659bdd3
children 2ee8d6b765f9
files src/dmzlib.c src/dmzlib.h
diffstat 2 files changed, 45 insertions(+), 18 deletions(-) [+]
line wrap: on
line diff
--- a/src/dmzlib.c	Mon Mar 02 02:12:47 2015 +0200
+++ b/src/dmzlib.c	Mon Mar 02 02:56:37 2015 +0200
@@ -332,6 +332,7 @@
                 ctx->zout = zout;
                 return DMERR_OK;
             }
+
             z -= 257;
 
             len = dm_zlib_length_base[z];
@@ -384,31 +385,44 @@
 
 static int dmZLibComputeHuffmanCodes(DMZLibContext * ctx)
 {
-    DMZHuffmanContext z_codelength;
-    Uint8 codeLengths[288 + 32 + 137];     // padding for maximum single op
+    DMZHuffmanContext codeLengthCtx;
     Uint8 codeLengthSizes[DM_ZLIB_NCODELENGTH_SIZES];
+    Uint8 codeLengths[288 + 32 + 137]; // padding for maximum single op
     int i, n, ret;
 
-    int hlit  = dmZReceive(ctx, 5) + 257;
-    int hdist = dmZReceive(ctx, 5) + 1;
-    int hclen = dmZReceive(ctx, 4) + 4;
+    // Get table sizes
+    int hlit  = dmZReceive(ctx, 5) + 257; // 288 = X
+    int hdist = dmZReceive(ctx, 5) + 1;   // 32  = X
+    int hclen = dmZReceive(ctx, 4) + 4;   // 19  = DM_ZLIB_NCODELENGTH_SIZES
 
+    if (hlit > 286 || hdist > 30)
+    {
+        return dmErrorDBG(DMERR_INVALID_DATA,
+            "Too many Huffman length or distance symbols (%d, %d)",
+            hlit, hdist);
+    }
+
+    // Get lengths table (uninitialized entries should be set to 0)
     memset(codeLengthSizes, 0, sizeof(codeLengthSizes));
-
     for (i = 0; i < hclen; i++)
     {
         int s = dmZReceive(ctx, 3);
         codeLengthSizes[dm_zlib_length_dezigzag[i]] = (Uint8) s;
     }
 
-    if ((ret = dmZLibBuildHuffmanTables(&z_codelength, codeLengthSizes, 19)) != DMERR_OK)
-        return ret;
+    // Inflate the code lengths table
+    if ((ret = dmZLibBuildHuffmanTables(&codeLengthCtx,
+        codeLengthSizes, DM_ZLIB_NCODELENGTH_SIZES)) != DMERR_OK)
+    {
+        return dmErrorDBG(ret,
+            "Invalid code lengths set.\n");
+    }
 
     n = 0;
     while (n < hlit + hdist)
     {
         int c;
-        if ((ret = dmZLibHuffmanDecode(ctx, &z_codelength, &c)) != DMERR_OK)
+        if ((ret = dmZLibHuffmanDecode(ctx, &codeLengthCtx, &c)) != DMERR_OK)
             return ret;
 
         DMZLIB_ASSERT(c >= 0 && c < DM_ZLIB_NCODELENGTH_SIZES);
@@ -418,31 +432,43 @@
         else
         if (c == 16)
         {
-            c = dmZReceive(ctx, 2) + 3;
-            memset(codeLengths + n, codeLengths[n - 1], c);
-            n += c;
+            int bv = dmZReceive(ctx, 2) + 3;
+            if (n == 0)
+            {
+                return dmErrorDBG(DMERR_INVALID_DATA,
+                    "Invalid bit length repeat.\n");
+            }
+            memset(codeLengths + n, codeLengths[n - 1], bv);
+            n += bv;
         }
         else
         if (c == 17)
         {
-            c = dmZReceive(ctx, 3) + 3;
-            memset(codeLengths + n, 0, c);
-            n += c;
+            int bv = dmZReceive(ctx, 3) + 3;
+            memset(codeLengths + n, 0, bv);
+            n += bv;
         }
         else
         {
-            c = dmZReceive(ctx, 7) + 11;
-            memset(codeLengths + n, 0, c);
-            n += c;
+            int bv = dmZReceive(ctx, 7) + 11;
+            memset(codeLengths + n, 0, bv);
+            n += bv;
         }
     }
 
+    if (codeLengths[256] == 0)
+    {
+        return dmErrorDBG(DMERR_DATA_ERROR,
+            "Invalid code -- missing end-of-block.\n");
+    }
+
     if (n != hlit + hdist)
     {
         return dmErrorDBG(DMERR_DATA_ERROR,
             "Bad huffman codelengths.\n");
     }
 
+    // Build the code tables
     if ((ret = dmZLibBuildHuffmanTables(&ctx->zlength, codeLengths, hlit)) != DMERR_OK)
         return ret;
 
--- a/src/dmzlib.h	Mon Mar 02 02:12:47 2015 +0200
+++ b/src/dmzlib.h	Mon Mar 02 02:56:37 2015 +0200
@@ -21,6 +21,7 @@
 #define DM_ZLIB_HUFF_CODES  (288)
 #define DM_ZLIB_HUFF_DIST   (32)
 
+
 typedef struct
 {
     BOOL    initialized;