Skip site navigation (1)Skip section navigation (2)
Date:      Mon, 25 Nov 2002 18:26:15 -0800 (PST)
From:      Peter Wemm <peter@FreeBSD.org>
To:        Perforce Change Reviews <perforce@freebsd.org>
Subject:   PERFORCE change 21511 for review
Message-ID:  <200211260226.gAQ2QFZv033407@repoman.freebsd.org>

next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=21511

Change 21511 by peter@peter_ia64 on 2002/11/25 18:25:51

	Fix some integer overflows.  This makes localtime and mktime
	work happily for time_t's up to about the year 2^31.  Unfortunately,
	bash2's configure script tries to do a localtime/mktime on a time_t
	of about 2^63, which is in the year (roughly) 292 billion, which
	will not fit in 'int tm_year' (as specified by the standard).  With
	these fixes, we're good up until about the year 2.4billion or so.
	
	This is the cause of the original mktime cpu loop, and the cause of
	why the bash2 configure script spins.  Note that the bash2 script
	actually times out after 60 seconds and kills itself and declares
	mktime(3) to be broken.
	
	Also note that mktime(3) fails the same tests on i386 and all the
	other platforms.  This is because it fails the so-called "spring
	foward" test when mktime() fails when asked for a time in some
	window.
	
	/* Fail if mktime fails to convert a date in the spring-forward gap.
	   Based on a problem report from Andreas Jaeger.  */
	static void
	spring_forward_gap ()
	{
	  /* glibc (up to about 1998-10-07) failed this test. */
	  struct tm tm;
	
	  /* Use the portable POSIX.1 specification "TZ=PST8PDT,M4.1.0,M10.5.0"
	     instead of "TZ=America/Vancouver" in order to detect the bug even
	     on systems that don't support the Olson extension, or don't have the
	     full zoneinfo tables installed.  */
	  putenv ("TZ=PST8PDT,M4.1.0,M10.5.0");   
	
	  tm.tm_year = 98;
	  tm.tm_mon = 3;
	  tm.tm_mday = 5;
	  tm.tm_hour = 2;
	  tm.tm_min = 0;
	  tm.tm_sec = 0;
	  tm.tm_isdst = -1;
	  if (mktime (&tm) == (time_t)-1) {
	    printf("fail spring forward\n");
	    exit (1);
	  }
	}
	As I said, this fails on x86 as well.  So we dont need to worry about
	failures on ia64 when the tester tries to generate unrepresentable (in
	struct tm) time_t's 292 billion years into the future.

Affected files ...

.. //depot/projects/ia64/lib/libc/stdtime/localtime.c#7 edit

Differences ...

==== //depot/projects/ia64/lib/libc/stdtime/localtime.c#7 (text+ko) ====

@@ -149,7 +149,7 @@
 				long offset, int * okayp);
 static void		timesub(const time_t * timep, long offset,
 				const struct state * sp, struct tm * tmp);
-static int		tmcomp(const struct tm * atmp,
+static long		tmcomp(const struct tm * atmp,
 				const struct tm * btmp);
 static time_t		transtime(time_t janfirst, int year,
 				const struct rule * rulep, long offset);
@@ -1222,7 +1222,7 @@
 	const struct lsinfo *	lp;
 	long			days;
 	long			rem;
-	int			y;
+	long			y;
 	int			yleap;
 	const int *		ip;
 	long			corr;
@@ -1291,7 +1291,7 @@
 	y = EPOCH_YEAR;
 #define LEAPS_THRU_END_OF(y)	((y) / 4 - (y) / 100 + (y) / 400)
 	while (days < 0 || days >= (long) year_lengths[yleap = isleap(y)]) {
-		int	newy;
+		long	newy;
 
 		newy = y + days / DAYSPERNYEAR;
 		if (days < 0)
@@ -1380,12 +1380,12 @@
 	return increment_overflow(tensptr, tensdelta);
 }
 
-static int
+static long
 tmcomp(atmp, btmp)
 const struct tm * const atmp;
 const struct tm * const btmp;
 {
-	int	result;
+	long	result;
 
 	if ((result = (atmp->tm_year - btmp->tm_year)) == 0 &&
 		(result = (atmp->tm_mon - btmp->tm_mon)) == 0 &&
@@ -1404,7 +1404,7 @@
 int * const		okayp;
 {
 	const struct state *	sp;
-	int			dir;
+	long			dir;
 	int			bits;
 	int			i, j ;
 	int			saved_seconds;

To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe p4-projects" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200211260226.gAQ2QFZv033407>