Mercurial > hg > octave-kai > gnulib-hg
changeset 14249:52b55b447c02
TYPE_MAXIMUM: avoid theoretically undefined behavior
* lib/intprops.h (TYPE_MINIMUM, TYPE_MAXIMUM): Do not shift a
negative number, which the C Standard says has undefined behavior.
In practice this is not a problem, but might as well do it by the book.
Reported by Rich Felker and Eric Blake; see
<http://lists.gnu.org/archive/html/bug-gnulib/2011-01/msg00493.html>.
* lib/strtol.c (TYPE_MINIMUM, TYPE_MAXIMUM): Likewise.
* m4/mktime.m4 (AC_FUNC_MKTIME): Likewise.
* m4/nanosleep.m4 (gl_FUNC_NANOSLEEP): Likewise.
* m4/parse-datetime.m4 (gl_PARSE_DATETIME): Likewise.
* m4/stdint.m4 (gl_STDINT_H): Likewise.
* lib/mktime.c (TYPE_MAXIMUM): Redo slightly to match the others.
author | Paul Eggert <eggert@cs.ucla.edu> |
---|---|
date | Sat, 29 Jan 2011 23:59:31 -0800 |
parents | d10e6185929a |
children | d54c81f4d85a |
files | ChangeLog lib/intprops.h lib/mktime.c lib/strtol.c m4/mktime.m4 m4/nanosleep.m4 m4/parse-datetime.m4 m4/stdint.m4 |
diffstat | 8 files changed, 34 insertions(+), 16 deletions(-) [+] |
line wrap: on
line diff
--- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,18 @@ 2011-01-29 Paul Eggert <eggert@cs.ucla.edu> + TYPE_MAXIMUM: avoid theoretically undefined behavior + * lib/intprops.h (TYPE_MINIMUM, TYPE_MAXIMUM): Do not shift a + negative number, which the C Standard says has undefined behavior. + In practice this is not a problem, but might as well do it by the book. + Reported by Rich Felker and Eric Blake; see + <http://lists.gnu.org/archive/html/bug-gnulib/2011-01/msg00493.html>. + * lib/strtol.c (TYPE_MINIMUM, TYPE_MAXIMUM): Likewise. + * m4/mktime.m4 (AC_FUNC_MKTIME): Likewise. + * m4/nanosleep.m4 (gl_FUNC_NANOSLEEP): Likewise. + * m4/parse-datetime.m4 (gl_PARSE_DATETIME): Likewise. + * m4/stdint.m4 (gl_STDINT_H): Likewise. + * lib/mktime.c (TYPE_MAXIMUM): Redo slightly to match the others. + mktime: #undef mktime before #defining it * lib/mktime.c (mktime) [DEBUG]: #undef mktime before #defining it.
--- a/lib/intprops.h +++ b/lib/intprops.h @@ -49,11 +49,11 @@ ? (t) 0 \ : TYPE_SIGNED_MAGNITUDE (t) \ ? ~ (t) 0 \ - : ~ (t) 0 << (sizeof (t) * CHAR_BIT - 1))) + : ~ TYPE_MAXIMUM (t))) # define TYPE_MAXIMUM(t) \ ((t) (! TYPE_SIGNED (t) \ ? (t) -1 \ - : ~ (~ (t) 0 << (sizeof (t) * CHAR_BIT - 1)))) + : ((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) * 2 + 1))) /* Return zero if T can be determined to be an unsigned type. Otherwise, return 1.
--- a/lib/mktime.c +++ b/lib/mktime.c @@ -113,7 +113,7 @@ #define TYPE_MAXIMUM(t) \ ((t) (! TYPE_SIGNED (t) \ ? (t) -1 \ - : (((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) << 1) + 1))) + : ((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) * 2 + 1))) #ifndef TIME_T_MIN # define TIME_T_MIN TYPE_MINIMUM (time_t)
--- a/lib/strtol.c +++ b/lib/strtol.c @@ -141,11 +141,11 @@ ? (t) 0 \ : TYPE_SIGNED_MAGNITUDE (t) \ ? ~ (t) 0 \ - : ~ (t) 0 << (sizeof (t) * CHAR_BIT - 1))) + : ~ TYPE_MAXIMUM (t))) # define TYPE_MAXIMUM(t) \ ((t) (! TYPE_SIGNED (t) \ ? (t) -1 \ - : ~ (~ (t) 0 << (sizeof (t) * CHAR_BIT - 1)))) + : ((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) * 2 + 1))) # ifndef ULLONG_MAX # define ULLONG_MAX TYPE_MAXIMUM (unsigned long long)
--- a/m4/mktime.m4 +++ b/m4/mktime.m4 @@ -1,4 +1,4 @@ -# serial 18 +# serial 19 dnl Copyright (C) 2002-2003, 2005-2007, 2009-2011 Free Software Foundation, dnl Inc. dnl This file is free software; the Free Software Foundation @@ -175,12 +175,13 @@ time_t_max = (! time_t_signed ? (time_t) -1 - : ~ (~ (time_t) 0 << (sizeof (time_t) * CHAR_BIT - 1))); + : ((((time_t) 1 << (sizeof (time_t) * CHAR_BIT - 2)) - 1) + * 2 + 1)); time_t_min = (! time_t_signed ? (time_t) 0 : time_t_signed_magnitude ? ~ (time_t) 0 - : ~ (time_t) 0 << (sizeof (time_t) * CHAR_BIT - 1)); + : ~ time_t_max); delta = time_t_max / 997; /* a suitable prime number */ for (i = 0; i < N_STRINGS; i++)
--- a/m4/nanosleep.m4 +++ b/m4/nanosleep.m4 @@ -1,4 +1,4 @@ -# serial 32 +# serial 33 dnl From Jim Meyering. dnl Check for the nanosleep function. @@ -58,7 +58,7 @@ #define TYPE_MAXIMUM(t) \ ((t) (! TYPE_SIGNED (t) \ ? (t) -1 \ - : ~ (~ (t) 0 << (sizeof (t) * CHAR_BIT - 1)))) + : ((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) * 2 + 1))) static void check_for_SIGALRM (int sig)
--- a/m4/parse-datetime.m4 +++ b/m4/parse-datetime.m4 @@ -1,4 +1,4 @@ -# parse-datetime.m4 serial 18 +# parse-datetime.m4 serial 19 dnl Copyright (C) 2002-2006, 2008-2011 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -41,9 +41,11 @@ #include <time.h> /* for time_t */ #include <limits.h> /* for CHAR_BIT, LONG_MIN, LONG_MAX */ #define TYPE_MINIMUM(t) \ - ((t) ((t) 0 < (t) -1 ? (t) 0 : ~ (t) 0 << (sizeof (t) * CHAR_BIT - 1))) + ((t) ((t) 0 < (t) -1 ? (t) 0 : ~ TYPE_MAXIMUM (t))) #define TYPE_MAXIMUM(t) \ - ((t) ((t) 0 < (t) -1 ? (t) -1 : ~ (~ (t) 0 << (sizeof (t) * CHAR_BIT - 1)))) + ((t) ((t) 0 < (t) -1 \ + ? (t) -1 \ + : ((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) * 2 + 1))) typedef int verify_min[2 * (LONG_MIN <= TYPE_MINIMUM (time_t)) - 1]; typedef int verify_max[2 * (TYPE_MAXIMUM (time_t) <= LONG_MAX) - 1]; ]])],
--- a/m4/stdint.m4 +++ b/m4/stdint.m4 @@ -1,4 +1,4 @@ -# stdint.m4 serial 36 +# stdint.m4 serial 37 dnl Copyright (C) 2001-2011 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, @@ -145,9 +145,11 @@ #include <limits.h> /* for CHAR_BIT */ #define TYPE_MINIMUM(t) \ - ((t) ((t) 0 < (t) -1 ? (t) 0 : ~ (t) 0 << (sizeof (t) * CHAR_BIT - 1))) + ((t) ((t) 0 < (t) -1 ? (t) 0 : ~ TYPE_MAXIMUM (t))) #define TYPE_MAXIMUM(t) \ - ((t) ((t) 0 < (t) -1 ? (t) -1 : ~ (~ (t) 0 << (sizeof (t) * CHAR_BIT - 1)))) + ((t) ((t) 0 < (t) -1 \ + ? (t) -1 \ + : ((((t) 1 << (sizeof (t) * CHAR_BIT - 2)) - 1) * 2 + 1))) struct s { int check_PTRDIFF: PTRDIFF_MIN == TYPE_MINIMUM (ptrdiff_t)