aboutsummaryrefslogtreecommitdiff
path: root/sysdeps/unix
diff options
context:
space:
mode:
authorZack Weinberg <zackw@panix.com>2019-07-27 19:26:23 -0400
committerZack Weinberg <zackw@panix.com>2019-07-27 20:14:35 -0400
commit3f649995a112b91754b49b7fff389385ce55f54f (patch)
tree3999bdce24cbfc67c223f3610ba6dd92d59d0994 /sysdeps/unix
parent50ce3eae5ba304650459d4441d7d246a7cefc26f (diff)
downloadglibc-zack/gtod-no-timezone.zip
glibc-zack/gtod-no-timezone.tar.gz
glibc-zack/gtod-no-timezone.tar.bz2
Remove access to legacy time zone support in gettimeofday etc.zack/gtod-no-timezone
gettimeofday and ftime are not quite fully implementable on systems that only provide a primitive equivalent to clock_gettime, because they can also report information about a system-wide time zone. This mechanism has been deprecated for many years because it can only be configured on a system-wide basis, and because it only supports the simplest kinds of daylight-savings rules, but we’ve supported it on a best-effort basis until now. This patch removes our support for it: * The type 'struct timezone' is still declared as a complete type in <sys/time.h>, but code that uses its fields (tz_minuteswest and tz_dsttime) will not compile. * Similarly, code that uses the 'timezone' and 'dstflag' fields of struct timeb will not compile anymore. (This is a willful violation of the older iterations of XPG that included sys/timeb.h; the relevant conformance tests are XFAILed.) * Old binaries that pass a non-NULL 'tzp' pointer to gettimeofday will always receive a 'struct timezone' whose tz_minuteswest and tz_dsttime fields are zero (as if the system were operating on UTC). * Similarly, old binaries that call ftime will always receive a 'struct timeb' whose timezone and dstflag fields are zero. * If the 'tzp' argument to settimeofday is not NULL, the call will fail and set errno to ENOSYS. (This was already the case on the Hurd.) * glibc will always pass a second argument of NULL when invoking a kernel-provided gettimeofday. * On Alpha, the compat symbols gettimeofday@GLIBC_2.0 and settimeofday@GLIBC_2.0 (which used 32-bit time_t) now convert their arguments and call system primitives that use 64-bit time_t, instead of invoking legacy “osf” system calls. ChangeLog: * time/sys/time.h (struct timezone): Remove tz_minuteswest and tz_dsttime fields; replace with padding to preserve the size. * time/sys/timeb.h (struct timeb): Remove timezone and dstflag fields; replace with padding to preserve the size. * conform/Makefile: XFAIL tests because struct timeb is no longer fully conformant with Unix98. * sysdeps/posix/gettimeofday.c * sysdeps/unix/sysv/linux/gettimeofday.c * sysdeps/unix/sysv/linux/aarch64/gettimeofday.c * sysdeps/unix/sysv/linux/powerpc/gettimeofday.c * sysdeps/unix/sysv/linux/x86/gettimeofday.c (gettimeofday): When ‘tz’ argument is not NULL, just clear it. Always pass a null pointer as the second argument to a gettimeofday (v)syscall. * sysdeps/unix/bsd/ftime.c: Unconditionally clear the memory that was formerly the ‘timezone’ and ‘dstflag’ fields of struct timeb. * sysdeps/unix/syscalls.list: Remove entry for settimeofday. * sysdeps/unix/settimeofday.c: New file. (settimeofday): Fail with ENOSYS if ‘tz’ argument is not NULL. * sysdeps/unix/sysv/linux/alpha/syscalls.list: Remove entries for osf_gettimeofday, osf_settimeofday, and settimeofday. * sysdeps/unix/sysv/linux/alpha/osf_gettimeofday.c: New file. Call the 64-bit gettimeofday, then convert to a 32-bit struct timeval. On overflow, saturate the struct timeval and fail with EOVERFLOW. * sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c: New file. Convert to a 64-bit struct timeval and call 64-bit settimeofday. Fail with ENOSYS if ‘tz’ argument is not NULL. * sunrpc/auth_des.c, sunrpc/auth_unix.c * sysdeps/posix/time.c, sysdeps/unix/stime.c: Remove unnecessary casts of NULL. * sysdeps/unix/sysv/linux/powerpc/time.c (time_syscall): Use (void *)0 instead of NULL when passing a null pointer as an untyped argument. * manual/time.texi: Remove documentation of fields of struct timezone. Revise text to further emphasize that the second argument to gettimeofday/settimeofday should always be a null pointer.
Diffstat (limited to 'sysdeps/unix')
-rw-r--r--sysdeps/unix/bsd/ftime.c10
-rw-r--r--sysdeps/unix/settimeofday.c36
-rw-r--r--sysdeps/unix/stime.c2
-rw-r--r--sysdeps/unix/syscalls.list1
-rw-r--r--sysdeps/unix/sysv/linux/aarch64/gettimeofday.c8
-rw-r--r--sysdeps/unix/sysv/linux/alpha/osf_gettimeofday.c62
-rw-r--r--sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c51
-rw-r--r--sysdeps/unix/sysv/linux/alpha/syscalls.list3
-rw-r--r--sysdeps/unix/sysv/linux/gettimeofday.c5
-rw-r--r--sysdeps/unix/sysv/linux/powerpc/gettimeofday.c13
-rw-r--r--sysdeps/unix/sysv/linux/powerpc/time.c2
-rw-r--r--sysdeps/unix/sysv/linux/x86/gettimeofday.c8
12 files changed, 183 insertions, 18 deletions
diff --git a/sysdeps/unix/bsd/ftime.c b/sysdeps/unix/bsd/ftime.c
index 3a1c6e9..32ce84e 100644
--- a/sysdeps/unix/bsd/ftime.c
+++ b/sysdeps/unix/bsd/ftime.c
@@ -17,14 +17,14 @@
#include <sys/timeb.h>
#include <sys/time.h>
+#include <string.h>
int
ftime (struct timeb *timebuf)
{
struct timeval tv;
- struct timezone tz;
- if (__gettimeofday (&tv, &tz) < 0)
+ if (__gettimeofday (&tv, 0) < 0)
return -1;
timebuf->time = tv.tv_sec;
@@ -34,7 +34,9 @@ ftime (struct timeb *timebuf)
++timebuf->time;
timebuf->millitm = 0;
}
- timebuf->timezone = tz.tz_minuteswest;
- timebuf->dstflag = tz.tz_dsttime;
+
+ memset (timebuf->__preserve_historic_size, 0,
+ sizeof timebuf->__preserve_historic_size);
+
return 0;
}
diff --git a/sysdeps/unix/settimeofday.c b/sysdeps/unix/settimeofday.c
new file mode 100644
index 0000000..741493b
--- /dev/null
+++ b/sysdeps/unix/settimeofday.c
@@ -0,0 +1,36 @@
+/* settimeofday -- Set the current time of day. Unix version.
+ Copyright (C) 2019 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, see
+ <http://www.gnu.org/licenses/>. */
+
+#include <errno.h>
+#include <sys/time.h>
+#include <sysdep.h>
+#include <libc-symbols.h>
+
+/* Set the current time of day and timezone information.
+ This call is restricted to the super-user. */
+int
+__settimeofday (const struct timeval *tv, const struct timezone *tz)
+{
+ if (tz)
+ {
+ __set_errno (ENOSYS);
+ return -1;
+ }
+ return INLINE_SYSCALL_CALL (settimeofday, tv, (void *)0);
+}
+weak_alias (__settimeofday, settimeofday);
diff --git a/sysdeps/unix/stime.c b/sysdeps/unix/stime.c
index b0809be..554b3ef 100644
--- a/sysdeps/unix/stime.c
+++ b/sysdeps/unix/stime.c
@@ -35,5 +35,5 @@ stime (const time_t *when)
tv.tv_sec = *when;
tv.tv_usec = 0;
- return __settimeofday (&tv, (struct timezone *) 0);
+ return __settimeofday (&tv, 0);
}
diff --git a/sysdeps/unix/syscalls.list b/sysdeps/unix/syscalls.list
index 61e5360..5fedd57 100644
--- a/sysdeps/unix/syscalls.list
+++ b/sysdeps/unix/syscalls.list
@@ -76,7 +76,6 @@ setreuid - setreuid i:ii __setreuid setreuid
setrlimit - setrlimit i:ip __setrlimit setrlimit
setsid - setsid i: __setsid setsid
setsockopt - setsockopt i:iiibn setsockopt __setsockopt
-settimeofday - settimeofday i:PP __settimeofday settimeofday
setuid - setuid i:i __setuid setuid
shutdown - shutdown i:ii shutdown
sigaction - sigaction i:ipp __sigaction sigaction
diff --git a/sysdeps/unix/sysv/linux/aarch64/gettimeofday.c b/sysdeps/unix/sysv/linux/aarch64/gettimeofday.c
index 9180b50..47330e2 100644
--- a/sysdeps/unix/sysv/linux/aarch64/gettimeofday.c
+++ b/sysdeps/unix/sysv/linux/aarch64/gettimeofday.c
@@ -35,7 +35,9 @@
static int
__gettimeofday_vsyscall (struct timeval *tv, struct timezone *tz)
{
- return INLINE_VSYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_VSYSCALL (gettimeofday, 2, tv, (void *)0);
}
/* PREPARE_VERSION_KNOWN will need an __LP64__ ifdef when ILP32 support
@@ -61,7 +63,9 @@ __hidden_ver1 (__gettimeofday_vsyscall, __GI___gettimeofday,
int
__gettimeofday (struct timeval *tv, struct timezone *tz)
{
- return INLINE_SYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_SYSCALL (gettimeofday, 2, tv, (void *)0);
}
libc_hidden_def (__gettimeofday)
diff --git a/sysdeps/unix/sysv/linux/alpha/osf_gettimeofday.c b/sysdeps/unix/sysv/linux/alpha/osf_gettimeofday.c
new file mode 100644
index 0000000..8e57727
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/alpha/osf_gettimeofday.c
@@ -0,0 +1,62 @@
+/* gettimeofday -- Get the current time of day. Linux/Alpha/tv32 version.
+ Copyright (C) 2019 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, see
+ <http://www.gnu.org/licenses/>. */
+
+#include <errno.h>
+#include <limits.h>
+#include <sys/time.h>
+#include <sysdep.h>
+#include <shlib-compat.h>
+
+#if SHLIB_COMPAT (libc, GLIBC_2_0, GLIBC_2_1)
+
+struct timeval32
+{
+ int tv_sec, tv_usec;
+};
+
+/* Get the current time of day and timezone information. */
+int
+attribute_compat_text_section
+__gettimeofday_tv32 (struct timeval32 *tv32,
+ struct timezone *tz)
+{
+ struct timeval tv64;
+ if (__gettimeofday (&tv64, tz))
+ return -1;
+
+ /* The tv_sec field of a 64-bit struct timeval will overflow the
+ range representable by 'int' at 2038-01-19 03:14:07 +0000. */
+ if (tv64.tv_sec > (time_t)INT_MAX)
+ {
+ tv32.tv_sec = INT_MAX;
+ tv32.tv_usec = 0;
+ __set_errno (EOVERFLOW);
+ return -1;
+ }
+ tv32.tv_sec = (int)tv64.tv_sec;
+
+ /* The tv_usec field of a 64-bit struct timeval may be a 64-bit
+ type, but it never contains a value outside the range [0, 999999],
+ so this cast is guaranteed not to lose information. */
+ tv32.tv_usec = (int)tv64.tv_usec;
+
+ return 0;
+}
+
+compat_symbol (libc, __gettimeofday_tv32, gettimeofday, GLIBC_2_0);
+#endif
diff --git a/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c
new file mode 100644
index 0000000..2ab2f81
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c
@@ -0,0 +1,51 @@
+/* settimeofday -- Set the current time of day. Linux/Alpha/tv32 version.
+ Copyright (C) 2019 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, see
+ <http://www.gnu.org/licenses/>. */
+
+#include <errno.h>
+#include <sys/time.h>
+#include <sysdep.h>
+#include <shlib-compat.h>
+
+#if SHLIB_COMPAT (libc, GLIBC_2_0, GLIBC_2_1)
+
+struct timeval32
+{
+ int tv_sec, tv_usec;
+};
+
+/* Set the current time of day and timezone information.
+ This call is restricted to the super-user. */
+int
+attribute_compat_text_section
+__settimeofday_tv32 (const struct timeval32 *tv32,
+ const struct timezone *tz)
+{
+ if (tz)
+ {
+ __set_errno (ENOSYS);
+ return -1;
+ }
+
+ struct timeval tv64;
+ tv64.tv_sec = tv32.tv_sec;
+ tv64.tv_usec = tv32.tv_usec;
+ return INLINE_SYSCALL_CALL (settimeofday, tv, (void *)0);
+}
+
+compat_symbol (libc, __settimeofday_tv32, settimeofday, GLIBC_2_0);
+#endif
diff --git a/sysdeps/unix/sysv/linux/alpha/syscalls.list b/sysdeps/unix/sysv/linux/alpha/syscalls.list
index 12cd021..8244f94 100644
--- a/sysdeps/unix/sysv/linux/alpha/syscalls.list
+++ b/sysdeps/unix/sysv/linux/alpha/syscalls.list
@@ -23,8 +23,6 @@ pciconfig_write EXTRA pciconfig_write 5 pciconfig_write
pciconfig_iobase EXTRA pciconfig_iobase 3 __pciconfig_iobase pciconfig_iobase
# support old timeval32 entry points
-osf_gettimeofday - osf_gettimeofday 2 __gettimeofday_tv32 __gettimeofday@GLIBC_2.0 gettimeofday@GLIBC_2.0
-osf_settimeofday - osf_settimeofday 2 __settimeofday_tv32 settimeofday@GLIBC_2.0
osf_getitimer - osf_getitimer 2 __getitimer_tv32 getitimer@GLIBC_2.0
osf_setitimer - osf_setitimer 3 __setitimer_tv32 setitimer@GLIBC_2.0
osf_utimes - osf_utimes 2 __utimes_tv32 utimes@GLIBC_2.0
@@ -33,7 +31,6 @@ osf_wait4 - osf_wait4 4 __wait4_tv32 wait4@GLIBC_2.0
# support new timeval64 entry points
gettimeofday - gettimeofday 2 __GI___gettimeofday gettimeofday@@GLIBC_2.1 __gettimeofday@@GLIBC_2.1
-settimeofday - settimeofday 2 __settimeofday settimeofday@@GLIBC_2.1
getitimer - getitimer 2 __getitimer getitimer@@GLIBC_2.1
setitimer - setitimer 3 __setitimer setitimer@@GLIBC_2.1
utimes - utimes 2 __utimes utimes@@GLIBC_2.1
diff --git a/sysdeps/unix/sysv/linux/gettimeofday.c b/sysdeps/unix/sysv/linux/gettimeofday.c
index a74f038..3509ca9 100644
--- a/sysdeps/unix/sysv/linux/gettimeofday.c
+++ b/sysdeps/unix/sysv/linux/gettimeofday.c
@@ -18,6 +18,7 @@
#include <errno.h>
#include <sys/time.h>
+#include <string.h>
#undef __gettimeofday
@@ -32,7 +33,9 @@
int
__gettimeofday (struct timeval *tv, struct timezone *tz)
{
- return INLINE_VSYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_VSYSCALL (gettimeofday, 2, tv, (void *)0);
}
libc_hidden_def (__gettimeofday)
weak_alias (__gettimeofday, gettimeofday)
diff --git a/sysdeps/unix/sysv/linux/powerpc/gettimeofday.c b/sysdeps/unix/sysv/linux/powerpc/gettimeofday.c
index 463b678..e798a80 100644
--- a/sysdeps/unix/sysv/linux/powerpc/gettimeofday.c
+++ b/sysdeps/unix/sysv/linux/powerpc/gettimeofday.c
@@ -22,6 +22,7 @@
#endif
#include <sys/time.h>
+#include <string.h>
#ifdef SHARED
@@ -35,7 +36,9 @@
int
__gettimeofday_vsyscall (struct timeval *tv, struct timezone *tz)
{
- return INLINE_VSYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_VSYSCALL (gettimeofday, 2, tv, (void *)0);
}
/* __GI___gettimeofday is defined as hidden and for ppc32 it enables the
@@ -54,7 +57,9 @@ __gettimeofday_vsyscall (struct timeval *tv, struct timezone *tz)
static int
__gettimeofday_syscall (struct timeval *tv, struct timezone *tz)
{
- return INLINE_SYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_SYSCALL (gettimeofday, 2, tv, (void *)0);
}
# define INIT_ARCH() \
@@ -76,7 +81,9 @@ libc_hidden_def (__gettimeofday)
int
__gettimeofday (struct timeval *tv, struct timezone *tz)
{
- return INLINE_SYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_SYSCALL (gettimeofday, 2, tv, (void *)0);
}
libc_hidden_def (__gettimeofday)
diff --git a/sysdeps/unix/sysv/linux/powerpc/time.c b/sysdeps/unix/sysv/linux/powerpc/time.c
index cb3e8b9..42b0d2d 100644
--- a/sysdeps/unix/sysv/linux/powerpc/time.c
+++ b/sysdeps/unix/sysv/linux/powerpc/time.c
@@ -56,7 +56,7 @@ time_syscall (time_t *t)
struct timeval tv;
time_t result;
- if (INLINE_VSYSCALL (gettimeofday, 2, &tv, NULL) < 0)
+ if (INLINE_VSYSCALL (gettimeofday, 2, &tv, (void *)0) < 0)
result = (time_t) -1;
else
result = (time_t) tv.tv_sec;
diff --git a/sysdeps/unix/sysv/linux/x86/gettimeofday.c b/sysdeps/unix/sysv/linux/x86/gettimeofday.c
index 8886ccd..58a8763 100644
--- a/sysdeps/unix/sysv/linux/x86/gettimeofday.c
+++ b/sysdeps/unix/sysv/linux/x86/gettimeofday.c
@@ -26,7 +26,9 @@
static int
__gettimeofday_syscall (struct timeval *tv, struct timezone *tz)
{
- return INLINE_SYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_SYSCALL (gettimeofday, 2, tv, (void *)0);
}
# ifndef __gettimeofday_type
@@ -52,7 +54,9 @@ libc_hidden_def (__gettimeofday)
int
__gettimeofday (struct timeval *tv, struct timezone *tz)
{
- return INLINE_SYSCALL (gettimeofday, 2, tv, tz);
+ if (tz)
+ memset (tz, 0, sizeof (struct timezone));
+ return INLINE_SYSCALL (gettimeofday, 2, tv, (void *)0);
}
libc_hidden_def (__gettimeofday)