Better support unsigned time_t

This commit is contained in:
Werner Koch 2010-10-27 11:26:53 +00:00
parent dc5150db78
commit 2e82b095cd
8 changed files with 85 additions and 26 deletions

View File

@ -1,3 +1,9 @@
2010-10-27 Werner Koch <wk@g10code.com>
* acinclude.m4 (GNUPG_TIME_T_UNSIGNED): New.
* configure.ac (AC_HEADER_TIME): Include before checking time_t.
(GNUPG_TIME_T_UNSIGNED): Add.
2010-10-26 Werner Koch <wk@g10code.com> 2010-10-26 Werner Koch <wk@g10code.com>
Release 2.1.0beta1. Release 2.1.0beta1.

View File

@ -305,5 +305,28 @@ fi
]) ])
# GNUPG_TIME_T_UNSIGNED
# Check whether time_t is unsigned
#
AC_DEFUN([GNUPG_TIME_T_UNSIGNED],
[ AC_CACHE_CHECK(whether time_t is unsigned, gnupg_cv_time_t_unsigned,
[AC_REQUIRE([AC_HEADER_TIME])dnl
AC_COMPILE_IFELSE([AC_LANG_BOOL_COMPILE_TRY(
[AC_INCLUDES_DEFAULT([])
#if TIME_WITH_SYS_TIME
# include <sys/time.h>
# include <time.h>
#else
# if HAVE_SYS_TIME_H
# include <sys/time.h>
# else
# include <time.h>
# endif
#endif
],
[((time_t)-1) < 0])],
gnupg_cv_time_t_unsigned=no, gnupg_cv_time_t_unsigned=yes)])
if test $gnupg_cv_time_t_unsigned = yes; then
AC_DEFINE(HAVE_UNSIGNED_TIME_T,1,[Defined if time_t is an unsigned type])
fi
])# GNUPG_TIME_T_UNSIGNED

View File

@ -1,3 +1,11 @@
2010-10-27 Werner Koch <wk@g10code.com>
* gettime.c (gnupg_get_isotime): Compare to (time_t)-1.
(epoch2isotime): Ditto.
(IS_INVALID_TIME_T): New.
(asctimestamp): Use lNew macro.
(strtimestamp, isotimestamp): Ditto. Use snprintf.
2010-10-25 Werner Koch <wk@g10code.com> 2010-10-25 Werner Koch <wk@g10code.com>
* logging.c (do_log): Rename to log_log and make global. * logging.c (do_log): Rename to log_log and make global.

View File

@ -29,6 +29,14 @@
#include "i18n.h" #include "i18n.h"
#include "gettime.h" #include "gettime.h"
#ifdef HAVE_UNSIGNED_TIME_T
# define IS_INVALID_TIME_T(a) ((a) == (time_t)(-1))
#else
/* Error or 32 bit time_t and value after 2038-01-19. */
# define IS_INVALID_TIME_T(a) ((a) < 0)
#endif
static unsigned long timewarp; static unsigned long timewarp;
static enum { NORMAL = 0, FROZEN, FUTURE, PAST } timemode; static enum { NORMAL = 0, FROZEN, FUTURE, PAST } timemode;
@ -59,7 +67,7 @@ gnupg_get_isotime (gnupg_isotime_t timebuf)
{ {
time_t atime = gnupg_get_time (); time_t atime = gnupg_get_time ();
if (atime < 0) if (atime == (time_t)(-1))
*timebuf = 0; *timebuf = 0;
else else
{ {
@ -223,7 +231,7 @@ isotime2epoch (const char *string)
void void
epoch2isotime (gnupg_isotime_t timebuf, time_t atime) epoch2isotime (gnupg_isotime_t timebuf, time_t atime)
{ {
if (atime < 0) if (atime == (time_t)(-1))
*timebuf = 0; *timebuf = 0;
else else
{ {
@ -283,21 +291,23 @@ strtimevalue( u32 value )
* Note: this function returns GMT * Note: this function returns GMT
*/ */
const char * const char *
strtimestamp( u32 stamp ) strtimestamp (u32 stamp)
{ {
static char buffer[11+5]; static char buffer[11+5];
struct tm *tp; struct tm *tp;
time_t atime = stamp; time_t atime = stamp;
if (atime < 0) { if (IS_INVALID_TIME_T (atime))
strcpy (buffer, "????" "-??" "-??"); {
strcpy (buffer, "????" "-??" "-??");
} }
else { else
tp = gmtime( &atime ); {
sprintf(buffer,"%04d-%02d-%02d", tp = gmtime( &atime );
snprintf (buffer, sizeof buffer, "%04d-%02d-%02d",
1900+tp->tm_year, tp->tm_mon+1, tp->tm_mday ); 1900+tp->tm_year, tp->tm_mon+1, tp->tm_mday );
} }
return buffer; return buffer;
} }
@ -311,16 +321,16 @@ isotimestamp (u32 stamp)
struct tm *tp; struct tm *tp;
time_t atime = stamp; time_t atime = stamp;
if (atime < 0) if (IS_INVALID_TIME_T (atime))
{ {
strcpy (buffer, "????" "-??" "-??" " " "??" ":" "??" ":" "??"); strcpy (buffer, "????" "-??" "-??" " " "??" ":" "??" ":" "??");
} }
else else
{ {
tp = gmtime ( &atime ); tp = gmtime ( &atime );
sprintf (buffer,"%04d-%02d-%02d %02d:%02d:%02d", snprintf (buffer, sizeof buffer, "%04d-%02d-%02d %02d:%02d:%02d",
1900+tp->tm_year, tp->tm_mon+1, tp->tm_mday, 1900+tp->tm_year, tp->tm_mon+1, tp->tm_mday,
tp->tm_hour, tp->tm_min, tp->tm_sec); tp->tm_hour, tp->tm_min, tp->tm_sec);
} }
return buffer; return buffer;
} }
@ -339,7 +349,7 @@ asctimestamp (u32 stamp)
struct tm *tp; struct tm *tp;
time_t atime = stamp; time_t atime = stamp;
if (atime < 0) if (IS_INVALID_TIME_T (atime))
{ {
strcpy (buffer, "????" "-??" "-??"); strcpy (buffer, "????" "-??" "-??");
return buffer; return buffer;

View File

@ -1160,6 +1160,7 @@ AC_CHECK_SIZEOF(unsigned short)
AC_CHECK_SIZEOF(unsigned int) AC_CHECK_SIZEOF(unsigned int)
AC_CHECK_SIZEOF(unsigned long) AC_CHECK_SIZEOF(unsigned long)
AC_CHECK_SIZEOF(unsigned long long) AC_CHECK_SIZEOF(unsigned long long)
AC_HEADER_TIME
AC_CHECK_SIZEOF(time_t,,[[ AC_CHECK_SIZEOF(time_t,,[[
#include <stdio.h> #include <stdio.h>
#if TIME_WITH_SYS_TIME #if TIME_WITH_SYS_TIME
@ -1173,6 +1174,7 @@ AC_CHECK_SIZEOF(time_t,,[[
# endif # endif
#endif #endif
]]) ]])
GNUPG_TIME_T_UNSIGNED
# Ensure that we have UINT64_C before we bother to check for uint64_t # Ensure that we have UINT64_C before we bother to check for uint64_t

View File

@ -1,3 +1,10 @@
2010-10-27 Werner Koch <wk@g10code.com>
* keygen.c (ask_expire_interval): Do not print the y2038 if we
have an unsigned time_t.
* keyid.c (IS_INVALID_TIME_T): New.
(mk_datestr): Use it to detect the y2038 problem.
2010-10-26 Werner Koch <wk@g10code.com> 2010-10-26 Werner Koch <wk@g10code.com>
* keyedit.c (change_passphrase): Handle the passwd_nonce. * keyedit.c (change_passphrase): Handle the passwd_nonce.

View File

@ -1854,7 +1854,7 @@ ask_expire_interval(int object,const char *def_expire)
? _("Key expires at %s\n") ? _("Key expires at %s\n")
: _("Signature expires at %s\n"), : _("Signature expires at %s\n"),
asctimestamp((ulong)(curtime + interval) ) ); asctimestamp((ulong)(curtime + interval) ) );
#if SIZEOF_TIME_T <= 4 #if SIZEOF_TIME_T <= 4 && !defined (HAVE_UNSIGNED_TIME_T)
if ( (time_t)((ulong)(curtime+interval)) < 0 ) if ( (time_t)((ulong)(curtime+interval)) < 0 )
tty_printf (_("Your system can't display dates beyond 2038.\n" tty_printf (_("Your system can't display dates beyond 2038.\n"
"However, it will be correctly handled up to" "However, it will be correctly handled up to"

View File

@ -37,6 +37,13 @@
#define KEYID_STR_SIZE 19 #define KEYID_STR_SIZE 19
#ifdef HAVE_UNSIGNED_TIME_T
# define IS_INVALID_TIME_T(a) ((a) == (time_t)(-1))
#else
/* Error or 32 bit time_t and value after 2038-01-19. */
# define IS_INVALID_TIME_T(a) ((a) < 0)
#endif
/* Return a letter describing the public key algorithms. */ /* Return a letter describing the public key algorithms. */
int int
@ -446,12 +453,8 @@ mk_datestr (char *buffer, time_t atime)
{ {
struct tm *tp; struct tm *tp;
/* Note: VMS uses an unsigned time_t thus the compiler yields a if (IS_INVALID_TIME_T (atime))
warning here. You may ignore this warning or def out this test strcpy (buffer, "????" "-??" "-??"); /* Mark this as invalid. */
for VMS. The proper way to handle this would be a configure test
to a detect properly implemented unsigned time_t. */
if ( atime < 0 ) /* 32 bit time_t and after 2038-01-19 */
strcpy (buffer, "????" "-??" "-??"); /* mark this as invalid */
else else
{ {
tp = gmtime (&atime); tp = gmtime (&atime);