autoconf-patches
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH 2/2] AC_SYS_LARGEFILE now widens time_t if possible


From: Paul Eggert
Subject: [PATCH 2/2] AC_SYS_LARGEFILE now widens time_t if possible
Date: Tue, 9 Aug 2022 11:07:26 -0700

This change is taken from Gnulib, and is needed for apps like GDB.
* lib/autoconf/specific.m4 (_AC_SYS_YEAR2038_TEST_INCLUDES)
(_AC_SYS_YEAR2038, AC_SYS_YEAR2038): New macros, taken (with
renaming) from Gnulib.
(_AC_SYS_LARGEFILE_MACRO_VALUE): #undef before #define.
(AC_SYS_LARGEFILE): Prefer AS_IF and AS_CASE to doing it by hand.
Widen time_t if possible, too.  Define  __MINGW_USE_VC2005_COMPAT
early if needed.
---
 NEWS                     |   6 ++
 doc/autoconf.texi        |  33 +++++++++-
 lib/autoconf/specific.m4 | 134 +++++++++++++++++++++++++++++++++++----
 3 files changed, 159 insertions(+), 14 deletions(-)

diff --git a/NEWS b/NEWS
index ef0f5f83..204f95f1 100644
--- a/NEWS
+++ b/NEWS
@@ -21,7 +21,13 @@ GNU Autoconf NEWS - User visible changes.
   that you will get a confusing error message if you run autoconf on
   a configure.ac that neglects to use AC_INIT or AC_OUTPUT.
 
+*** AC_SYS_LARGEFILE now arranges for 64-bit time_t if possible.
+
+
 ** New features
+
+*** New macro AC_YEAR2038 for 64-bit time_t.
+
 ** Obsolete features and new warnings
 
 *** Autoconf now quotes 'like this' instead of `like this'.
diff --git a/doc/autoconf.texi b/doc/autoconf.texi
index fa5a9f48..209840c2 100644
--- a/doc/autoconf.texi
+++ b/doc/autoconf.texi
@@ -8869,6 +8869,7 @@ if the system supports @samp{#!}, @samp{no} if not.
 @acindex{SYS_LARGEFILE}
 @cvindex _FILE_OFFSET_BITS
 @cvindex _LARGE_FILES
+@cvindex _TIME_BITS
 @ovindex CC
 @cindex Large file support
 @cindex LFS
@@ -8877,13 +8878,15 @@ Arrange for 64-bit file offsets, known as
 large-file support}.  On some hosts, one must use special compiler
 options to build programs that can access large files.  Append any such
 options to the output variable @code{CC}.  Define
-@code{_FILE_OFFSET_BITS} and @code{_LARGE_FILES} if necessary.
+@code{_FILE_OFFSET_BITS}, @code{_LARGE_FILES}, and @code{_TIME_BITS}
+if necessary.
 
 Large-file support can be disabled by configuring with the
 @option{--disable-largefile} option.
 
-If you use this macro, check that your program works even when
-@code{off_t} is wider than @code{long int}, since this is common when
+If you use this macro, check that your program works even when the types
+@code{blkcnt_t}, @code{dev_t}, @code{ino_t}, @code{off_t}, and @code{time_t}
+are wider than @code{long int}, since this is common when
 large-file support is enabled.  For example, it is not correct to print
 an arbitrary @code{off_t} value @code{X} with @code{printf ("%ld",
 (long int) X)}.  Also, when using this macro in concert with
@@ -8915,6 +8918,30 @@ system.  If so, set the shell variable 
@code{ac_cv_sys_posix_termios} to
 @samp{yes}.  If not, set the variable to @samp{no}.
 @end defmac
 
+@defmac AC_SYS_YEAR2038
+@acindex{SYS_YEAR2038}
+@cvindex _TIME_BITS
+@ovindex CC
+@cindex Year 2038
+If the default @code{time_t} type is a signed 32-bit integer that stops
+working in the year 2038, then arrange to use a wider @code{time_t} if
+possible and report a fatal error otherwise.  Define @code{_TIME_BITS}
+if necessary.
+
+Wider-time support can be disabled by configuring with the
+@option{--disable-year2038} option.
+
+Regardless of whether you use this macro, portable programs should not
+assume that @code{time_t} fits into @code{long int}.  For example, it is
+not correct to print an arbitrary @code{time_t} value @code{X} with
+@code{printf ("%ld", (long int) X)}.  Also, when using this macro in
+concert with @code{AC_CONFIG_HEADERS}, be sure that @file{config.h} is
+included before any system header.
+
+Although @code{AC_SYS_LARGFILE} also widens @code{time_t} if possible,
+it merely warns if this cannot be done, rather than reporting a fatal error.
+@end defmac
+
 @node C and Posix Variants
 @section C and Posix Variants
 
diff --git a/lib/autoconf/specific.m4 b/lib/autoconf/specific.m4
index 757d678b..0af41176 100644
--- a/lib/autoconf/specific.m4
+++ b/lib/autoconf/specific.m4
@@ -85,6 +85,112 @@ AU_DEFUN([AC_ARG_ARRAY], [],
 with arguments. Remove this warning when you adjust your code.])
 
 
+# _AC_SYS_YEAR2038_TEST_INCLUDES
+# ------------------------------
+AC_DEFUN([_AC_SYS_YEAR2038_TEST_INCLUDES],
+[[
+  #include <time.h>
+  /* Check that time_t can represent 2**32 - 1 correctly.  */
+  #define LARGE_TIME_T \\
+    ((time_t) (((time_t) 1 << 30) - 1 + 3 * ((time_t) 1 << 30)))
+  int verify_time_t_range[(LARGE_TIME_T / 65537 == 65535
+                           && LARGE_TIME_T % 65537 == 0)
+                          ? 1 : -1];
+]])
+
+# _AC_SYS_YEAR2038(REQUIRE-YEAR2038-SAFE)
+# ---------------------------------------
+AC_DEFUN([_AC_SYS_YEAR2038],
+[
+ AC_ARG_ENABLE([year2038],
+   [  --disable-year2038      omit support for timestamps past the year 2038])
+ AS_IF([test "$enable_year2038" != no],
+ [
+  dnl On many systems, time_t is already a 64-bit type.
+  dnl On those systems where time_t is still 32-bit, it requires kernel
+  dnl and libc support to make it 64-bit. For glibc 2.34 and later on Linux,
+  dnl defining _TIME_BITS=64 and _FILE_OFFSET_BITS=64 is needed on x86 and ARM.
+  dnl
+  dnl On native Windows, the system include files define types __time32_t
+  dnl and __time64_t. By default, time_t is an alias of
+  dnl   - __time32_t on 32-bit mingw,
+  dnl   - __time64_t on 64-bit mingw and on MSVC (since MSVC 8).
+  dnl But when compiling with -D__MINGW_USE_VC2005_COMPAT, time_t is an
+  dnl alias of __time64_t.
+  dnl And when compiling with -D_USE_32BIT_TIME_T, time_t is an alias of
+  dnl __time32_t.
+  AC_CACHE_CHECK([for time_t past the year 2038], [ac_cv_type_time_t_y2038],
+    [AC_COMPILE_IFELSE(
+       [AC_LANG_SOURCE([_AC_SYS_YEAR2038_TEST_INCLUDES])],
+       [ac_cv_type_time_t_y2038=yes], [ac_cv_type_time_t_y2038=no])
+    ])
+  if test "$ac_cv_type_time_t_y2038" = no; then
+    AC_CACHE_CHECK([for 64-bit time_t with _TIME_BITS=64],
+      [ac_cv_type_time_t_bits_macro],
+      [AC_COMPILE_IFELSE(
+         [AC_LANG_SOURCE([[#define _TIME_BITS 64
+                           #define _FILE_OFFSET_BITS 64
+                           ]_AC_SYS_YEAR2038_TEST_INCLUDES])],
+         [ac_cv_type_time_t_bits_macro=yes],
+         [ac_cv_type_time_t_bits_macro=no])
+      ])
+    if test "$ac_cv_type_time_t_bits_macro" = yes; then
+      AC_DEFINE([_TIME_BITS], [64],
+        [Number of bits in a timestamp, on hosts where this is settable.])
+      dnl AC_SYS_LARGFILE also defines this; it's OK if we do too.
+      AC_DEFINE([_FILE_OFFSET_BITS], [64],
+        [Number of bits in a file offset, on hosts where this is settable.])
+      ac_cv_type_time_t_y2038=yes
+    fi
+  fi
+  if test $ac_cv_type_time_t_y2038 = no; then
+    AC_COMPILE_IFELSE(
+      [AC_LANG_SOURCE(
+         [[#ifdef _USE_32BIT_TIME_T
+             int ok;
+           #else
+             error fail
+           #endif
+         ]])],
+      [AC_MSG_FAILURE(
+         [The 'time_t' type stops working after January 2038.
+          Remove _USE_32BIT_TIME_T from the compiler flags.])],
+      [# If not cross-compiling and $1 says we should check,
+       # and 'touch' works with a large timestamp, then evidently wider time_t
+       # is desired and supported, so fail and ask the builder to fix the
+       # problem.  Otherwise, just warn the builder.
+       m4_ifval([$1],
+         [if test $cross_compiling = no \
+             && TZ=UTC0 touch -t 210602070628.15 conftest.time 2>/dev/null; 
then
+            case `TZ=UTC0 LC_ALL=C ls -l conftest.time 2>/dev/null` in
+              *'Feb  7  2106'* | *'Feb  7 17:10'*)
+                AC_MSG_FAILURE(
+                  [The 'time_t' type stops working after January 2038,
+                   and your system appears to support a wider 'time_t'.
+                   Try configuring with 'CC="${CC} -m64"'.
+                   To build with a 32-bit time_t anyway (not recommended),
+                   configure with '--disable-year2038'.]);;
+            esac
+            rm -f conftest.time
+          fi])
+       if test "$ac_warned_about_y2038" != yes; then
+         AC_MSG_WARN(
+           [The 'time_t' type stops working after January 2038,
+            and this package needs a wider 'time_t' type
+            if there is any way to access timestamps after that.
+            Configure with 'CC="${CC} -m64"' perhaps?])
+         ac_warned_about_y2038=yes
+       fi
+      ])
+  fi])
+])
+
+AC_DEFUN([AC_SYS_YEAR2038],
+[
+  _$0([require-year2038-safe])
+])
+
+
 # _AC_SYS_LARGEFILE_TEST_INCLUDES
 # -------------------------------
 m4_define([_AC_SYS_LARGEFILE_TEST_INCLUDES],
@@ -112,7 +218,8 @@ m4_define([_AC_SYS_LARGEFILE_MACRO_VALUE],
     [AC_LANG_PROGRAM([$5], [$6])],
     [$3=no; break])
   m4_ifval([$6], [AC_LINK_IFELSE], [AC_COMPILE_IFELSE])(
-    [AC_LANG_PROGRAM([@%:@define $1 $2
+    [AC_LANG_PROGRAM([#undef $1
+#define $1 $2
 $5], [$6])],
     [$3=$2; break])
   $3=unknown
@@ -138,9 +245,8 @@ rm -rf conftest*[]dnl
 AC_DEFUN([AC_SYS_LARGEFILE],
 [AC_ARG_ENABLE(largefile,
               [  --disable-largefile     omit support for large files])
-if test "$enable_largefile" != no; then
-
-  AC_CACHE_CHECK([for special C compiler options needed for large files],
+AS_IF([test "$enable_largefile" != no],
+ [AC_CACHE_CHECK([for special C compiler options needed for large files],
     ac_cv_sys_largefile_CC,
     [ac_cv_sys_largefile_CC=no
      if test "$GCC" != yes; then
@@ -165,13 +271,19 @@ if test "$enable_largefile" != no; then
     ac_cv_sys_file_offset_bits,
     [Number of bits in a file offset, on hosts where this is settable.],
     [_AC_SYS_LARGEFILE_TEST_INCLUDES])
-  if test $ac_cv_sys_file_offset_bits = unknown; then
-    _AC_SYS_LARGEFILE_MACRO_VALUE(_LARGE_FILES, 1,
-      ac_cv_sys_large_files,
-      [Define for large files, on AIX-style hosts.],
-      [_AC_SYS_LARGEFILE_TEST_INCLUDES])
-  fi
-fi
+  AS_CASE([$ac_cv_sys_file_offset_bits],
+    [unknown],
+      [_AC_SYS_LARGEFILE_MACRO_VALUE([_LARGE_FILES], [1],
+         [ac_cv_sys_large_files],
+         [Define for large files, on AIX-style hosts.],
+         [_AC_SYS_LARGEFILE_TEST_INCLUDES])],
+    [64],
+      [_AC_SYS_YEAR2038()])])
+
+  AH_VERBATIM([__MINGW_USE_VC2005_COMPAT],
+[#if !defined __MINGW_USE_VC2005_COMPAT && defined __MINGW32__
+# define __MINGW_USE_VC2005_COMPAT 1 /* For 64-bit time_t.  */
+#endif])
 ])# AC_SYS_LARGEFILE
 
 
-- 
2.37.1




reply via email to

[Prev in Thread] Current Thread [Next in Thread]