]> Savannah Git Hosting - gnulib.git/commitdiff
time_rz: simplify CVE-2017-7476 fix
authorPaul Eggert <eggert@cs.ucla.edu>
Thu, 12 Nov 2020 03:20:42 +0000 (19:20 -0800)
committerPaul Eggert <eggert@cs.ucla.edu>
Thu, 12 Nov 2020 03:21:20 +0000 (19:21 -0800)
* lib/time_rz.c: Do not include limits.h; I think it was included
under the mistaken impression that limits.h defines SIZE_MAX.
(SIZE_MAX): Remove.
(save_abbr): Put string length into a ptrdiff_t variable,
so that the size comparison works naturally.  This
fixes CVE-2017-7476 in a cleaner way.

ChangeLog
lib/time_rz.c

index 530c9a661aab8754dff9ff3bfb3dc0b81a283a7a..fe298605e77cba4ffbf4e153ab46c242461f3cd2 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,13 @@
 2020-11-11  Paul Eggert  <eggert@cs.ucla.edu>
 
+       time_rz: simplify CVE-2017-7476 fix
+       * lib/time_rz.c: Do not include limits.h; I think it was included
+       under the mistaken impression that limits.h defines SIZE_MAX.
+       (SIZE_MAX): Remove.
+       (save_abbr): Put string length into a ptrdiff_t variable,
+       so that the size comparison works naturally.  This
+       fixes CVE-2017-7476 in a cleaner way.
+
        parse-datetime: streamline overflow checking
        When parse-datetime.y’s overflow code was written, INT_ADD_WRAPV
        did not work for unsigned destinations, and since time_t might
index c58e6831bf400549d23b4354e6298daf8a6b99f5..a33b8078bf8c27469423d2bf80e97eceb91d8241 100644 (file)
@@ -27,7 +27,6 @@
 #include <time.h>
 
 #include <errno.h>
-#include <limits.h>
 #include <stdbool.h>
 #include <stddef.h>
 #include <stdlib.h>
 #include "flexmember.h"
 #include "time-internal.h"
 
-#ifndef SIZE_MAX
-# define SIZE_MAX ((size_t) -1)
-#endif
-
 /* The approximate size to use for small allocation requests.  This is
    the largest "small" request for the GNU C library malloc.  */
 enum { DEFAULT_MXFAST = 64 * sizeof (size_t) / 4 };
@@ -125,14 +120,8 @@ save_abbr (timezone_t tz, struct tm *tm)
         {
           if (! (*zone_copy || (zone_copy == tz->abbrs && tz->tz_is_set)))
             {
-              size_t zone_size = strlen (zone) + 1;
-              size_t zone_used = zone_copy - tz->abbrs;
-              if (SIZE_MAX - zone_used < zone_size)
-                {
-                  errno = ENOMEM;
-                  return false;
-                }
-              if (zone_used + zone_size < ABBR_SIZE_MIN)
+              ptrdiff_t zone_size = strlen (zone) + 1;
+              if (zone_size < tz->abbrs + ABBR_SIZE_MIN - zone_copy)
                 extend_abbrs (zone_copy, zone, zone_size);
               else
                 {