bug-gnulib@gnu.org mirror (unofficial)
 help / color / mirror / Atom feed
* mingw strtol bug
@ 2021-03-17 13:08 Eric Blake
  2021-04-02 19:00 ` Bruno Haible
  0 siblings, 1 reply; 2+ messages in thread
From: Eric Blake @ 2021-03-17 13:08 UTC (permalink / raw)
  To: Gnulib bugs

I ran into a mingw bug on strtol() today, and don't see it documented or
worked around in gnulib:

$ cat foo.c
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>

int main(void)
{
    unsigned long u;
    const char *str = "0x";
    char *end;
    errno = 0;
    u = strtoul(str, &end, 10);
    printf("%lu %s %d\n", u, end, errno);
    errno = 0;
    u = strtoul(str, &end, 16);
    printf("%lu %s %d\n", u, end, errno);
    errno = 0;
    u = strtoul(str, &end, 0);
    printf("%lu %s %d\n", u, end, errno);

    str = "0xq";
    errno = 0;
    u = strtoul(str, &end, 10);
    printf("%lu %s %d\n", u, end, errno);
    errno = 0;
    u = strtoul(str, &end, 16);
    printf("%lu %s %d\n", u, end, errno);
    errno = 0;
    u = strtoul(str, &end, 0);
    printf("%lu %s %d\n", u, end, errno);
    return 0;
}
$ gcc                    -o foo-linux -Wall foo.c
$ x86_64-w64-mingw32-gcc -o foo-mingw -Wall foo.c
$ ./foo-linux
0 x 0
0 x 0
0 x 0
0 xq 0
0 xq 0
0 xq 0
$ wine ./foo-mingw.exe 2>/dev/null
0 x 0
0 0x 0
0 0x 0
0 xq 0
0 0xq 0
0 0xq 0

In short, mingw (at least when run under wine, I did not actually test
on a Windows machine) fails to properly consume '0' when parsing in base
16 or 0 when there are no hex digits after a trailing garbage of 'x' or 'X'.

-- 
Eric Blake, Principal Software Engineer
Red Hat, Inc.           +1-919-301-3226
Virtualization:  qemu.org | libvirt.org



^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: mingw strtol bug
  2021-03-17 13:08 mingw strtol bug Eric Blake
@ 2021-04-02 19:00 ` Bruno Haible
  0 siblings, 0 replies; 2+ messages in thread
From: Bruno Haible @ 2021-04-02 19:00 UTC (permalink / raw)
  To: bug-gnulib; +Cc: Eric Blake

[-- Attachment #1: Type: text/plain, Size: 3863 bytes --]

Hi Eric,

> I ran into a mingw bug on strtol() today, and don't see it documented or
> worked around in gnulib:

Thanks for the report and test case. The functions strtoul(), strtoll(),
strtoull() are equally affected. I'm adding workarounds to gnulib.


2021-04-02  Bruno Haible  <bruno@clisp.org>

	strtoul, strtoll, strtoull: Fix compilation warning.
	* lib/strtol.c (strtol): Undefine before defining as a macro.

2021-04-02  Bruno Haible  <bruno@clisp.org>

	strtoll: Work around a bug on native Windows and Minix.
	* lib/stdlib.in.h (strtoll): Override if REPLACE_STRTOLL is 1.
	* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOLL.
	* m4/strtoll.m4 (gl_FUNC_STRTOLL): Test whether strtoll works. Set
	REPLACE_STRTOLL.
	* modules/stdlib (Makefile.am): Substitute REPLACE_STRTOLL.
	* modules/strtoll (configure.ac): Test REPLACE_STRTOLL.
	* tests/test-strtoll.c (main): Add tests of hexadecimal integer syntax.
	* doc/posix-functions/strtoll.texi: Mention the bug.

2021-04-02  Bruno Haible  <bruno@clisp.org>

	strtol: Work around a bug on native Windows and Minix.
	* lib/stdlib.in.h (strtol): New declaration.
	* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtol is declared.
	(gl_STDLIB_H_DEFAULTS): Initialize GNULIB_STRTOL, HAVE_STRTOL,
	REPLACE_STRTOL.
	* m4/strtol.m4 (gl_FUNC_STRTOL): Require gl_STDLIB_H_DEFAULTS. Test
	whether strtol works. Set REPLACE_STRTOL.
	* modules/stdlib (Makefile.am): Substitute GNULIB_STRTOL, HAVE_STRTOL,
	REPLACE_STRTOL.
	* modules/strtol (Status, Notice): Remove.
	(Depends-on): Add stdlib.
	(configure.ac): Test HAVE_STRTOL and REPLACE_STRTOL. Invoke
	gl_STDLIB_MODULE_INDICATOR.
	* tests/test-strtol.c (main): Add tests of hexadecimal integer syntax.
	* doc/posix-functions/strtol.texi: Mention the bug.

2021-04-02  Bruno Haible  <bruno@clisp.org>

	strtoull: Work around a bug on native Windows and Minix.
	* lib/stdlib.in.h (strtoull): Override if REPLACE_STRTOULL is 1.
	* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOULL.
	* m4/strtoull.m4 (gl_FUNC_STRTOULL): Test whether strtoull works. Set
	REPLACE_STRTOULL.
	* modules/stdlib (Makefile.am): Substitute REPLACE_STRTOULL.
	* modules/strtoull (configure.ac): Test REPLACE_STRTOULL.
	* tests/test-strtoull.c (main): Add tests of hexadecimal integer syntax.
	* doc/posix-functions/strtoull.texi: Mention the bug.

2021-04-02  Bruno Haible  <bruno@clisp.org>

	strtoul: Work around a bug on native Windows and Minix.
	Reported by Eric Blake <eblake@redhat.com> in
	<https://lists.gnu.org/archive/html/bug-gnulib/2021-03/msg00082.html>.
	* lib/stdlib.in.h (strtoul): New declaration.
	* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtoul is declared.
	(gl_STDLIB_H_DEFAULTS): Initialize GNULIB_STRTOUL, HAVE_STRTOUL,
	REPLACE_STRTOUL.
	* m4/strtoul.m4 (gl_FUNC_STRTOUL): Require gl_STDLIB_H_DEFAULTS. Test
	whether strtoul works. Set REPLACE_STRTOUL.
	* modules/stdlib (Makefile.am): Substitute GNULIB_STRTOUL, HAVE_STRTOUL,
	REPLACE_STRTOUL.
	* modules/strtoul (Status, Notice): Remove.
	(Depends-on): Add stdlib.
	(configure.ac): Test HAVE_STRTOUL and REPLACE_STRTOUL. Invoke
	gl_STDLIB_MODULE_INDICATOR.
	* tests/test-strtoul.c (main): Add tests of hexadecimal integer syntax.
	* doc/posix-functions/strtoul.texi: Mention the bug.

2021-04-02  Bruno Haible  <bruno@clisp.org>

	strtol, strtoul, strtoll, strtoull: Optimize.
	* lib/strtol.c (GROUP_PARAM_PROTO): New macro.
	(INTERNAL): Define differently if !USE_NUMBER_GROUPING.
	(INTERNAL (strtol)): Define without 'int group' parameter if
	!USE_NUMBER_GROUPING.
	(strtol): Don't define if !USE_NUMBER_GROUPING.

2021-04-02  Bruno Haible  <bruno@clisp.org>

	strto*l: Don't pass invalid arguments to isspace, isalnum, toupper.
	* lib/strtol.c (ISSPACE, ISALPHA, TOUPPER): Cast argument to
	'unsigned char' before passing it to the functions isspace(), isalpha(),
	toupper().


[-- Attachment #2: 0001-strto-l-Don-t-pass-invalid-arguments-to-isspace-isal.patch --]
[-- Type: text/x-patch, Size: 2001 bytes --]

From 71958eb7080485d7291b8b622b09e6b198f0d920 Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 19:47:53 +0200
Subject: [PATCH 1/7] strto*l: Don't pass invalid arguments to isspace,
 isalnum, toupper.

* lib/strtol.c (ISSPACE, ISALPHA, TOUPPER): Cast argument to
'unsigned char' before passing it to the functions isspace(), isalpha(),
toupper().
---
 ChangeLog    |  7 +++++++
 lib/strtol.c | 12 ++++++------
 2 files changed, 13 insertions(+), 6 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index f4e766f..0bf4c58 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,12 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strto*l: Don't pass invalid arguments to isspace, isalnum, toupper.
+	* lib/strtol.c (ISSPACE, ISALPHA, TOUPPER): Cast argument to
+	'unsigned char' before passing it to the functions isspace(), isalpha(),
+	toupper().
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	glob: Reject ~user syntax, when flag GLOB_TILDE_CHECK is given.
 	Reported and patch suggested by Eli Zaretskii <eliz@gnu.org> in
 	<https://lists.gnu.org/archive/html/bug-gnulib/2021-03/msg00136.html>.
diff --git a/lib/strtol.c b/lib/strtol.c
index 2f2159b..14836d0 100644
--- a/lib/strtol.c
+++ b/lib/strtol.c
@@ -166,13 +166,13 @@
 # define UCHAR_TYPE unsigned char
 # define STRING_TYPE char
 # ifdef USE_IN_EXTENDED_LOCALE_MODEL
-#  define ISSPACE(Ch) __isspace_l ((Ch), loc)
-#  define ISALPHA(Ch) __isalpha_l ((Ch), loc)
-#  define TOUPPER(Ch) __toupper_l ((Ch), loc)
+#  define ISSPACE(Ch) __isspace_l ((unsigned char) (Ch), loc)
+#  define ISALPHA(Ch) __isalpha_l ((unsigned char) (Ch), loc)
+#  define TOUPPER(Ch) __toupper_l ((unsigned char) (Ch), loc)
 # else
-#  define ISSPACE(Ch) isspace (Ch)
-#  define ISALPHA(Ch) isalpha (Ch)
-#  define TOUPPER(Ch) toupper (Ch)
+#  define ISSPACE(Ch) isspace ((unsigned char) (Ch))
+#  define ISALPHA(Ch) isalpha ((unsigned char) (Ch))
+#  define TOUPPER(Ch) toupper ((unsigned char) (Ch))
 # endif
 #endif
 
-- 
2.7.4


[-- Attachment #3: 0002-strtol-strtoul-strtoll-strtoull-Optimize.patch --]
[-- Type: text/x-patch, Size: 2835 bytes --]

From 022521230ffa940a5428ee2a50120dc882920b16 Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 19:50:19 +0200
Subject: [PATCH 2/7] strtol, strtoul, strtoll, strtoull: Optimize.

* lib/strtol.c (GROUP_PARAM_PROTO): New macro.
(INTERNAL): Define differently if !USE_NUMBER_GROUPING.
(INTERNAL (strtol)): Define without 'int group' parameter if
!USE_NUMBER_GROUPING.
(strtol): Don't define if !USE_NUMBER_GROUPING.
---
 ChangeLog    |  9 +++++++++
 lib/strtol.c | 25 ++++++++++++++++++-------
 2 files changed, 27 insertions(+), 7 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 0bf4c58..d5b833a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,14 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strtol, strtoul, strtoll, strtoull: Optimize.
+	* lib/strtol.c (GROUP_PARAM_PROTO): New macro.
+	(INTERNAL): Define differently if !USE_NUMBER_GROUPING.
+	(INTERNAL (strtol)): Define without 'int group' parameter if
+	!USE_NUMBER_GROUPING.
+	(strtol): Don't define if !USE_NUMBER_GROUPING.
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	strto*l: Don't pass invalid arguments to isspace, isalnum, toupper.
 	* lib/strtol.c (ISSPACE, ISALPHA, TOUPPER): Cast argument to
 	'unsigned char' before passing it to the functions isspace(), isalpha(),
diff --git a/lib/strtol.c b/lib/strtol.c
index 14836d0..c30e5b4 100644
--- a/lib/strtol.c
+++ b/lib/strtol.c
@@ -131,6 +131,12 @@
 #endif
 
 
+#ifdef USE_NUMBER_GROUPING
+# define GROUP_PARAM_PROTO , int group
+#else
+# define GROUP_PARAM_PROTO
+#endif
+
 /* We use this code also for the extended locale handling where the
    function gets as an additional argument the locale which has to be
    used.  To access the values we have to redefine the _NL_CURRENT
@@ -176,9 +182,13 @@
 # endif
 #endif
 
-#define INTERNAL(X) INTERNAL1(X)
-#define INTERNAL1(X) __##X##_internal
-#define WEAKNAME(X) WEAKNAME1(X)
+#ifdef USE_NUMBER_GROUPING
+# define INTERNAL(X) INTERNAL1(X)
+# define INTERNAL1(X) __##X##_internal
+# define WEAKNAME(X) WEAKNAME1(X)
+#else
+# define INTERNAL(X) X
+#endif
 
 #ifdef USE_NUMBER_GROUPING
 /* This file defines a function to check for correct grouping.  */
@@ -196,7 +206,7 @@
 
 INT
 INTERNAL (strtol) (const STRING_TYPE *nptr, STRING_TYPE **endptr,
-                   int base, int group LOCALE_PARAM_PROTO)
+                   int base GROUP_PARAM_PROTO LOCALE_PARAM_PROTO)
 {
   int negative;
   register unsigned LONG int cutoff;
@@ -379,15 +389,16 @@ noconv:
   return 0L;
 }
 \f
+#ifdef USE_NUMBER_GROUPING
 /* External user entry point.  */
 
-
 INT
-#ifdef weak_function
+# ifdef weak_function
 weak_function
-#endif
+# endif
 strtol (const STRING_TYPE *nptr, STRING_TYPE **endptr,
         int base LOCALE_PARAM_PROTO)
 {
   return INTERNAL (strtol) (nptr, endptr, base, 0 LOCALE_PARAM);
 }
+#endif
-- 
2.7.4


[-- Attachment #4: 0003-strtoul-Work-around-a-bug-on-native-Windows-and-Mini.patch --]
[-- Type: text/x-patch, Size: 12853 bytes --]

From cbff21f910e678340da2cadf0bbf2bdc191c0eb9 Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 19:56:28 +0200
Subject: [PATCH 3/7] strtoul: Work around a bug on native Windows and Minix.

Reported by Eric Blake <eblake@redhat.com> in
<https://lists.gnu.org/archive/html/bug-gnulib/2021-03/msg00082.html>.

* lib/stdlib.in.h (strtoul): New declaration.
* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtoul is declared.
(gl_STDLIB_H_DEFAULTS): Initialize GNULIB_STRTOUL, HAVE_STRTOUL,
REPLACE_STRTOUL.
* m4/strtoul.m4 (gl_FUNC_STRTOUL): Require gl_STDLIB_H_DEFAULTS. Test
whether strtoul works. Set REPLACE_STRTOUL.
* modules/stdlib (Makefile.am): Substitute GNULIB_STRTOUL, HAVE_STRTOUL,
REPLACE_STRTOUL.
* modules/strtoul (Status, Notice): Remove.
(Depends-on): Add stdlib.
(configure.ac): Test HAVE_STRTOUL and REPLACE_STRTOUL. Invoke
gl_STDLIB_MODULE_INDICATOR.
* tests/test-strtoul.c (main): Add tests of hexadecimal integer syntax.
* doc/posix-functions/strtoul.texi: Mention the bug.
---
 ChangeLog                        | 20 +++++++++++++
 doc/posix-functions/strtoul.texi |  4 +++
 lib/stdlib.in.h                  | 40 ++++++++++++++++++++++++++
 m4/stdlib_h.m4                   |  7 +++--
 m4/strtoul.m4                    | 38 +++++++++++++++++++++++-
 modules/stdlib                   |  3 ++
 modules/strtoul                  | 10 ++-----
 tests/test-strtoul.c             | 62 ++++++++++++++++++++++++++++++++++++++++
 8 files changed, 174 insertions(+), 10 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index d5b833a..9ce3bae 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,25 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strtoul: Work around a bug on native Windows and Minix.
+	Reported by Eric Blake <eblake@redhat.com> in
+	<https://lists.gnu.org/archive/html/bug-gnulib/2021-03/msg00082.html>.
+	* lib/stdlib.in.h (strtoul): New declaration.
+	* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtoul is declared.
+	(gl_STDLIB_H_DEFAULTS): Initialize GNULIB_STRTOUL, HAVE_STRTOUL,
+	REPLACE_STRTOUL.
+	* m4/strtoul.m4 (gl_FUNC_STRTOUL): Require gl_STDLIB_H_DEFAULTS. Test
+	whether strtoul works. Set REPLACE_STRTOUL.
+	* modules/stdlib (Makefile.am): Substitute GNULIB_STRTOUL, HAVE_STRTOUL,
+	REPLACE_STRTOUL.
+	* modules/strtoul (Status, Notice): Remove.
+	(Depends-on): Add stdlib.
+	(configure.ac): Test HAVE_STRTOUL and REPLACE_STRTOUL. Invoke
+	gl_STDLIB_MODULE_INDICATOR.
+	* tests/test-strtoul.c (main): Add tests of hexadecimal integer syntax.
+	* doc/posix-functions/strtoul.texi: Mention the bug.
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	strtol, strtoul, strtoll, strtoull: Optimize.
 	* lib/strtol.c (GROUP_PARAM_PROTO): New macro.
 	(INTERNAL): Define differently if !USE_NUMBER_GROUPING.
diff --git a/doc/posix-functions/strtoul.texi b/doc/posix-functions/strtoul.texi
index b79b56b..3b1fa7f 100644
--- a/doc/posix-functions/strtoul.texi
+++ b/doc/posix-functions/strtoul.texi
@@ -10,6 +10,10 @@ Portability problems fixed by Gnulib:
 @itemize
 @item
 This function is missing on some old platforms.
+@item
+This function does not parse the leading @samp{0} when the input string is
+@code{"0x"} and the base is 16 or 0 on some platforms:
+Minix 3.3, mingw, MSVC 14.
 @end itemize
 
 Portability problems not fixed by Gnulib:
diff --git a/lib/stdlib.in.h b/lib/stdlib.in.h
index 49fc44e..0a377c0 100644
--- a/lib/stdlib.in.h
+++ b/lib/stdlib.in.h
@@ -1229,6 +1229,46 @@ _GL_WARN_ON_USE (strtoll, "strtoll is unportable - "
 # endif
 #endif
 
+#if @GNULIB_STRTOUL@
+/* Parse an unsigned integer whose textual representation starts at STRING.
+   The integer is expected to be in base BASE (2 <= BASE <= 36); if BASE == 0,
+   it may be decimal or octal (with prefix "0") or hexadecimal (with prefix
+   "0x").
+   If ENDPTR is not NULL, the address of the first byte after the integer is
+   stored in *ENDPTR.
+   Upon overflow, the return value is ULONG_MAX, and errno is set to ERANGE.  */
+# if @REPLACE_STRTOUL@
+#  if !(defined __cplusplus && defined GNULIB_NAMESPACE)
+#   define strtoul rpl_strtoul
+#  endif
+#  define GNULIB_defined_strtoul_function 1
+_GL_FUNCDECL_RPL (strtoul, unsigned long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base)
+                  _GL_ARG_NONNULL ((1)));
+_GL_CXXALIAS_RPL (strtoul, unsigned long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base));
+# else
+#  if !@HAVE_STRTOUL@
+_GL_FUNCDECL_SYS (strtoul, unsigned long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base)
+                  _GL_ARG_NONNULL ((1)));
+#  endif
+_GL_CXXALIAS_SYS (strtoul, unsigned long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base));
+# endif
+_GL_CXXALIASWARN (strtoul);
+#elif defined GNULIB_POSIXCHECK
+# undef strtoul
+# if HAVE_RAW_DECL_STRTOUL
+_GL_WARN_ON_USE (strtoul, "strtoul is unportable - "
+                 "use gnulib module strtoul for portability");
+# endif
+#endif
+
 #if @GNULIB_STRTOULL@
 /* Parse an unsigned integer whose textual representation starts at STRING.
    The integer is expected to be in base BASE (2 <= BASE <= 36); if BASE == 0,
diff --git a/m4/stdlib_h.m4 b/m4/stdlib_h.m4
index 5a02972..5895586 100644
--- a/m4/stdlib_h.m4
+++ b/m4/stdlib_h.m4
@@ -1,4 +1,4 @@
-# stdlib_h.m4 serial 55
+# stdlib_h.m4 serial 56
 dnl Copyright (C) 2007-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -28,7 +28,7 @@ AC_DEFUN([gl_STDLIB_H],
     posix_memalign posix_openpt ptsname ptsname_r qsort_r
     random random_r reallocarray realpath rpmatch secure_getenv setenv
     setstate setstate_r srandom srandom_r
-    strtod strtold strtoll strtoull unlockpt unsetenv])
+    strtod strtold strtoll strtoul strtoull unlockpt unsetenv])
 
   AC_REQUIRE([AC_C_RESTRICT])
 
@@ -90,6 +90,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   GNULIB_STRTOD=0;        AC_SUBST([GNULIB_STRTOD])
   GNULIB_STRTOLD=0;       AC_SUBST([GNULIB_STRTOLD])
   GNULIB_STRTOLL=0;       AC_SUBST([GNULIB_STRTOLL])
+  GNULIB_STRTOUL=0;       AC_SUBST([GNULIB_STRTOUL])
   GNULIB_STRTOULL=0;      AC_SUBST([GNULIB_STRTOULL])
   GNULIB_SYSTEM_POSIX=0;  AC_SUBST([GNULIB_SYSTEM_POSIX])
   GNULIB_UNLOCKPT=0;      AC_SUBST([GNULIB_UNLOCKPT])
@@ -139,6 +140,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   HAVE_STRTOD=1;             AC_SUBST([HAVE_STRTOD])
   HAVE_STRTOLD=1;            AC_SUBST([HAVE_STRTOLD])
   HAVE_STRTOLL=1;            AC_SUBST([HAVE_STRTOLL])
+  HAVE_STRTOUL=1;            AC_SUBST([HAVE_STRTOUL])
   HAVE_STRTOULL=1;           AC_SUBST([HAVE_STRTOULL])
   HAVE_STRUCT_RANDOM_DATA=1; AC_SUBST([HAVE_STRUCT_RANDOM_DATA])
   HAVE_SYS_LOADAVG_H=0;      AC_SUBST([HAVE_SYS_LOADAVG_H])
@@ -165,6 +167,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   REPLACE_SETSTATE=0;        AC_SUBST([REPLACE_SETSTATE])
   REPLACE_STRTOD=0;          AC_SUBST([REPLACE_STRTOD])
   REPLACE_STRTOLD=0;         AC_SUBST([REPLACE_STRTOLD])
+  REPLACE_STRTOUL=0;         AC_SUBST([REPLACE_STRTOUL])
   REPLACE_UNSETENV=0;        AC_SUBST([REPLACE_UNSETENV])
   REPLACE_WCTOMB=0;          AC_SUBST([REPLACE_WCTOMB])
 ])
diff --git a/m4/strtoul.m4 b/m4/strtoul.m4
index 853c1a6..b915679 100644
--- a/m4/strtoul.m4
+++ b/m4/strtoul.m4
@@ -1,4 +1,4 @@
-# strtoul.m4 serial 5
+# strtoul.m4 serial 6
 dnl Copyright (C) 2002, 2006, 2009-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -6,5 +6,41 @@ dnl with or without modifications, as long as this notice is preserved.
 
 AC_DEFUN([gl_FUNC_STRTOUL],
 [
+  AC_REQUIRE([gl_STDLIB_H_DEFAULTS])
+  AC_REQUIRE([AC_CANONICAL_HOST])
   AC_CHECK_FUNCS([strtoul])
+  if test $ac_cv_func_strtoul = yes; then
+    AC_CACHE_CHECK([whether strtoul works],
+      [gl_cv_func_strtoul_works],
+      [AC_RUN_IFELSE(
+         [AC_LANG_PROGRAM(
+            [[#include <stdlib.h>]],
+            [[int result = 0;
+              char *term;
+              /* This test fails on Minix and native Windows.  */
+              {
+                const char input[] = "0x";
+                (void) strtoul (input, &term, 16);
+                if (term != input + 1)
+                  result |= 1;
+              }
+              return result;
+            ]])
+         ],
+         [gl_cv_func_strtoul_works=yes],
+         [gl_cv_func_strtoul_works=no],
+         [case "$host_os" in
+                    # Guess no on native Windows.
+            mingw*) gl_cv_func_strtoul_works="guessing no" ;;
+            *)      gl_cv_func_strtoul_works="$gl_cross_guess_normal" ;;
+          esac
+         ])
+    ])
+    case "$gl_cv_func_strtoul_works" in
+      *yes) ;;
+      *)    REPLACE_STRTOUL=1 ;;
+    esac
+  else
+    HAVE_STRTOUL=0
+  fi
 ])
diff --git a/modules/stdlib b/modules/stdlib
index 9b65a01..998f44d 100644
--- a/modules/stdlib
+++ b/modules/stdlib
@@ -64,6 +64,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's/@''GNULIB_STRTOD''@/$(GNULIB_STRTOD)/g' \
 	      -e 's/@''GNULIB_STRTOLD''@/$(GNULIB_STRTOLD)/g' \
 	      -e 's/@''GNULIB_STRTOLL''@/$(GNULIB_STRTOLL)/g' \
+	      -e 's/@''GNULIB_STRTOUL''@/$(GNULIB_STRTOUL)/g' \
 	      -e 's/@''GNULIB_STRTOULL''@/$(GNULIB_STRTOULL)/g' \
 	      -e 's/@''GNULIB_SYSTEM_POSIX''@/$(GNULIB_SYSTEM_POSIX)/g' \
 	      -e 's/@''GNULIB_UNLOCKPT''@/$(GNULIB_UNLOCKPT)/g' \
@@ -111,6 +112,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's|@''HAVE_STRTOD''@|$(HAVE_STRTOD)|g' \
 	      -e 's|@''HAVE_STRTOLD''@|$(HAVE_STRTOLD)|g' \
 	      -e 's|@''HAVE_STRTOLL''@|$(HAVE_STRTOLL)|g' \
+	      -e 's|@''HAVE_STRTOUL''@|$(HAVE_STRTOUL)|g' \
 	      -e 's|@''HAVE_STRTOULL''@|$(HAVE_STRTOULL)|g' \
 	      -e 's|@''HAVE_STRUCT_RANDOM_DATA''@|$(HAVE_STRUCT_RANDOM_DATA)|g' \
 	      -e 's|@''HAVE_SYS_LOADAVG_H''@|$(HAVE_SYS_LOADAVG_H)|g' \
@@ -137,6 +139,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's|@''REPLACE_SETSTATE''@|$(REPLACE_SETSTATE)|g' \
 	      -e 's|@''REPLACE_STRTOD''@|$(REPLACE_STRTOD)|g' \
 	      -e 's|@''REPLACE_STRTOLD''@|$(REPLACE_STRTOLD)|g' \
+	      -e 's|@''REPLACE_STRTOUL''@|$(REPLACE_STRTOUL)|g' \
 	      -e 's|@''REPLACE_UNSETENV''@|$(REPLACE_UNSETENV)|g' \
 	      -e 's|@''REPLACE_WCTOMB''@|$(REPLACE_WCTOMB)|g' \
 	      -e '/definitions of _GL_FUNCDECL_RPL/r $(CXXDEFS_H)' \
diff --git a/modules/strtoul b/modules/strtoul
index 7f3139c..c790e41 100644
--- a/modules/strtoul
+++ b/modules/strtoul
@@ -1,24 +1,20 @@
 Description:
 strtoul() function: convert string to 'unsigned long'.
 
-Status:
-obsolete
-
-Notice:
-This module is obsolete.
-
 Files:
 lib/strtol.c
 lib/strtoul.c
 m4/strtoul.m4
 
 Depends-on:
+stdlib
 
 configure.ac:
 gl_FUNC_STRTOUL
-if test $ac_cv_func_strtoul = no; then
+if test $HAVE_STRTOUL = 0 || test $REPLACE_STRTOUL = 1; then
   AC_LIBOBJ([strtoul])
 fi
+gl_STDLIB_MODULE_INDICATOR([strtoul])
 
 Makefile.am:
 
diff --git a/tests/test-strtoul.c b/tests/test-strtoul.c
index 0e1917d..d34272b 100644
--- a/tests/test-strtoul.c
+++ b/tests/test-strtoul.c
@@ -176,5 +176,67 @@ main (void)
     ASSERT (errno == 0);
   }
 
+  /* Hexadecimal integer syntax.  */
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    unsigned long result;
+    errno = 0;
+    result = strtoul (input, &ptr, 10);
+    ASSERT (result == 0UL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    unsigned long result;
+    errno = 0;
+    result = strtoul (input, &ptr, 16);
+    ASSERT (result == 42UL);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    unsigned long result;
+    errno = 0;
+    result = strtoul (input, &ptr, 0);
+    ASSERT (result == 42UL);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    unsigned long result;
+    errno = 0;
+    result = strtoul (input, &ptr, 10);
+    ASSERT (result == 0UL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    unsigned long result;
+    errno = 0;
+    result = strtoul (input, &ptr, 16);
+    ASSERT (result == 0UL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    unsigned long result;
+    errno = 0;
+    result = strtoul (input, &ptr, 0);
+    ASSERT (result == 0UL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+
   return 0;
 }
-- 
2.7.4


[-- Attachment #5: 0004-strtoull-Work-around-a-bug-on-native-Windows-and-Min.patch --]
[-- Type: text/x-patch, Size: 9165 bytes --]

From 837ffb5ee4585ce6947e1013d03c7d6f21cbd635 Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 20:14:28 +0200
Subject: [PATCH 4/7] strtoull: Work around a bug on native Windows and Minix.

* lib/stdlib.in.h (strtoull): Override if REPLACE_STRTOULL is 1.
* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOULL.
* m4/strtoull.m4 (gl_FUNC_STRTOULL): Test whether strtoull works. Set
REPLACE_STRTOULL.
* modules/stdlib (Makefile.am): Substitute REPLACE_STRTOULL.
* modules/strtoull (configure.ac): Test REPLACE_STRTOULL.
* tests/test-strtoull.c (main): Add tests of hexadecimal integer syntax.
* doc/posix-functions/strtoull.texi: Mention the bug.
---
 ChangeLog                         | 12 ++++++++
 doc/posix-functions/strtoull.texi |  4 +++
 lib/stdlib.in.h                   | 18 ++++++++++--
 m4/stdlib_h.m4                    |  3 +-
 m4/strtoull.m4                    | 36 +++++++++++++++++++++--
 modules/stdlib                    |  1 +
 modules/strtoull                  |  2 +-
 tests/test-strtoull.c             | 62 +++++++++++++++++++++++++++++++++++++++
 8 files changed, 132 insertions(+), 6 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 9ce3bae..5d752ab 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,17 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strtoull: Work around a bug on native Windows and Minix.
+	* lib/stdlib.in.h (strtoull): Override if REPLACE_STRTOULL is 1.
+	* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOULL.
+	* m4/strtoull.m4 (gl_FUNC_STRTOULL): Test whether strtoull works. Set
+	REPLACE_STRTOULL.
+	* modules/stdlib (Makefile.am): Substitute REPLACE_STRTOULL.
+	* modules/strtoull (configure.ac): Test REPLACE_STRTOULL.
+	* tests/test-strtoull.c (main): Add tests of hexadecimal integer syntax.
+	* doc/posix-functions/strtoull.texi: Mention the bug.
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	strtoul: Work around a bug on native Windows and Minix.
 	Reported by Eric Blake <eblake@redhat.com> in
 	<https://lists.gnu.org/archive/html/bug-gnulib/2021-03/msg00082.html>.
diff --git a/doc/posix-functions/strtoull.texi b/doc/posix-functions/strtoull.texi
index 2057fc7..68ede34 100644
--- a/doc/posix-functions/strtoull.texi
+++ b/doc/posix-functions/strtoull.texi
@@ -11,6 +11,10 @@ Portability problems fixed by Gnulib:
 @item
 This function is missing on some platforms:
 HP-UX 11.11, MSVC 9.
+@item
+This function does not parse the leading @samp{0} when the input string is
+@code{"0x"} and the base is 16 or 0 on some platforms:
+Minix 3.3, mingw, MSVC 14.
 @end itemize
 
 Portability problems not fixed by Gnulib:
diff --git a/lib/stdlib.in.h b/lib/stdlib.in.h
index 0a377c0..0506362 100644
--- a/lib/stdlib.in.h
+++ b/lib/stdlib.in.h
@@ -1278,15 +1278,29 @@ _GL_WARN_ON_USE (strtoul, "strtoul is unportable - "
    stored in *ENDPTR.
    Upon overflow, the return value is ULLONG_MAX, and errno is set to
    ERANGE.  */
-# if !@HAVE_STRTOULL@
+# if @REPLACE_STRTOULL@
+#  if !(defined __cplusplus && defined GNULIB_NAMESPACE)
+#   define strtoull rpl_strtoull
+#  endif
+#  define GNULIB_defined_strtoull_function 1
+_GL_FUNCDECL_RPL (strtoull, unsigned long long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base)
+                  _GL_ARG_NONNULL ((1)));
+_GL_CXXALIAS_RPL (strtoull, unsigned long long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base));
+# else
+#  if !@HAVE_STRTOULL@
 _GL_FUNCDECL_SYS (strtoull, unsigned long long,
                   (const char *restrict string, char **restrict endptr,
                    int base)
                   _GL_ARG_NONNULL ((1)));
-# endif
+#  endif
 _GL_CXXALIAS_SYS (strtoull, unsigned long long,
                   (const char *restrict string, char **restrict endptr,
                    int base));
+# endif
 _GL_CXXALIASWARN (strtoull);
 #elif defined GNULIB_POSIXCHECK
 # undef strtoull
diff --git a/m4/stdlib_h.m4 b/m4/stdlib_h.m4
index 5895586..652ba86 100644
--- a/m4/stdlib_h.m4
+++ b/m4/stdlib_h.m4
@@ -1,4 +1,4 @@
-# stdlib_h.m4 serial 56
+# stdlib_h.m4 serial 57
 dnl Copyright (C) 2007-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -168,6 +168,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   REPLACE_STRTOD=0;          AC_SUBST([REPLACE_STRTOD])
   REPLACE_STRTOLD=0;         AC_SUBST([REPLACE_STRTOLD])
   REPLACE_STRTOUL=0;         AC_SUBST([REPLACE_STRTOUL])
+  REPLACE_STRTOULL=0;        AC_SUBST([REPLACE_STRTOULL])
   REPLACE_UNSETENV=0;        AC_SUBST([REPLACE_UNSETENV])
   REPLACE_WCTOMB=0;          AC_SUBST([REPLACE_WCTOMB])
 ])
diff --git a/m4/strtoull.m4 b/m4/strtoull.m4
index 88867ee..41178cc 100644
--- a/m4/strtoull.m4
+++ b/m4/strtoull.m4
@@ -1,4 +1,4 @@
-# strtoull.m4 serial 8
+# strtoull.m4 serial 9
 dnl Copyright (C) 2002, 2004, 2006, 2008-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -7,8 +7,40 @@ dnl with or without modifications, as long as this notice is preserved.
 AC_DEFUN([gl_FUNC_STRTOULL],
 [
   AC_REQUIRE([gl_STDLIB_H_DEFAULTS])
+  AC_REQUIRE([AC_CANONICAL_HOST])
   AC_CHECK_FUNCS([strtoull])
-  if test $ac_cv_func_strtoull = no; then
+  if test $ac_cv_func_strtoull = yes; then
+    AC_CACHE_CHECK([whether strtoull works],
+      [gl_cv_func_strtoull_works],
+      [AC_RUN_IFELSE(
+         [AC_LANG_PROGRAM(
+            [[#include <stdlib.h>]],
+            [[int result = 0;
+              char *term;
+              /* This test fails on Minix and native Windows.  */
+              {
+                const char input[] = "0x";
+                (void) strtoull (input, &term, 16);
+                if (term != input + 1)
+                  result |= 1;
+              }
+              return result;
+            ]])
+         ],
+         [gl_cv_func_strtoull_works=yes],
+         [gl_cv_func_strtoull_works=no],
+         [case "$host_os" in
+                    # Guess no on native Windows.
+            mingw*) gl_cv_func_strtoull_works="guessing no" ;;
+            *)      gl_cv_func_strtoull_works="$gl_cross_guess_normal" ;;
+          esac
+         ])
+    ])
+    case "$gl_cv_func_strtoull_works" in
+      *yes) ;;
+      *)    REPLACE_STRTOULL=1 ;;
+    esac
+  else
     HAVE_STRTOULL=0
   fi
 ])
diff --git a/modules/stdlib b/modules/stdlib
index 998f44d..4bd7a5c 100644
--- a/modules/stdlib
+++ b/modules/stdlib
@@ -140,6 +140,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's|@''REPLACE_STRTOD''@|$(REPLACE_STRTOD)|g' \
 	      -e 's|@''REPLACE_STRTOLD''@|$(REPLACE_STRTOLD)|g' \
 	      -e 's|@''REPLACE_STRTOUL''@|$(REPLACE_STRTOUL)|g' \
+	      -e 's|@''REPLACE_STRTOULL''@|$(REPLACE_STRTOULL)|g' \
 	      -e 's|@''REPLACE_UNSETENV''@|$(REPLACE_UNSETENV)|g' \
 	      -e 's|@''REPLACE_WCTOMB''@|$(REPLACE_WCTOMB)|g' \
 	      -e '/definitions of _GL_FUNCDECL_RPL/r $(CXXDEFS_H)' \
diff --git a/modules/strtoull b/modules/strtoull
index ff83b69..9b5895b 100644
--- a/modules/strtoull
+++ b/modules/strtoull
@@ -13,7 +13,7 @@ stdlib
 
 configure.ac:
 gl_FUNC_STRTOULL
-if test $HAVE_STRTOULL = 0; then
+if test $HAVE_STRTOULL = 0 || test $REPLACE_STRTOULL = 1; then
   AC_LIBOBJ([strtoull])
   gl_PREREQ_STRTOULL
 fi
diff --git a/tests/test-strtoull.c b/tests/test-strtoull.c
index 8242d3c..db7b371 100644
--- a/tests/test-strtoull.c
+++ b/tests/test-strtoull.c
@@ -176,5 +176,67 @@ main (void)
     ASSERT (errno == 0);
   }
 
+  /* Hexadecimal integer syntax.  */
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    unsigned long long result;
+    errno = 0;
+    result = strtoull (input, &ptr, 10);
+    ASSERT (result == 0ULL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    unsigned long long result;
+    errno = 0;
+    result = strtoull (input, &ptr, 16);
+    ASSERT (result == 42ULL);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    unsigned long long result;
+    errno = 0;
+    result = strtoull (input, &ptr, 0);
+    ASSERT (result == 42ULL);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    unsigned long long result;
+    errno = 0;
+    result = strtoull (input, &ptr, 10);
+    ASSERT (result == 0ULL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    unsigned long long result;
+    errno = 0;
+    result = strtoull (input, &ptr, 16);
+    ASSERT (result == 0ULL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    unsigned long long result;
+    errno = 0;
+    result = strtoull (input, &ptr, 0);
+    ASSERT (result == 0ULL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+
   return 0;
 }
-- 
2.7.4


[-- Attachment #6: 0005-strtol-Work-around-a-bug-on-native-Windows-and-Minix.patch --]
[-- Type: text/x-patch, Size: 12469 bytes --]

From 705c23696fcaf5bd9d4f0aaecd106b4a2c1417b2 Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 20:42:13 +0200
Subject: [PATCH 5/7] strtol: Work around a bug on native Windows and Minix.

* lib/stdlib.in.h (strtol): New declaration.
* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtol is declared.
(gl_STDLIB_H_DEFAULTS): Initialize GNULIB_STRTOL, HAVE_STRTOL,
REPLACE_STRTOL.
* m4/strtol.m4 (gl_FUNC_STRTOL): Require gl_STDLIB_H_DEFAULTS. Test
whether strtol works. Set REPLACE_STRTOL.
* modules/stdlib (Makefile.am): Substitute GNULIB_STRTOL, HAVE_STRTOL,
REPLACE_STRTOL.
* modules/strtol (Status, Notice): Remove.
(Depends-on): Add stdlib.
(configure.ac): Test HAVE_STRTOL and REPLACE_STRTOL. Invoke
gl_STDLIB_MODULE_INDICATOR.
* tests/test-strtol.c (main): Add tests of hexadecimal integer syntax.
* doc/posix-functions/strtol.texi: Mention the bug.
---
 ChangeLog                       | 18 ++++++++++++
 doc/posix-functions/strtol.texi |  4 +++
 lib/stdlib.in.h                 | 41 +++++++++++++++++++++++++++
 m4/stdlib_h.m4                  |  7 +++--
 m4/strtol.m4                    | 38 ++++++++++++++++++++++++-
 modules/stdlib                  |  3 ++
 modules/strtol                  | 10 ++-----
 tests/test-strtol.c             | 62 +++++++++++++++++++++++++++++++++++++++++
 8 files changed, 173 insertions(+), 10 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 5d752ab..9a84589 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,23 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strtol: Work around a bug on native Windows and Minix.
+	* lib/stdlib.in.h (strtol): New declaration.
+	* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtol is declared.
+	(gl_STDLIB_H_DEFAULTS): Initialize GNULIB_STRTOL, HAVE_STRTOL,
+	REPLACE_STRTOL.
+	* m4/strtol.m4 (gl_FUNC_STRTOL): Require gl_STDLIB_H_DEFAULTS. Test
+	whether strtol works. Set REPLACE_STRTOL.
+	* modules/stdlib (Makefile.am): Substitute GNULIB_STRTOL, HAVE_STRTOL,
+	REPLACE_STRTOL.
+	* modules/strtol (Status, Notice): Remove.
+	(Depends-on): Add stdlib.
+	(configure.ac): Test HAVE_STRTOL and REPLACE_STRTOL. Invoke
+	gl_STDLIB_MODULE_INDICATOR.
+	* tests/test-strtol.c (main): Add tests of hexadecimal integer syntax.
+	* doc/posix-functions/strtol.texi: Mention the bug.
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	strtoull: Work around a bug on native Windows and Minix.
 	* lib/stdlib.in.h (strtoull): Override if REPLACE_STRTOULL is 1.
 	* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOULL.
diff --git a/doc/posix-functions/strtol.texi b/doc/posix-functions/strtol.texi
index bf539c4..c9333ce 100644
--- a/doc/posix-functions/strtol.texi
+++ b/doc/posix-functions/strtol.texi
@@ -11,6 +11,10 @@ Portability problems fixed by Gnulib:
 @item
 This function is missing on some old platforms.
 @end itemize
+@item
+This function does not parse the leading @samp{0} when the input string is
+@code{"0x"} and the base is 16 or 0 on some platforms:
+Minix 3.3, mingw, MSVC 14.
 
 Portability problems not fixed by Gnulib:
 @itemize
diff --git a/lib/stdlib.in.h b/lib/stdlib.in.h
index 0506362..e2c461b 100644
--- a/lib/stdlib.in.h
+++ b/lib/stdlib.in.h
@@ -1202,6 +1202,47 @@ _GL_WARN_ON_USE (strtold, "strtold is unportable - "
 # endif
 #endif
 
+#if @GNULIB_STRTOL@
+/* Parse a signed integer whose textual representation starts at STRING.
+   The integer is expected to be in base BASE (2 <= BASE <= 36); if BASE == 0,
+   it may be decimal or octal (with prefix "0") or hexadecimal (with prefix
+   "0x").
+   If ENDPTR is not NULL, the address of the first byte after the integer is
+   stored in *ENDPTR.
+   Upon overflow, the return value is LONG_MAX or LONG_MIN, and errno is set
+   to ERANGE.  */
+# if @REPLACE_STRTOL@
+#  if !(defined __cplusplus && defined GNULIB_NAMESPACE)
+#   define strtol rpl_strtol
+#  endif
+#  define GNULIB_defined_strtol_function 1
+_GL_FUNCDECL_RPL (strtol, long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base)
+                  _GL_ARG_NONNULL ((1)));
+_GL_CXXALIAS_RPL (strtol, long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base));
+# else
+#  if !@HAVE_STRTOL@
+_GL_FUNCDECL_SYS (strtol, long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base)
+                  _GL_ARG_NONNULL ((1)));
+#  endif
+_GL_CXXALIAS_SYS (strtol, long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base));
+# endif
+_GL_CXXALIASWARN (strtol);
+#elif defined GNULIB_POSIXCHECK
+# undef strtol
+# if HAVE_RAW_DECL_STRTOL
+_GL_WARN_ON_USE (strtol, "strtol is unportable - "
+                 "use gnulib module strtol for portability");
+# endif
+#endif
+
 #if @GNULIB_STRTOLL@
 /* Parse a signed integer whose textual representation starts at STRING.
    The integer is expected to be in base BASE (2 <= BASE <= 36); if BASE == 0,
diff --git a/m4/stdlib_h.m4 b/m4/stdlib_h.m4
index 652ba86..7f084f1 100644
--- a/m4/stdlib_h.m4
+++ b/m4/stdlib_h.m4
@@ -1,4 +1,4 @@
-# stdlib_h.m4 serial 57
+# stdlib_h.m4 serial 58
 dnl Copyright (C) 2007-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -28,7 +28,7 @@ AC_DEFUN([gl_STDLIB_H],
     posix_memalign posix_openpt ptsname ptsname_r qsort_r
     random random_r reallocarray realpath rpmatch secure_getenv setenv
     setstate setstate_r srandom srandom_r
-    strtod strtold strtoll strtoul strtoull unlockpt unsetenv])
+    strtod strtol strtold strtoll strtoul strtoull unlockpt unsetenv])
 
   AC_REQUIRE([AC_C_RESTRICT])
 
@@ -88,6 +88,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   GNULIB_SECURE_GETENV=0; AC_SUBST([GNULIB_SECURE_GETENV])
   GNULIB_SETENV=0;        AC_SUBST([GNULIB_SETENV])
   GNULIB_STRTOD=0;        AC_SUBST([GNULIB_STRTOD])
+  GNULIB_STRTOL=0;        AC_SUBST([GNULIB_STRTOL])
   GNULIB_STRTOLD=0;       AC_SUBST([GNULIB_STRTOLD])
   GNULIB_STRTOLL=0;       AC_SUBST([GNULIB_STRTOLL])
   GNULIB_STRTOUL=0;       AC_SUBST([GNULIB_STRTOUL])
@@ -138,6 +139,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   HAVE_SETSTATE=1;           AC_SUBST([HAVE_SETSTATE])
   HAVE_DECL_SETSTATE=1;      AC_SUBST([HAVE_DECL_SETSTATE])
   HAVE_STRTOD=1;             AC_SUBST([HAVE_STRTOD])
+  HAVE_STRTOL=1;             AC_SUBST([HAVE_STRTOL])
   HAVE_STRTOLD=1;            AC_SUBST([HAVE_STRTOLD])
   HAVE_STRTOLL=1;            AC_SUBST([HAVE_STRTOLL])
   HAVE_STRTOUL=1;            AC_SUBST([HAVE_STRTOUL])
@@ -166,6 +168,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   REPLACE_SETENV=0;          AC_SUBST([REPLACE_SETENV])
   REPLACE_SETSTATE=0;        AC_SUBST([REPLACE_SETSTATE])
   REPLACE_STRTOD=0;          AC_SUBST([REPLACE_STRTOD])
+  REPLACE_STRTOL=0;          AC_SUBST([REPLACE_STRTOL])
   REPLACE_STRTOLD=0;         AC_SUBST([REPLACE_STRTOLD])
   REPLACE_STRTOUL=0;         AC_SUBST([REPLACE_STRTOUL])
   REPLACE_STRTOULL=0;        AC_SUBST([REPLACE_STRTOULL])
diff --git a/m4/strtol.m4 b/m4/strtol.m4
index ec7b8d1..343507b 100644
--- a/m4/strtol.m4
+++ b/m4/strtol.m4
@@ -1,4 +1,4 @@
-# strtol.m4 serial 6
+# strtol.m4 serial 7
 dnl Copyright (C) 2002-2003, 2006, 2009-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -6,5 +6,41 @@ dnl with or without modifications, as long as this notice is preserved.
 
 AC_DEFUN([gl_FUNC_STRTOL],
 [
+  AC_REQUIRE([gl_STDLIB_H_DEFAULTS])
+  AC_REQUIRE([AC_CANONICAL_HOST])
   AC_CHECK_FUNCS([strtol])
+  if test $ac_cv_func_strtol = yes; then
+    AC_CACHE_CHECK([whether strtol works],
+      [gl_cv_func_strtol_works],
+      [AC_RUN_IFELSE(
+         [AC_LANG_PROGRAM(
+            [[#include <stdlib.h>]],
+            [[int result = 0;
+              char *term;
+              /* This test fails on Minix and native Windows.  */
+              {
+                const char input[] = "0x";
+                (void) strtol (input, &term, 16);
+                if (term != input + 1)
+                  result |= 1;
+              }
+              return result;
+            ]])
+         ],
+         [gl_cv_func_strtol_works=yes],
+         [gl_cv_func_strtol_works=no],
+         [case "$host_os" in
+                    # Guess no on native Windows.
+            mingw*) gl_cv_func_strtol_works="guessing no" ;;
+            *)      gl_cv_func_strtol_works="$gl_cross_guess_normal" ;;
+          esac
+         ])
+    ])
+    case "$gl_cv_func_strtol_works" in
+      *yes) ;;
+      *)    REPLACE_STRTOL=1 ;;
+    esac
+  else
+    HAVE_STRTOL=0
+  fi
 ])
diff --git a/modules/stdlib b/modules/stdlib
index 4bd7a5c..33b8d50 100644
--- a/modules/stdlib
+++ b/modules/stdlib
@@ -62,6 +62,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's/@''GNULIB_SECURE_GETENV''@/$(GNULIB_SECURE_GETENV)/g' \
 	      -e 's/@''GNULIB_SETENV''@/$(GNULIB_SETENV)/g' \
 	      -e 's/@''GNULIB_STRTOD''@/$(GNULIB_STRTOD)/g' \
+	      -e 's/@''GNULIB_STRTOL''@/$(GNULIB_STRTOL)/g' \
 	      -e 's/@''GNULIB_STRTOLD''@/$(GNULIB_STRTOLD)/g' \
 	      -e 's/@''GNULIB_STRTOLL''@/$(GNULIB_STRTOLL)/g' \
 	      -e 's/@''GNULIB_STRTOUL''@/$(GNULIB_STRTOUL)/g' \
@@ -110,6 +111,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's|@''HAVE_SETSTATE''@|$(HAVE_SETSTATE)|g' \
 	      -e 's|@''HAVE_DECL_SETSTATE''@|$(HAVE_DECL_SETSTATE)|g' \
 	      -e 's|@''HAVE_STRTOD''@|$(HAVE_STRTOD)|g' \
+	      -e 's|@''HAVE_STRTOL''@|$(HAVE_STRTOL)|g' \
 	      -e 's|@''HAVE_STRTOLD''@|$(HAVE_STRTOLD)|g' \
 	      -e 's|@''HAVE_STRTOLL''@|$(HAVE_STRTOLL)|g' \
 	      -e 's|@''HAVE_STRTOUL''@|$(HAVE_STRTOUL)|g' \
@@ -138,6 +140,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's|@''REPLACE_SETENV''@|$(REPLACE_SETENV)|g' \
 	      -e 's|@''REPLACE_SETSTATE''@|$(REPLACE_SETSTATE)|g' \
 	      -e 's|@''REPLACE_STRTOD''@|$(REPLACE_STRTOD)|g' \
+	      -e 's|@''REPLACE_STRTOL''@|$(REPLACE_STRTOL)|g' \
 	      -e 's|@''REPLACE_STRTOLD''@|$(REPLACE_STRTOLD)|g' \
 	      -e 's|@''REPLACE_STRTOUL''@|$(REPLACE_STRTOUL)|g' \
 	      -e 's|@''REPLACE_STRTOULL''@|$(REPLACE_STRTOULL)|g' \
diff --git a/modules/strtol b/modules/strtol
index 65b6946..24d4c73 100644
--- a/modules/strtol
+++ b/modules/strtol
@@ -1,23 +1,19 @@
 Description:
 strtol() function: convert string to 'long'.
 
-Status:
-obsolete
-
-Notice:
-This module is obsolete.
-
 Files:
 lib/strtol.c
 m4/strtol.m4
 
 Depends-on:
+stdlib
 
 configure.ac:
 gl_FUNC_STRTOL
-if test $ac_cv_func_strtol = no; then
+if test $HAVE_STRTOL = 0 || test $REPLACE_STRTOL = 1; then
   AC_LIBOBJ([strtol])
 fi
+gl_STDLIB_MODULE_INDICATOR([strtol])
 
 Makefile.am:
 
diff --git a/tests/test-strtol.c b/tests/test-strtol.c
index 105bc58..467514c 100644
--- a/tests/test-strtol.c
+++ b/tests/test-strtol.c
@@ -177,5 +177,67 @@ main (void)
       ASSERT (errno == 0);
     }
 
+  /* Hexadecimal integer syntax.  */
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    long result;
+    errno = 0;
+    result = strtol (input, &ptr, 10);
+    ASSERT (result == 0L);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    long result;
+    errno = 0;
+    result = strtol (input, &ptr, 16);
+    ASSERT (result == 42L);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    long result;
+    errno = 0;
+    result = strtol (input, &ptr, 0);
+    ASSERT (result == 42L);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    long result;
+    errno = 0;
+    result = strtol (input, &ptr, 10);
+    ASSERT (result == 0L);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    long result;
+    errno = 0;
+    result = strtol (input, &ptr, 16);
+    ASSERT (result == 0L);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    long result;
+    errno = 0;
+    result = strtol (input, &ptr, 0);
+    ASSERT (result == 0L);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+
   return 0;
 }
-- 
2.7.4


[-- Attachment #7: 0006-strtoll-Work-around-a-bug-on-native-Windows-and-Mini.patch --]
[-- Type: text/x-patch, Size: 9037 bytes --]

From ea1816fd6d334b4bfd8368a63d9bda3cad1c9b0d Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 20:46:15 +0200
Subject: [PATCH 6/7] strtoll: Work around a bug on native Windows and Minix.

* lib/stdlib.in.h (strtoll): Override if REPLACE_STRTOLL is 1.
* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOLL.
* m4/strtoll.m4 (gl_FUNC_STRTOLL): Test whether strtoll works. Set
REPLACE_STRTOLL.
* modules/stdlib (Makefile.am): Substitute REPLACE_STRTOLL.
* modules/strtoll (configure.ac): Test REPLACE_STRTOLL.
* tests/test-strtoll.c (main): Add tests of hexadecimal integer syntax.
* doc/posix-functions/strtoll.texi: Mention the bug.
---
 ChangeLog                        | 12 ++++++++
 doc/posix-functions/strtoll.texi |  4 +++
 lib/stdlib.in.h                  | 18 ++++++++++--
 m4/stdlib_h.m4                   |  3 +-
 m4/strtoll.m4                    | 36 +++++++++++++++++++++--
 modules/stdlib                   |  1 +
 modules/strtoll                  |  2 +-
 tests/test-strtoll.c             | 62 ++++++++++++++++++++++++++++++++++++++++
 8 files changed, 132 insertions(+), 6 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 9a84589..b479574 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,17 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strtoll: Work around a bug on native Windows and Minix.
+	* lib/stdlib.in.h (strtoll): Override if REPLACE_STRTOLL is 1.
+	* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOLL.
+	* m4/strtoll.m4 (gl_FUNC_STRTOLL): Test whether strtoll works. Set
+	REPLACE_STRTOLL.
+	* modules/stdlib (Makefile.am): Substitute REPLACE_STRTOLL.
+	* modules/strtoll (configure.ac): Test REPLACE_STRTOLL.
+	* tests/test-strtoll.c (main): Add tests of hexadecimal integer syntax.
+	* doc/posix-functions/strtoll.texi: Mention the bug.
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	strtol: Work around a bug on native Windows and Minix.
 	* lib/stdlib.in.h (strtol): New declaration.
 	* m4/stdlib_h.m4 (gl_STDLIB_H): Test whether strtol is declared.
diff --git a/doc/posix-functions/strtoll.texi b/doc/posix-functions/strtoll.texi
index 45a7035..b507fc3 100644
--- a/doc/posix-functions/strtoll.texi
+++ b/doc/posix-functions/strtoll.texi
@@ -11,6 +11,10 @@ Portability problems fixed by Gnulib:
 @item
 This function is missing on some platforms:
 HP-UX 11.11, MSVC 9.
+@item
+This function does not parse the leading @samp{0} when the input string is
+@code{"0x"} and the base is 16 or 0 on some platforms:
+Minix 3.3, mingw, MSVC 14.
 @end itemize
 
 Portability problems not fixed by Gnulib:
diff --git a/lib/stdlib.in.h b/lib/stdlib.in.h
index e2c461b..c07fd1f 100644
--- a/lib/stdlib.in.h
+++ b/lib/stdlib.in.h
@@ -1252,15 +1252,29 @@ _GL_WARN_ON_USE (strtol, "strtol is unportable - "
    stored in *ENDPTR.
    Upon overflow, the return value is LLONG_MAX or LLONG_MIN, and errno is set
    to ERANGE.  */
-# if !@HAVE_STRTOLL@
+# if @REPLACE_STRTOLL@
+#  if !(defined __cplusplus && defined GNULIB_NAMESPACE)
+#   define strtoll rpl_strtoll
+#  endif
+#  define GNULIB_defined_strtoll_function 1
+_GL_FUNCDECL_RPL (strtoll, long long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base)
+                  _GL_ARG_NONNULL ((1)));
+_GL_CXXALIAS_RPL (strtoll, long long,
+                  (const char *restrict string, char **restrict endptr,
+                   int base));
+# else
+#  if !@HAVE_STRTOLL@
 _GL_FUNCDECL_SYS (strtoll, long long,
                   (const char *restrict string, char **restrict endptr,
                    int base)
                   _GL_ARG_NONNULL ((1)));
-# endif
+#  endif
 _GL_CXXALIAS_SYS (strtoll, long long,
                   (const char *restrict string, char **restrict endptr,
                    int base));
+# endif
 _GL_CXXALIASWARN (strtoll);
 #elif defined GNULIB_POSIXCHECK
 # undef strtoll
diff --git a/m4/stdlib_h.m4 b/m4/stdlib_h.m4
index 7f084f1..5fdb0a7 100644
--- a/m4/stdlib_h.m4
+++ b/m4/stdlib_h.m4
@@ -1,4 +1,4 @@
-# stdlib_h.m4 serial 58
+# stdlib_h.m4 serial 59
 dnl Copyright (C) 2007-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -170,6 +170,7 @@ AC_DEFUN([gl_STDLIB_H_DEFAULTS],
   REPLACE_STRTOD=0;          AC_SUBST([REPLACE_STRTOD])
   REPLACE_STRTOL=0;          AC_SUBST([REPLACE_STRTOL])
   REPLACE_STRTOLD=0;         AC_SUBST([REPLACE_STRTOLD])
+  REPLACE_STRTOLL=0;         AC_SUBST([REPLACE_STRTOLL])
   REPLACE_STRTOUL=0;         AC_SUBST([REPLACE_STRTOUL])
   REPLACE_STRTOULL=0;        AC_SUBST([REPLACE_STRTOULL])
   REPLACE_UNSETENV=0;        AC_SUBST([REPLACE_UNSETENV])
diff --git a/m4/strtoll.m4 b/m4/strtoll.m4
index d2c9e53..14455dc 100644
--- a/m4/strtoll.m4
+++ b/m4/strtoll.m4
@@ -1,4 +1,4 @@
-# strtoll.m4 serial 8
+# strtoll.m4 serial 9
 dnl Copyright (C) 2002, 2004, 2006, 2008-2021 Free Software Foundation, Inc.
 dnl This file is free software; the Free Software Foundation
 dnl gives unlimited permission to copy and/or distribute it,
@@ -7,8 +7,40 @@ dnl with or without modifications, as long as this notice is preserved.
 AC_DEFUN([gl_FUNC_STRTOLL],
 [
   AC_REQUIRE([gl_STDLIB_H_DEFAULTS])
+  AC_REQUIRE([AC_CANONICAL_HOST])
   AC_CHECK_FUNCS([strtoll])
-  if test $ac_cv_func_strtoll = no; then
+  if test $ac_cv_func_strtoll = yes; then
+    AC_CACHE_CHECK([whether strtoll works],
+      [gl_cv_func_strtoll_works],
+      [AC_RUN_IFELSE(
+         [AC_LANG_PROGRAM(
+            [[#include <stdlib.h>]],
+            [[int result = 0;
+              char *term;
+              /* This test fails on Minix and native Windows.  */
+              {
+                const char input[] = "0x";
+                (void) strtoll (input, &term, 16);
+                if (term != input + 1)
+                  result |= 1;
+              }
+              return result;
+            ]])
+         ],
+         [gl_cv_func_strtoll_works=yes],
+         [gl_cv_func_strtoll_works=no],
+         [case "$host_os" in
+                    # Guess no on native Windows.
+            mingw*) gl_cv_func_strtoll_works="guessing no" ;;
+            *)      gl_cv_func_strtoll_works="$gl_cross_guess_normal" ;;
+          esac
+         ])
+    ])
+    case "$gl_cv_func_strtoll_works" in
+      *yes) ;;
+      *)    REPLACE_STRTOLL=1 ;;
+    esac
+  else
     HAVE_STRTOLL=0
   fi
 ])
diff --git a/modules/stdlib b/modules/stdlib
index 33b8d50..ad04ede 100644
--- a/modules/stdlib
+++ b/modules/stdlib
@@ -142,6 +142,7 @@ stdlib.h: stdlib.in.h $(top_builddir)/config.status $(CXXDEFS_H) \
 	      -e 's|@''REPLACE_STRTOD''@|$(REPLACE_STRTOD)|g' \
 	      -e 's|@''REPLACE_STRTOL''@|$(REPLACE_STRTOL)|g' \
 	      -e 's|@''REPLACE_STRTOLD''@|$(REPLACE_STRTOLD)|g' \
+	      -e 's|@''REPLACE_STRTOLL''@|$(REPLACE_STRTOLL)|g' \
 	      -e 's|@''REPLACE_STRTOUL''@|$(REPLACE_STRTOUL)|g' \
 	      -e 's|@''REPLACE_STRTOULL''@|$(REPLACE_STRTOULL)|g' \
 	      -e 's|@''REPLACE_UNSETENV''@|$(REPLACE_UNSETENV)|g' \
diff --git a/modules/strtoll b/modules/strtoll
index 7b6d80c..da5a5a1 100644
--- a/modules/strtoll
+++ b/modules/strtoll
@@ -12,7 +12,7 @@ stdlib
 
 configure.ac:
 gl_FUNC_STRTOLL
-if test $HAVE_STRTOLL = 0; then
+if test $HAVE_STRTOLL = 0 || test $REPLACE_STRTOLL = 1; then
   AC_LIBOBJ([strtoll])
   gl_PREREQ_STRTOLL
 fi
diff --git a/tests/test-strtoll.c b/tests/test-strtoll.c
index ad43fc6..5f2b193 100644
--- a/tests/test-strtoll.c
+++ b/tests/test-strtoll.c
@@ -177,5 +177,67 @@ main (void)
       ASSERT (errno == 0);
     }
 
+  /* Hexadecimal integer syntax.  */
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    long long result;
+    errno = 0;
+    result = strtoll (input, &ptr, 10);
+    ASSERT (result == 0LL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    long long result;
+    errno = 0;
+    result = strtoll (input, &ptr, 16);
+    ASSERT (result == 42LL);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x2A";
+    char *ptr;
+    long long result;
+    errno = 0;
+    result = strtoll (input, &ptr, 0);
+    ASSERT (result == 42LL);
+    ASSERT (ptr == input + 4);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    long long result;
+    errno = 0;
+    result = strtoll (input, &ptr, 10);
+    ASSERT (result == 0LL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    long long result;
+    errno = 0;
+    result = strtoll (input, &ptr, 16);
+    ASSERT (result == 0LL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+  {
+    const char input[] = "0x";
+    char *ptr;
+    long long result;
+    errno = 0;
+    result = strtoll (input, &ptr, 0);
+    ASSERT (result == 0LL);
+    ASSERT (ptr == input + 1);
+    ASSERT (errno == 0);
+  }
+
   return 0;
 }
-- 
2.7.4


[-- Attachment #8: 0007-strtoul-strtoll-strtoull-Fix-compilation-warning.patch --]
[-- Type: text/x-patch, Size: 1558 bytes --]

From 2b038f1cc7e9a7e0a6257527a127a87753fc794c Mon Sep 17 00:00:00 2001
From: Bruno Haible <bruno@clisp.org>
Date: Fri, 2 Apr 2021 20:56:28 +0200
Subject: [PATCH 7/7] strtoul, strtoll, strtoull: Fix compilation warning.

* lib/strtol.c (strtol): Undefine before defining as a macro.
---
 ChangeLog    | 5 +++++
 lib/strtol.c | 4 ++++
 2 files changed, 9 insertions(+)

diff --git a/ChangeLog b/ChangeLog
index b479574..6224aa7 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,10 @@
 2021-04-02  Bruno Haible  <bruno@clisp.org>
 
+	strtoul, strtoll, strtoull: Fix compilation warning.
+	* lib/strtol.c (strtol): Undefine before defining as a macro.
+
+2021-04-02  Bruno Haible  <bruno@clisp.org>
+
 	strtoll: Work around a bug on native Windows and Minix.
 	* lib/stdlib.in.h (strtoll): Override if REPLACE_STRTOLL is 1.
 	* m4/stdlib_h.m4 (gl_STDLIB_H_DEFAULTS): Initialize REPLACE_STRTOLL.
diff --git a/lib/strtol.c b/lib/strtol.c
index c30e5b4..c904482 100644
--- a/lib/strtol.c
+++ b/lib/strtol.c
@@ -51,6 +51,7 @@
 
 /* Determine the name.  */
 #ifdef USE_IN_EXTENDED_LOCALE_MODEL
+# undef strtol
 # if UNSIGNED
 #  ifdef USE_WIDE_CHAR
 #   ifdef QUAD
@@ -82,6 +83,7 @@
 # endif
 #else
 # if UNSIGNED
+#  undef strtol
 #  ifdef USE_WIDE_CHAR
 #   ifdef QUAD
 #    define strtol wcstoull
@@ -97,6 +99,7 @@
 #  endif
 # else
 #  ifdef USE_WIDE_CHAR
+#   undef strtol
 #   ifdef QUAD
 #    define strtol wcstoll
 #   else
@@ -104,6 +107,7 @@
 #   endif
 #  else
 #   ifdef QUAD
+#    undef strtol
 #    define strtol strtoll
 #   endif
 #  endif
-- 
2.7.4


^ permalink raw reply related	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2021-04-02 19:00 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-03-17 13:08 mingw strtol bug Eric Blake
2021-04-02 19:00 ` Bruno Haible

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).