]> git.ipfire.org Git - thirdparty/zlib-ng.git/commitdiff
Fixed unsigned integer overflow ASAN error when hash_head > s->strstart.
authorNathan Moinvaziri <nathan@nathanm.com>
Sun, 20 Sep 2020 02:39:42 +0000 (19:39 -0700)
committerHans Kristian Rosbach <hk-github@circlestorm.org>
Sun, 18 Oct 2020 12:35:55 +0000 (14:35 +0200)
  zlib-ng/deflate_medium.c:244:47: runtime error: unsigned integer overflow: 58442 - 58452 cannot be represented in type 'unsigned int'

Co-authored-by: Mika Lindqvist <postmaster@raasu.org>
Co-authored-by: Hans Kristian Rosbach <hk-git@circlestorm.org>
deflate_fast.c
deflate_medium.c
deflate_quick.c
deflate_slow.c

index a88e60272bab1d186a4867694b8e60cf36411f08..14718ba14cbdb62714001b0d7807f1578be15e0c 100644 (file)
@@ -19,6 +19,7 @@
 Z_INTERNAL block_state deflate_fast(deflate_state *s, int flush) {
     Pos hash_head;        /* head of the hash chain */
     int bflush = 0;       /* set if current block must be flushed */
+    int64_t dist;
     uint32_t match_len = 0;
 
     for (;;) {
@@ -41,10 +42,13 @@ Z_INTERNAL block_state deflate_fast(deflate_state *s, int flush) {
          */
         if (s->lookahead >= MIN_MATCH) {
             hash_head = functable.quick_insert_string(s, s->strstart);
+            dist = (int64_t)s->strstart - hash_head;
+
             /* Find the longest match, discarding those <= prev_length.
              * At this point we have always match length < MIN_MATCH
              */
-            if (hash_head != 0 && s->strstart - hash_head <= MAX_DIST(s)) {
+            
+            if (dist <= MAX_DIST(s) && dist > 0) {
                 /* To simplify the code, we prevent matches with the string
                  * of window index 0 (in particular we have to avoid a match
                  * of the string with itself at the start of the input file).
index a5b1b9a1e238ae79285de7f2a462ebd54277e2f3..27ca1905ef25429bc7187c9eba3305e073803cfa 100644 (file)
@@ -171,6 +171,7 @@ Z_INTERNAL block_state deflate_medium(deflate_state *s, int flush) {
     for (;;) {
         Pos hash_head = 0;    /* head of the hash chain */
         int bflush = 0;       /* set if current block must be flushed */
+        int64_t dist;
 
         /* Make sure that we always have enough lookahead, except
          * at the end of the input file. We need MAX_MATCH bytes
@@ -208,7 +209,8 @@ Z_INTERNAL block_state deflate_medium(deflate_state *s, int flush) {
              * At this point we have always match_length < MIN_MATCH
              */
 
-            if (hash_head != 0 && s->strstart - hash_head <= MAX_DIST(s)) {
+            dist = (int64_t)s->strstart - hash_head;
+            if (dist <= MAX_DIST(s) && dist > 0) {
                 /* To simplify the code, we prevent matches with the string
                  * of window index 0 (in particular we have to avoid a match
                  * of the string with itself at the start of the input file).
@@ -241,7 +243,9 @@ Z_INTERNAL block_state deflate_medium(deflate_state *s, int flush) {
             /* Find the longest match, discarding those <= prev_length.
              * At this point we have always match_length < MIN_MATCH
              */
-            if (hash_head != 0 && s->strstart - hash_head <= MAX_DIST(s)) {
+
+            dist = (int64_t)s->strstart - hash_head;
+            if (dist <= MAX_DIST(s) && dist > 0) {
                 /* To simplify the code, we prevent matches with the string
                  * of window index 0 (in particular we have to avoid a match
                  * of the string with itself at the start of the input file).
index 3ed934cbda6e0ba8ce16626db958ded045bddafa..268cce80d16fa0da91268818a873c0d57b4bfc46 100644 (file)
@@ -45,7 +45,8 @@ extern const ct_data static_dtree[D_CODES];
 
 Z_INTERNAL block_state deflate_quick(deflate_state *s, int flush) {
     Pos hash_head;
-    unsigned dist, match_len, last;
+    int64_t dist;
+    unsigned match_len, last;
 
 
     last = (flush == Z_FINISH) ? 1 : 0;
@@ -85,9 +86,9 @@ Z_INTERNAL block_state deflate_quick(deflate_state *s, int flush) {
 
         if (LIKELY(s->lookahead >= MIN_MATCH)) {
             hash_head = functable.quick_insert_string(s, s->strstart);
-            dist = s->strstart - hash_head;
+            dist = (int64_t)s->strstart - hash_head;
 
-            if (dist > 0 && dist < MAX_DIST(s)) {
+            if (dist <= MAX_DIST(s) && dist > 0) {
                 match_len = functable.compare258(s->window + s->strstart, s->window + hash_head);
 
                 if (match_len >= MIN_MATCH) {
@@ -96,7 +97,7 @@ Z_INTERNAL block_state deflate_quick(deflate_state *s, int flush) {
 
                     check_match(s, s->strstart, hash_head, match_len);
 
-                    zng_tr_emit_dist(s, static_ltree, static_dtree, match_len - MIN_MATCH, dist);
+                    zng_tr_emit_dist(s, static_ltree, static_dtree, match_len - MIN_MATCH, (uint32_t)dist);
                     s->lookahead -= match_len;
                     s->strstart += match_len;
                     continue;
index ea5eed8448c733cf79cdc52c9502a85444bec9c9..cac8a96299b76c5c8b1c1bd762c9024e01e64e98 100644 (file)
@@ -17,6 +17,7 @@
 Z_INTERNAL block_state deflate_slow(deflate_state *s, int flush) {
     Pos hash_head;           /* head of hash chain */
     int bflush;              /* set if current block must be flushed */
+    int64_t dist;
     uint32_t match_len;
 
     /* Process the input block. */
@@ -47,8 +48,9 @@ Z_INTERNAL block_state deflate_slow(deflate_state *s, int flush) {
          */
         s->prev_match = (Pos)s->match_start;
         match_len = MIN_MATCH-1;
+        dist = (int64_t)s->strstart - hash_head;
 
-        if (hash_head != 0 && s->prev_length < s->max_lazy_match && s->strstart - hash_head <= MAX_DIST(s)) {
+        if (dist <= MAX_DIST(s) && dist > 0 && s->prev_length < s->max_lazy_match) {
             /* To simplify the code, we prevent matches with the string
              * of window index 0 (in particular we have to avoid a match
              * of the string with itself at the start of the input file).