]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
[multiple changes]
authorArnaud Charlet <charlet@gcc.gnu.org>
Mon, 20 Apr 2009 08:26:13 +0000 (10:26 +0200)
committerArnaud Charlet <charlet@gcc.gnu.org>
Mon, 20 Apr 2009 08:26:13 +0000 (10:26 +0200)
2009-04-20  Hristian Kirtchev  <kirtchev@adacore.com>

* a-calend.adb: Remove types char_Pointer, int, tm and tm_Pointer.
(localtime_tzoff): This routine no longer accepts an actual of type
tm_Pointer.
(UTC_Time_Offset): Remove local variable Secs_TM.

* sysdep.c (__gnat_localtime_tzoff): This routine no longer accepts an
actual of type struct tm*. Add local variable of type struct tm for all
targets that provide localtime_r and need to invoke it.

2009-04-20  Thomas Quinot  <quinot@adacore.com>

* s-oscons-tmplt.c, g-socket.adb, g-socket.ads
(GNAT.Sockets.Resolve_Error): Add case of EPIPE
Add case of EAGAIN for platforms where it is not equal to EWOULDBLOCK

From-SVN: r146369

gcc/ada/ChangeLog
gcc/ada/a-calend.adb
gcc/ada/g-socket.adb
gcc/ada/g-socket.ads
gcc/ada/s-oscons-tmplt.c
gcc/ada/sysdep.c

index 1ef52e07f479f339b99d2307836aa22ca035c061..b9463f6a4d39de9fb4c0f110c9bc897a27a62d2d 100644 (file)
@@ -1,3 +1,20 @@
+2009-04-20  Hristian Kirtchev  <kirtchev@adacore.com>
+
+       * a-calend.adb: Remove types char_Pointer, int, tm and tm_Pointer.
+       (localtime_tzoff): This routine no longer accepts an actual of type
+       tm_Pointer.
+       (UTC_Time_Offset): Remove local variable Secs_TM.
+
+       * sysdep.c (__gnat_localtime_tzoff): This routine no longer accepts an
+       actual of type struct tm*. Add local variable of type struct tm for all
+       targets that provide localtime_r and need to invoke it.
+
+2009-04-20  Thomas Quinot  <quinot@adacore.com>
+
+       * s-oscons-tmplt.c, g-socket.adb, g-socket.ads
+       (GNAT.Sockets.Resolve_Error): Add case of EPIPE
+       Add case of EAGAIN for platforms where it is not equal to EWOULDBLOCK
+
 2009-04-20  Robert Dewar  <dewar@adacore.com>
 
        * sem_ch3.adb: Minor reformatting
index 7e785116f027e1b77b453a1d4291e3da36768e9b..9aa88521b90570594ff90f1a4a559a58f9555788 100644 (file)
@@ -1474,39 +1474,15 @@ package body Ada.Calendar is
 
       Nanos_In_56_Years : constant := (14 * 366 + 42 * 365) * Nanos_In_Day;
 
-      --  Base C types. There is no point dragging in Interfaces.C just for
-      --  these four types.
-
-      type char_Pointer is access Character;
-      subtype int is Integer;
       subtype long is Long_Integer;
       type long_Pointer is access all long;
 
-      --  The Ada equivalent of struct tm and type time_t
-
-      type tm is record
-         tm_sec    : int;           --  seconds after the minute (0 .. 60)
-         tm_min    : int;           --  minutes after the hour (0 .. 59)
-         tm_hour   : int;           --  hours since midnight (0 .. 24)
-         tm_mday   : int;           --  day of the month (1 .. 31)
-         tm_mon    : int;           --  months since January (0 .. 11)
-         tm_year   : int;           --  years since 1900
-         tm_wday   : int;           --  days since Sunday (0 .. 6)
-         tm_yday   : int;           --  days since January 1 (0 .. 365)
-         tm_isdst  : int;           --  Daylight Savings Time flag (-1 .. 1)
-         tm_gmtoff : long;          --  offset from UTC in seconds
-         tm_zone   : char_Pointer;  --  timezone abbreviation
-      end record;
-
-      type tm_Pointer is access all tm;
-
       subtype time_t is long;
       type time_t_Pointer is access all time_t;
 
       procedure localtime_tzoff
-       (C   : time_t_Pointer;
-        res : tm_Pointer;
-        off : long_Pointer);
+       (timer : time_t_Pointer;
+        off   : long_Pointer);
       pragma Import (C, localtime_tzoff, "__gnat_localtime_tzoff");
       --  This is a lightweight wrapper around the system library function
       --  localtime_r. Parameter 'off' captures the UTC offset which is either
@@ -1522,7 +1498,6 @@ package body Ada.Calendar is
          Date_N   : Time_Rep;
          Offset   : aliased long;
          Secs_T   : aliased time_t;
-         Secs_TM  : aliased tm;
 
       begin
          Date_N := Time_Rep (Date);
@@ -1568,7 +1543,6 @@ package body Ada.Calendar is
 
          localtime_tzoff
            (Secs_T'Unchecked_Access,
-            Secs_TM'Unchecked_Access,
             Offset'Unchecked_Access);
 
          return Offset;
index 1250607179fb3423599cf981105a47c6ef489bbf..784d0626bad5dc989f042cd2c12696f172641f06 100644 (file)
@@ -1681,6 +1681,17 @@ package body GNAT.Sockets is
          end case;
       end if;
 
+      --  Special case: EAGAIN may be the same value as EWOULDBLOCK, so we
+      --  can't include it in the case statement below.
+
+      pragma Warnings (Off);
+      --  Condition "EAGAIN /= EWOULDBLOCK" is known at compile time
+
+      if EAGAIN /= EWOULDBLOCK and then Error_Value = EAGAIN then
+         return Resource_Temporarily_Unavailable;
+      end if;
+      pragma Warnings (On);
+
       case Error_Value is
          when ENOERROR        => return Success;
          when EACCES          => return Permission_Denied;
@@ -1716,6 +1727,7 @@ package body GNAT.Sockets is
          when ENOTSOCK        => return Socket_Operation_On_Non_Socket;
          when EOPNOTSUPP      => return Operation_Not_Supported;
          when EPFNOSUPPORT    => return Protocol_Family_Not_Supported;
+         when EPIPE           => return Broken_Pipe;
          when EPROTONOSUPPORT => return Protocol_Not_Supported;
          when EPROTOTYPE      => return Protocol_Wrong_Type_For_Socket;
          when ESHUTDOWN       => return
@@ -1724,10 +1736,9 @@ package body GNAT.Sockets is
          when ETIMEDOUT       => return Connection_Timed_Out;
          when ETOOMANYREFS    => return Too_Many_References;
          when EWOULDBLOCK     => return Resource_Temporarily_Unavailable;
-         when others          => null;
-      end case;
 
-      return Cannot_Resolve_Error;
+         when others          => return Cannot_Resolve_Error;
+      end case;
    end Resolve_Error;
 
    -----------------------
index 439655f5371ffba289e343da6af93828bc13f979..f8dd6bfecfca6ce69e9e409f86729d98aaf36fff 100644 (file)
@@ -603,6 +603,9 @@ package GNAT.Sockets is
    --  brackets and a string describing the error code.
 
    --  The name of the enumeration constant documents the error condition
+   --  Note that on some platforms, a single error value is used for both
+   --  EWOULDBLOCK and EAGAIN. Both errors are therefore always reported as
+   --  Resource_Temporarily_Unavailable.
 
    type Error_Type is
      (Success,
@@ -644,6 +647,7 @@ package GNAT.Sockets is
       Connection_Timed_Out,
       Too_Many_References,
       Resource_Temporarily_Unavailable,
+      Broken_Pipe,
       Unknown_Host,
       Host_Name_Lookup_Failure,
       Non_Recoverable_Error,
index 958b11e938b93c14d42f6185b5d15e157edbf8a8..e6e1849154292e2bafa6e190ff17bcb07be8b9fa 100644 (file)
@@ -451,6 +451,11 @@ CND(ENOTSOCK, "Operation on non socket")
 #endif
 CND(EOPNOTSUPP, "Operation not supported")
 
+#ifndef EPIPE
+# define EPIPE -1
+#endif
+CND(EPIPE, "Broken pipe")
+
 #ifndef EPFNOSUPPORT
 # define EPFNOSUPPORT -1
 #endif
index 56f3ebd3b0f519eb3a9120cc58265cbb9a1c171f..8a227b42037d9d98699780b388ad6d3883943fde 100644 (file)
@@ -743,26 +743,53 @@ extern void (*Unlock_Task) (void);
 
 /* Reentrant localtime for Windows and OS/2. */
 
-extern struct tm *
-__gnat_localtime_tzoff (const time_t *, struct tm *, long *);
+extern void
+__gnat_localtime_tzoff (const time_t *, long *);
 
-struct tm *
-__gnat_localtime_tzoff (const time_t *timer, struct tm *tp, long *off)
+static const unsigned long long w32_epoch_offset = 11644473600ULL;
+void
+__gnat_localtime_tzoff (const time_t *timer, long *off)
 {
-  DWORD dwRet;
-  struct tm *tmp;
+  union
+  {
+    FILETIME ft_time;
+    unsigned long long ull_time;
+  } utc_time, local_time;
+
+  SYSTEMTIME utc_sys_time, local_sys_time;
   TIME_ZONE_INFORMATION tzi;
 
+  BOOL  status = 1;
+  DWORD tzi_status;
+
   (*Lock_Task) ();
-  tmp = localtime (timer);
-  memcpy (tp, tmp, sizeof (struct tm));
-  dwRet = GetTimeZoneInformation (&tzi);
-  *off = tzi.Bias;
-  if (tp->tm_isdst > 0)
-    *off = *off + tzi.DaylightBias;
-  *off = *off * -60;
+
+  /* First convert unix time_t structure to windows FILETIME format.  */
+  utc_time.ull_time = ((unsigned long long) *timer + w32_epoch_offset)
+                      * 10000000ULL;
+
+  tzi_status = GetTimeZoneInformation (&tzi);
+
+  /* If GetTimeZoneInformation does not return a value between 0 and 2 then
+     it means that we were not able to retrieve timezone informations.
+     Note that we cannot use here FileTimeToLocalFileTime as Windows will use
+     in always in this case the current timezone setting. As suggested on
+     MSDN we use the following three system calls to get the right information.
+     Note also that starting with Windows Vista new functions are provided to
+     get timezone settings that depend on the year. We cannot use them as we
+     still support Windows XP and Windows 2003.  */
+  status = (tzi_status >= 0 && tzi_status <= 2)
+     && FileTimeToSystemTime (&utc_time.ft_time, &utc_sys_time)
+     && SystemTimeToTzSpecificLocalTime (&tzi, &utc_sys_time, &local_sys_time)
+     && SystemTimeToFileTime (&local_sys_time, &local_time.ft_time);
+
+  if (!status)
+     /* An error occurs so return invalid_tzoff.  */
+     *off = __gnat_invalid_tzoff;
+  else
+     *off = (long) ((local_time.ull_time - utc_time.ull_time) / 10000000ULL);
+
   (*Unlock_Task) ();
-  return tp;
 }
 
 #else
@@ -774,16 +801,14 @@ __gnat_localtime_tzoff (const time_t *timer, struct tm *tp, long *off)
    spec is required. Only use when ___THREADS_POSIX4ad4__ is defined,
    the Lynx convention when building against the legacy API. */
 
-extern struct tm *
-__gnat_localtime_tzoff (const time_t *, struct tm *, long *);
+extern void
+__gnat_localtime_tzoff (const time_t *, long *);
 
-struct tm *
-__gnat_localtime_tzoff (const time_t *timer, struct tm *tp, long *off)
+void
+__gnat_localtime_tzoff (const time_t *timer, long *off)
 {
   /* Treat all time values in GMT */
-  localtime_r (tp, timer);
   *off = 0;
-  return NULL;
 }
 
 #else
@@ -795,28 +820,21 @@ __gnat_localtime_tzoff (const time_t *timer, struct tm *tp, long *off)
 
 /* All other targets provide a standard localtime_r */
 
-extern struct tm *
-__gnat_localtime_tzoff (const time_t *, struct tm *, long *);
+extern void
+__gnat_localtime_tzoff (const time_t *, long *);
 
-struct tm *
-__gnat_localtime_tzoff (const time_t *timer, struct tm *tp, long *off)
+void
+__gnat_localtime_tzoff (const time_t *timer, long *off)
 {
-   localtime_r (timer, tp);
+   struct tm tp;
+   localtime_r (timer, &tp);
 
 /* AIX, HPUX, SGI Irix, Sun Solaris */
 #if defined (_AIX) || defined (__hpux__) || defined (sgi) || defined (sun)
-  /* The contents of external variable "timezone" may not always be
-     initialized. Instead of returning an incorrect offset, treat the local
-     time zone as 0 (UTC). The value of 28 hours is the maximum valid offset
-     allowed by Ada.Calendar.Time_Zones. */
-  if ((timezone < -28 * 3600) || (timezone > 28 * 3600))
-    *off = 0;
-  else
-  {
-    *off = (long) -timezone;
-    if (tp->tm_isdst > 0)
-      *off = *off + 3600;
-   }
+   *off = (long) -timezone;
+   if (tp.tm_isdst > 0)
+     *off = *off + 3600;
+
 /* Lynx - Treat all time values in GMT */
 #elif defined (__Lynx__)
   *off = 0;
@@ -850,17 +868,16 @@ __gnat_localtime_tzoff (const time_t *timer, struct tm *tp, long *off)
   }
 }
 
-/* Darwin, Free BSD, Linux, Tru64, where there exists a component tm_gmtoff
-   in struct tm */
+/* Darwin, Free BSD, Linux, Tru64, where component tm_gmtoff is present in
+   struct tm */
 #elif defined (__APPLE__) || defined (__FreeBSD__) || defined (linux) ||\
      (defined (__alpha__) && defined (__osf__)) || defined (__GLIBC__)
-  *off = tp->tm_gmtoff;
+  *off = tp.tm_gmtoff;
 
 /* All other platforms: Treat all time values in GMT */
 #else
   *off = 0;
 #endif
-   return NULL;
 }
 
 #endif