public inbox for glibc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug libc/541] New: mktime portability fix for gnulib on Crays
@ 2004-11-10 23:42 eggert@gnu.org
  2004-11-11  0:28 ` [Bug libc/541] " cvs-commit@gcc.gnu.org
  2004-11-11  0:29 ` roland@gnu.org
  0 siblings, 2 replies; 3+ messages in thread
From: eggert@gnu.org @ 2004-11-10 23:42 UTC (permalink / raw)
  To: glibc-bugs

Can you please install this mktime patch?  It is a portability fix to
mktime, needed for gnulib.  It does not affect the generated code in
glibc targets; it affects only code generated for gnulib-using applications
that are running on weird hosts like the Cray.  Thanks.


2004-11-10  Paul Eggert  <eggert@cs.ucla.edu>

	* time/mktime.c (SHR): New macro, which is a portable
	substitute for >> that should work even on Crays.
	(TIME_T_MIDPOINT, ydhms_diff, __mktime_internal): Use it.
	Problem reported by Mark D. Baushke in
	< http://lists.gnu.org/archive/html/bug-gnulib/2004-11/msg00071.html >.

--- time/mktime.c	2004-11-02 10:55:42 -0800
+++ /home/eggert/junk/mktime.c	2004-11-10 15:27:39 -0800
@@ -46,6 +46,21 @@
 # define mktime my_mktime
 #endif /* DEBUG */
 
+/* Shift A right by B bits portably, by dividing A by 2**B and
+   truncating towards minus infinity.  A and B should be free of side
+   effects, and B should be in the range 0 <= B <= INT_BITS - 2, where
+   INT_BITS is the number of useful bits in an int.  GNU code can
+   assume that INT_BITS is at least 32.
+
+   ISO C99 says that A >> B is implementation-defined if A < 0.  Some
+   implementations (e.g., UNICOS 9.0 on a Cray Y-MP EL) don't shift
+   right in the usual way when A < 0, so SHR falls back on division if
+   ordinary A >> B doesn't seem to be the usual signed shift.  */
+#define SHR(a, b)	\
+  (-1 >> 1 == -1	\
+   ? (a) >> (b)		\
+   : (a) / (1 << (b)) - ((a) % (1 << (b)) < 0))
+
 /* The extra casts work around common compiler bugs.  */
 #define TYPE_SIGNED(t) (! ((t) 0 < (t) -1))
 /* The outer cast is needed to work around a bug in Cray C 5.0.3.0.
@@ -60,14 +75,13 @@
 #ifndef TIME_T_MAX
 # define TIME_T_MAX TYPE_MAXIMUM (time_t)
 #endif
-#define TIME_T_MIDPOINT (((TIME_T_MIN + TIME_T_MAX) >> 1) + 1)
+#define TIME_T_MIDPOINT (SHR (TIME_T_MIN + TIME_T_MAX, 1) + 1)
 
 /* Verify a requirement at compile-time (unlike assert, which is runtime).  */
 #define verify(name, assertion) struct name { char a[(assertion) ? 1 : -1]; }
 
 verify (time_t_is_integer, (time_t) 0.5 == 0);
 verify (twos_complement_arithmetic, -1 == ~1 + 1);
-verify (right_shift_propagates_sign, -1 >> 1 == -1);
 /* The code also assumes that signed integer overflow silently wraps
    around, but this assumption can't be stated without causing a
    diagnostic on some hosts.  */
@@ -133,12 +147,12 @@ ydhms_diff (long int year1, long int yda
 
   /* Compute intervening leap days correctly even if year is negative.
      Take care to avoid integer overflow here.  */
-  int a4 = (year1 >> 2) + (TM_YEAR_BASE >> 2) - ! (year1 & 3);
-  int b4 = (year0 >> 2) + (TM_YEAR_BASE >> 2) - ! (year0 & 3);
+  int a4 = SHR (year1, 2) + SHR (TM_YEAR_BASE, 2) - ! (year1 & 3);
+  int b4 = SHR (year0, 2) + SHR (TM_YEAR_BASE, 2) - ! (year0 & 3);
   int a100 = a4 / 25 - (a4 % 25 < 0);
   int b100 = b4 / 25 - (b4 % 25 < 0);
-  int a400 = a100 >> 2;
-  int b400 = b100 >> 2;
+  int a400 = SHR (a100, 2);
+  int b400 = SHR (b100, 2);
   int intervening_leap_days = (a4 - b4) - (a100 - b100) + (a400 - b400);
 
   /* Compute the desired time in time_t precision.  Overflow might
@@ -322,14 +336,16 @@ __mktime_internal (struct tm *tp,
       int LOG2_YEARS_PER_BIENNIUM = 1;
 
       int approx_requested_biennia =
-	((year_requested >> LOG2_YEARS_PER_BIENNIUM)
-	 - ((EPOCH_YEAR - TM_YEAR_BASE) >> LOG2_YEARS_PER_BIENNIUM)
-	 + (mday >> ALOG2_DAYS_PER_BIENNIUM)
-	 + (hour >> ALOG2_HOURS_PER_BIENNIUM)
-	 + (min >> ALOG2_MINUTES_PER_BIENNIUM)
-	 + (LEAP_SECONDS_POSSIBLE ? 0 : sec >> ALOG2_SECONDS_PER_BIENNIUM));
+	(SHR (year_requested, LOG2_YEARS_PER_BIENNIUM)
+	 - SHR (EPOCH_YEAR - TM_YEAR_BASE, LOG2_YEARS_PER_BIENNIUM)
+	 + SHR (mday, ALOG2_DAYS_PER_BIENNIUM)
+	 + SHR (hour, ALOG2_HOURS_PER_BIENNIUM)
+	 + SHR (min, ALOG2_MINUTES_PER_BIENNIUM)
+	 + (LEAP_SECONDS_POSSIBLE
+	    ? 0
+	    : SHR (sec, ALOG2_SECONDS_PER_BIENNIUM)));
 
-      int approx_biennia = t0 >> ALOG2_SECONDS_PER_BIENNIUM;
+      int approx_biennia = SHR (t0, ALOG2_SECONDS_PER_BIENNIUM);
       int diff = approx_biennia - approx_requested_biennia;
       int abs_diff = diff < 0 ? - diff : diff;
 
@@ -347,7 +363,7 @@ __mktime_internal (struct tm *tp,
 	  /* Overflow occurred.  Try repairing it; this might work if
 	     the time zone offset is enough to undo the overflow.  */
 	  time_t repaired_t0 = -1 - t0;
-	  approx_biennia = repaired_t0 >> ALOG2_SECONDS_PER_BIENNIUM;
+	  approx_biennia = SHR (repaired_t0, ALOG2_SECONDS_PER_BIENNIUM);
 	  diff = approx_biennia - approx_requested_biennia;
 	  abs_diff = diff < 0 ? - diff : diff;
 	  if (overflow_threshold < abs_diff)

-- 
           Summary: mktime portability fix for gnulib on Crays
           Product: glibc
           Version: 2.3.3
            Status: NEW
          Severity: normal
          Priority: P2
         Component: libc
        AssignedTo: gotom at debian dot or dot jp
        ReportedBy: eggert at gnu dot org
                CC: glibc-bugs at sources dot redhat dot com


http://sources.redhat.com/bugzilla/show_bug.cgi?id=541

------- You are receiving this mail because: -------
You are on the CC list for the bug, or are watching someone who is.


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

* [Bug libc/541] mktime portability fix for gnulib on Crays
  2004-11-10 23:42 [Bug libc/541] New: mktime portability fix for gnulib on Crays eggert@gnu.org
@ 2004-11-11  0:28 ` cvs-commit@gcc.gnu.org
  2004-11-11  0:29 ` roland@gnu.org
  1 sibling, 0 replies; 3+ messages in thread
From: cvs-commit@gcc.gnu.org @ 2004-11-11  0:28 UTC (permalink / raw)
  To: glibc-bugs

------- Additional Comments From cvs-commit at gcc dot gnu dot org  2004-11-11 00:28 -------
Subject: Bug 541

CVSROOT:	/cvs/glibc
Module name:	libc
Changes by:	roland@sources.redhat.com	2004-11-11 00:28:18

Modified files:
	time           : mktime.c 

Log message:
	2004-11-10  Paul Eggert  <eggert@cs.ucla.edu>
	
	[BZ #541]
	* time/mktime.c (SHR): New macro, which is a portable
	substitute for >> that should work even on Crays.
	(TIME_T_MIDPOINT, ydhms_diff, __mktime_internal): Use it.
	Problem reported by Mark D. Baushke in
	< http://lists.gnu.org/archive/html/bug-gnulib/2004-11/msg00071.html >.

Patches:
http://sources.redhat.com/cgi-bin/cvsweb.cgi/libc/time/mktime.c.diff?cvsroot=glibc&r1=1.61&r2=1.62



-- 


http://sources.redhat.com/bugzilla/show_bug.cgi?id=541

------- You are receiving this mail because: -------
You are on the CC list for the bug, or are watching someone who is.


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

* [Bug libc/541] mktime portability fix for gnulib on Crays
  2004-11-10 23:42 [Bug libc/541] New: mktime portability fix for gnulib on Crays eggert@gnu.org
  2004-11-11  0:28 ` [Bug libc/541] " cvs-commit@gcc.gnu.org
@ 2004-11-11  0:29 ` roland@gnu.org
  1 sibling, 0 replies; 3+ messages in thread
From: roland@gnu.org @ 2004-11-11  0:29 UTC (permalink / raw)
  To: glibc-bugs

------- Additional Comments From roland at gnu dot org  2004-11-11 00:29 -------
It's in.

-- 
           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|NEW                         |RESOLVED
         Resolution|                            |FIXED


http://sources.redhat.com/bugzilla/show_bug.cgi?id=541

------- You are receiving this mail because: -------
You are on the CC list for the bug, or are watching someone who is.


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

end of thread, other threads:[~2004-11-11  0:29 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2004-11-10 23:42 [Bug libc/541] New: mktime portability fix for gnulib on Crays eggert@gnu.org
2004-11-11  0:28 ` [Bug libc/541] " cvs-commit@gcc.gnu.org
2004-11-11  0:29 ` roland@gnu.org

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).