Message ID | 20191025120832.27667-5-adhemerval.zanella@linaro.org |
---|---|
State | Accepted |
Commit | c3f9aef063cd9d5911e20d4f2b919ff2914c7965 |
Headers | show |
Series | Y2038 preparation: use clock_[gs]ettime to implement the other time-getting and -setting functions. | expand |
On Fri, 25 Oct 2019 09:08:25 -0300 Adhemerval Zanella <adhemerval.zanella@linaro.org> wrote: > From: Zack Weinberg <zackw@panix.com> > > Use clock_settime to implement settimeofday. > > Changes from previous version: > > - Added a NEWS entry. > > -- > > Unconditionally, on all ports, use clock_settime to implement > settimeofday. Remove sysdeps/unix/clock_settime.c, which implemented > clock_settime by calling settimeofday; new OS ports must henceforth > provide a real implementation of clock_settime. > > Hurd had a real implementation of settimeofday but not of > clock_settime; this patch converts it into an implementation of > clock_settime. It only supports CLOCK_REALTIME and microsecond > resolution; Hurd/Mach does not appear to have any support for > finer-resolution clocks. > > The vestigial "set time zone" feature of settimeofday complicates the > generic settimeofday implementation a little. The only remaining uses > of this feature that aren't just bugs, are using it to inform the > Linux kernel of the offset between the hardware clock and UTC, on > systems where the hardware clock doesn't run in UTC (usually because > of dual-booting with Windows). There currently isn't any other way to > do this. However, the callers that do this call settimeofday with > _only_ the timezone argument non-NULL. Therefore, glibc's new > behavior is: callers of settimeofday must supply one and only one of > the two arguments. If both arguments are non-NULL, or both arguments > are NULL, the call fails and sets errno to EINVAL. > > When only the timeval argument is supplied, settimeofday calls > __clock_settime(CLOCK_REALTIME), same as stime. > > When only the timezone argument is supplied, settimeofday calls a new > internal function called __settimezone. On Linux, only, this function > will pass the timezone structure to the settimeofday system call. On > all other operating systems, and on Linux architectures that don't > define __NR_settimeofday, __settimezone is a stub that always sets > errno to ENOSYS and returns -1. > > The settimeoday syscall is enabled on Linux by the flag > COMPAT_32BIT_TIME, which is an option to either 32-bits ABIs or COMPAT > builds (defined usually by 64-bit kernels that want to support 32-bit > ABIs, such as x86). The idea to future 64-bit time_t only ABIs > is to not provide settimeofday syscall. > > The same semantics are implemented for Linux/Alpha's GLIBC_2.0 compat > symbol for settimeofday. > > There are no longer any internal callers of __settimeofday, so the > internal prototype is removed. > > Checked on x86_64-linux-gnu, i686-linux-gnu, powerpc64le-linux-gnu, > powerpc64-linux-gnu, powerpc-linux-gnu, and aarch64-linux-gnu. > > Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org> > --- > NEWS | 24 +++++++++ > include/sys/time.h | 3 +- > sysdeps/{unix => mach/hurd}/clock_settime.c | 51 > ++++++++----------- sysdeps/unix/syscalls.list | > 1 - .../unix/sysv/linux/alpha/osf_settimeofday.c | 16 ++++-- > sysdeps/unix/sysv/linux/alpha/settimeofday.c | 22 ++++++++ > sysdeps/unix/sysv/linux/alpha/syscalls.list | 1 - > sysdeps/unix/sysv/linux/settimezone.c | 36 +++++++++++++ > time/Makefile | 8 +-- > time/settimeofday.c | 24 +++++++-- > .../hurd/settimeofday.c => time/settimezone.c | 34 ++----------- > 11 files changed, 147 insertions(+), 73 deletions(-) > rename sysdeps/{unix => mach/hurd}/clock_settime.c (65%) > create mode 100644 sysdeps/unix/sysv/linux/alpha/settimeofday.c > create mode 100644 sysdeps/unix/sysv/linux/settimezone.c > rename sysdeps/mach/hurd/settimeofday.c => time/settimezone.c (52%) > > diff --git a/NEWS b/NEWS > index 8727b5e7f0..0b1476e745 100644 > --- a/NEWS > +++ b/NEWS > @@ -34,6 +34,30 @@ Deprecated and removed features, and other changes > affecting compatibility: binaries and it has been removed from > <time.h> header. This function has been deprecated in favor of > clock_settime. > +* The settimeofday function can still be used to set a system-wide > time > + zone when the operating system supports it. This is because the > Linux > + kernel reused the API, on some architectures, to describe a > system-wide > + time-zone-like offset between the software clock maintained by the > kernel, > + and the “RTC” clock that keeps time when the system is shut down. > + > + However, to reduce the odds of this offset being set by accident, > + settimeofday can no longer be used to set the time and the offset > + simultaneously. If both of its two arguments are non-null, the > call > + will fail (setting errno to EINVAL). > + > + Callers attempting to set this offset should also be prepared for > the call > + to fail and set errno to ENOSYS; this already happens on the Hurd > and on > + some Linux architectures. The Linux kernel maintainers are > discussing a > + more principled replacement for the reused API. After a > replacement > + becomes available, we will change settimeofday to fail with ENOSYS > on all > + platforms when its ‘tzp’ argument is not a null pointer. > + > + Note that settimeofday itself is obsolescent according to POSIX. > + Programs that set the system time should use clock_settime and/or > + the adjtime family of functions instead. We may also cease to make > + settimeofday available to newly linked binaries after there is a > + replacement for Linux’s time-zone-like offset API. > + > Changes to build and runtime requirements: > > [Add changes to build and runtime requirements here] > diff --git a/include/sys/time.h b/include/sys/time.h > index 57208afa82..c0e30e70fb 100644 > --- a/include/sys/time.h > +++ b/include/sys/time.h > @@ -24,8 +24,7 @@ extern int __gettimeofday (struct timeval *__tv, > struct timezone *__tz); > libc_hidden_proto (__gettimeofday) > libc_hidden_proto (gettimeofday) > -extern int __settimeofday (const struct timeval *__tv, > - const struct timezone *__tz) > +extern int __settimezone (const struct timezone *__tz) > attribute_hidden; > extern int __adjtime (const struct timeval *__delta, > struct timeval *__olddelta); > diff --git a/sysdeps/unix/clock_settime.c > b/sysdeps/mach/hurd/clock_settime.c similarity index 65% > rename from sysdeps/unix/clock_settime.c > rename to sysdeps/mach/hurd/clock_settime.c > index 18d7c99864..02239c097a 100644 > --- a/sysdeps/unix/clock_settime.c > +++ b/sysdeps/mach/hurd/clock_settime.c > @@ -1,4 +1,4 @@ > -/* Copyright (C) 1999-2019 Free Software Foundation, Inc. > +/* Copyright (C) 1991-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 > @@ -17,38 +17,31 @@ > > #include <errno.h> > #include <time.h> > -#include <sys/time.h> > +#include <hurd.h> > +#include <hurd/port.h> > #include <shlib-compat.h> > > -/* Set CLOCK to value TP. */ > +/* Set the current time of day. > + This call is restricted to the super-user. */ > int > -__clock_settime (clockid_t clock_id, const struct timespec *tp) > +__clock_settime (clockid_t clock_id, const struct timespec *ts) > { > - int retval = -1; > - > - /* Make sure the time cvalue is OK. */ > - if (tp->tv_nsec < 0 || tp->tv_nsec >= 1000000000) > - { > - __set_errno (EINVAL); > - return -1; > - } > - > - switch (clock_id) > - { > - case CLOCK_REALTIME: > - { > - struct timeval tv; > - TIMESPEC_TO_TIMEVAL (&tv, tp); > - retval = __settimeofday (&tv, NULL); > - } > - break; > - > - default: > - __set_errno (EINVAL); > - break; > - } > - > - return retval; > + error_t err; > + mach_port_t hostpriv; > + time_value_t tv; > + > + if (clock_id != CLOCK_REALTIME) > + return __hurd_fail (EINVAL); > + > + err = __get_privileged_ports (&hostpriv, NULL); > + if (err) > + return __hurd_fail (EPERM); > + > + TIMESPEC_TO_TIME_VALUE (&tv, ts); > + err = __host_set_time (hostpriv, tv); > + __mach_port_deallocate (__mach_task_self (), hostpriv); > + > + return __hurd_fail (err); > } > libc_hidden_def (__clock_settime) > > diff --git a/sysdeps/unix/syscalls.list b/sysdeps/unix/syscalls.list > index 61e5360b4d..5fedd5733d 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/alpha/osf_settimeofday.c > b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c index > fb2a36df19..914f5ac57b 100644 --- > a/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c +++ > b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c @@ -32,9 +32,19 @@ > attribute_compat_text_section __settimeofday_tv32 (const struct > timeval32 *tv32, const struct timezone *tz) { > - struct timeval tv; > - tv32_to_tv64 (&tv, tv32); > - return __settimeofday (&tv, tz); > + if (__glibc_unlikely (tz != 0)) > + { > + if (tv32 != 0) > + { > + __set_errno (EINVAL); > + return -1; > + } > + return __settimezone (tz); > + } > + > + struct timespec ts; > + tv32_to_ts64 (&ts, tv32); This can be replaced with valid_timeval_to_timespec64() from include/time.h > + return __clock_settime (CLOCK_REALTIME, &ts); > } > > compat_symbol (libc, __settimeofday_tv32, settimeofday, GLIBC_2_0); > diff --git a/sysdeps/unix/sysv/linux/alpha/settimeofday.c > b/sysdeps/unix/sysv/linux/alpha/settimeofday.c new file mode 100644 > index 0000000000..36a6901e4e > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/alpha/settimeofday.c > @@ -0,0 +1,22 @@ > +/* settimeofday -- Set the current time of day. Linux/Alpha/tv64 > 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/>. */ > + > +/* We can use the generic implementation, but we have to override its > + default symbol version. */ > +#define VERSION_settimeofday GLIBC_2.1 > +#include <time/settimeofday.c> > diff --git a/sysdeps/unix/sysv/linux/alpha/syscalls.list > b/sysdeps/unix/sysv/linux/alpha/syscalls.list index > c786aa751e..95a27e18e8 100644 --- > a/sysdeps/unix/sysv/linux/alpha/syscalls.list +++ > b/sysdeps/unix/sysv/linux/alpha/syscalls.list @@ -24,7 +24,6 @@ > pciconfig_iobase EXTRA pciconfig_iobase 3 > __pciconfig_iobase pciconfig_iobase # timeval64 entry points (see > osf_*.c for GLIBC_2.0 timeval32 equivalents) gettimeofday > - gettimeofday i:pP __GI___gettimeofday > gettimeofday@@GLIBC_2.1 __gettimeofday@@GLIBC_2.1 > -settimeofday - settimeofday i:PP > __settimeofday settimeofday@@GLIBC_2.1 getitimer > - getitimer i:ip __getitimer > getitimer@@GLIBC_2.1 setitimer - setitimer > i:ipP __setitimer setitimer@@GLIBC_2.1 utimes > - utimes i:sp __utimes > utimes@@GLIBC_2.1 diff --git a/sysdeps/unix/sysv/linux/settimezone.c > b/sysdeps/unix/sysv/linux/settimezone.c new file mode 100644 index > 0000000000..90b38307c6 --- /dev/null +++ > b/sysdeps/unix/sysv/linux/settimezone.c @@ -0,0 +1,36 @@ +/* Obsolete > set system time. Linux 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> > + > +/* Set the system-wide timezone. > + This call is restricted to the super-user. > + This operation is considered obsolete, kernel support may not be > + available on all architectures. */ > +int > +__settimezone (const struct timezone *tz) > +{ > +#ifdef __NR_settimeofday > + return INLINE_SYSCALL_CALL (settimeofday, NULL, tz); > +#else > + __set_errno (ENOSYS); > + return -1 > +#endif > +} > diff --git a/time/Makefile b/time/Makefile > index ad8844ea34..6de4e418d9 100644 > --- a/time/Makefile > +++ b/time/Makefile > @@ -31,13 +31,13 @@ headers := time.h sys/time.h sys/timeb.h > bits/time.h \ > routines := offtime asctime clock ctime ctime_r difftime \ > gmtime localtime mktime time \ > - gettimeofday settimeofday adjtime tzset \ > - tzfile getitimer setitimer \ > + gettimeofday settimeofday settimezone \ > + adjtime tzset tzfile getitimer setitimer \ > stime dysize timegm ftime \ > getdate strptime strptime_l \ > strftime wcsftime strftime_l wcsftime_l \ > - timespec_get \ > - clock_getcpuclockid clock_getres \ > + timespec_get \ > + clock_getcpuclockid clock_getres \ > clock_gettime clock_settime clock_nanosleep > > aux := era alt_digit lc-time-cleanup > diff --git a/time/settimeofday.c b/time/settimeofday.c > index 6aa4832d65..ad57ad41a1 100644 > --- a/time/settimeofday.c > +++ b/time/settimeofday.c > @@ -16,6 +16,7 @@ > <https://www.gnu.org/licenses/>. */ > > #include <errno.h> > +#include <time.h> > #include <sys/time.h> > > /* Set the current time of day and timezone information. > @@ -23,9 +24,24 @@ > int > __settimeofday (const struct timeval *tv, const struct timezone *tz) > { > - __set_errno (ENOSYS); > - return -1; > + if (__glibc_unlikely (tz != 0)) > + { > + if (tv != 0) > + { > + __set_errno (EINVAL); > + return -1; > + } > + return __settimezone (tz); > + } > + > + struct timespec ts; > + TIMEVAL_TO_TIMESPEC (tv, &ts); > + return __clock_settime (CLOCK_REALTIME, &ts); > } > -stub_warning (settimeofday) > > -weak_alias (__settimeofday, settimeofday) > +#ifdef VERSION_settimeofday > +weak_alias (__settimeofday, __settimeofday_w); > +default_symbol_version (__settimeofday_w, settimeofday, > VERSION_settimeofday); +#else > +weak_alias (__settimeofday, settimeofday); > +#endif > diff --git a/sysdeps/mach/hurd/settimeofday.c b/time/settimezone.c > similarity index 52% > rename from sysdeps/mach/hurd/settimeofday.c > rename to time/settimezone.c > index 31bffcad9d..b9969c9dd5 100644 > --- a/sysdeps/mach/hurd/settimeofday.c > +++ b/time/settimezone.c > @@ -1,4 +1,4 @@ > -/* Copyright (C) 1991-2019 Free Software Foundation, Inc. > +/* 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 > @@ -17,36 +17,12 @@ > > #include <errno.h> > #include <sys/time.h> > -#include <hurd.h> > -#include <hurd/port.h> > > -/* Set the current time of day and timezone information. > +/* Set the system-wide timezone. > This call is restricted to the super-user. */ > int > -__settimeofday (const struct timeval *tv, const struct timezone *tz) > +__settimezone (const struct timezone *tz) > { > - error_t err; > - mach_port_t hostpriv; > - > - if (tz != NULL) > - { > - errno = ENOSYS; > - return -1; > - } > - > - err = __get_privileged_ports (&hostpriv, NULL); > - if (err) > - return __hurd_fail (EPERM); > - > - /* `time_value_t' and `struct timeval' are in fact identical with > the > - names changed. */ > - err = __host_set_time (hostpriv, *(time_value_t *) tv); > - __mach_port_deallocate (__mach_task_self (), hostpriv); > - > - if (err) > - return __hurd_fail (err); > - > - return 0; > + __set_errno (ENOSYS); > + return -1; > } > - > -weak_alias (__settimeofday, settimeofday) Reviewed-by: Lukasz Majewski <lukma@denx.de> Best regards, Lukasz Majewski -- DENX Software Engineering GmbH, Managing Director: Wolfgang Denk HRB 165235 Munich, Office: Kirchenstr.5, D-82194 Groebenzell, Germany Phone: (+49)-8142-66989-59 Fax: (+49)-8142-66989-80 Email: lukma@denx.de
On Fri, Oct 25, 2019 at 5:09 AM Adhemerval Zanella <adhemerval.zanella@linaro.org> wrote: > > From: Zack Weinberg <zackw@panix.com> > > Use clock_settime to implement settimeofday. > > Changes from previous version: > > - Added a NEWS entry. > > -- > > Unconditionally, on all ports, use clock_settime to implement > settimeofday. Remove sysdeps/unix/clock_settime.c, which implemented > clock_settime by calling settimeofday; new OS ports must henceforth > provide a real implementation of clock_settime. > > Hurd had a real implementation of settimeofday but not of > clock_settime; this patch converts it into an implementation of > clock_settime. It only supports CLOCK_REALTIME and microsecond > resolution; Hurd/Mach does not appear to have any support for > finer-resolution clocks. > > The vestigial "set time zone" feature of settimeofday complicates the > generic settimeofday implementation a little. The only remaining uses > of this feature that aren't just bugs, are using it to inform the > Linux kernel of the offset between the hardware clock and UTC, on > systems where the hardware clock doesn't run in UTC (usually because > of dual-booting with Windows). There currently isn't any other way to > do this. However, the callers that do this call settimeofday with > _only_ the timezone argument non-NULL. Therefore, glibc's new > behavior is: callers of settimeofday must supply one and only one of > the two arguments. If both arguments are non-NULL, or both arguments > are NULL, the call fails and sets errno to EINVAL. > > When only the timeval argument is supplied, settimeofday calls > __clock_settime(CLOCK_REALTIME), same as stime. > > When only the timezone argument is supplied, settimeofday calls a new > internal function called __settimezone. On Linux, only, this function > will pass the timezone structure to the settimeofday system call. On > all other operating systems, and on Linux architectures that don't > define __NR_settimeofday, __settimezone is a stub that always sets > errno to ENOSYS and returns -1. > > The settimeoday syscall is enabled on Linux by the flag > COMPAT_32BIT_TIME, which is an option to either 32-bits ABIs or COMPAT > builds (defined usually by 64-bit kernels that want to support 32-bit > ABIs, such as x86). The idea to future 64-bit time_t only ABIs > is to not provide settimeofday syscall. > > The same semantics are implemented for Linux/Alpha's GLIBC_2.0 compat > symbol for settimeofday. > > There are no longer any internal callers of __settimeofday, so the > internal prototype is removed. > > Checked on x86_64-linux-gnu, i686-linux-gnu, powerpc64le-linux-gnu, > powerpc64-linux-gnu, powerpc-linux-gnu, and aarch64-linux-gnu. > > Reviewed-by: Adhemerval Zanella <adhemerval.zanella@linaro.org> > --- > NEWS | 24 +++++++++ > include/sys/time.h | 3 +- > sysdeps/{unix => mach/hurd}/clock_settime.c | 51 ++++++++----------- > sysdeps/unix/syscalls.list | 1 - > .../unix/sysv/linux/alpha/osf_settimeofday.c | 16 ++++-- > sysdeps/unix/sysv/linux/alpha/settimeofday.c | 22 ++++++++ > sysdeps/unix/sysv/linux/alpha/syscalls.list | 1 - > sysdeps/unix/sysv/linux/settimezone.c | 36 +++++++++++++ > time/Makefile | 8 +-- > time/settimeofday.c | 24 +++++++-- > .../hurd/settimeofday.c => time/settimezone.c | 34 ++----------- > 11 files changed, 147 insertions(+), 73 deletions(-) > rename sysdeps/{unix => mach/hurd}/clock_settime.c (65%) > create mode 100644 sysdeps/unix/sysv/linux/alpha/settimeofday.c > create mode 100644 sysdeps/unix/sysv/linux/settimezone.c > rename sysdeps/mach/hurd/settimeofday.c => time/settimezone.c (52%) > > diff --git a/NEWS b/NEWS > index 8727b5e7f0..0b1476e745 100644 > --- a/NEWS > +++ b/NEWS > @@ -34,6 +34,30 @@ Deprecated and removed features, and other changes affecting compatibility: > binaries and it has been removed from <time.h> header. This function > has been deprecated in favor of clock_settime. > > +* The settimeofday function can still be used to set a system-wide time > + zone when the operating system supports it. This is because the Linux > + kernel reused the API, on some architectures, to describe a system-wide > + time-zone-like offset between the software clock maintained by the kernel, > + and the “RTC” clock that keeps time when the system is shut down. > + > + However, to reduce the odds of this offset being set by accident, > + settimeofday can no longer be used to set the time and the offset > + simultaneously. If both of its two arguments are non-null, the call > + will fail (setting errno to EINVAL). > + > + Callers attempting to set this offset should also be prepared for the call > + to fail and set errno to ENOSYS; this already happens on the Hurd and on > + some Linux architectures. The Linux kernel maintainers are discussing a > + more principled replacement for the reused API. After a replacement > + becomes available, we will change settimeofday to fail with ENOSYS on all > + platforms when its ‘tzp’ argument is not a null pointer. > + > + Note that settimeofday itself is obsolescent according to POSIX. > + Programs that set the system time should use clock_settime and/or > + the adjtime family of functions instead. We may also cease to make > + settimeofday available to newly linked binaries after there is a > + replacement for Linux’s time-zone-like offset API. > + > Changes to build and runtime requirements: > > [Add changes to build and runtime requirements here] > diff --git a/include/sys/time.h b/include/sys/time.h > index 57208afa82..c0e30e70fb 100644 > --- a/include/sys/time.h > +++ b/include/sys/time.h > @@ -24,8 +24,7 @@ extern int __gettimeofday (struct timeval *__tv, > struct timezone *__tz); > libc_hidden_proto (__gettimeofday) > libc_hidden_proto (gettimeofday) > -extern int __settimeofday (const struct timeval *__tv, > - const struct timezone *__tz) > +extern int __settimezone (const struct timezone *__tz) > attribute_hidden; > extern int __adjtime (const struct timeval *__delta, > struct timeval *__olddelta); > diff --git a/sysdeps/unix/clock_settime.c b/sysdeps/mach/hurd/clock_settime.c > similarity index 65% > rename from sysdeps/unix/clock_settime.c > rename to sysdeps/mach/hurd/clock_settime.c > index 18d7c99864..02239c097a 100644 > --- a/sysdeps/unix/clock_settime.c > +++ b/sysdeps/mach/hurd/clock_settime.c > @@ -1,4 +1,4 @@ > -/* Copyright (C) 1999-2019 Free Software Foundation, Inc. > +/* Copyright (C) 1991-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 > @@ -17,38 +17,31 @@ > > #include <errno.h> > #include <time.h> > -#include <sys/time.h> > +#include <hurd.h> > +#include <hurd/port.h> > #include <shlib-compat.h> > > -/* Set CLOCK to value TP. */ > +/* Set the current time of day. > + This call is restricted to the super-user. */ > int > -__clock_settime (clockid_t clock_id, const struct timespec *tp) > +__clock_settime (clockid_t clock_id, const struct timespec *ts) > { > - int retval = -1; > - > - /* Make sure the time cvalue is OK. */ > - if (tp->tv_nsec < 0 || tp->tv_nsec >= 1000000000) > - { > - __set_errno (EINVAL); > - return -1; > - } > - > - switch (clock_id) > - { > - case CLOCK_REALTIME: > - { > - struct timeval tv; > - TIMESPEC_TO_TIMEVAL (&tv, tp); > - retval = __settimeofday (&tv, NULL); > - } > - break; > - > - default: > - __set_errno (EINVAL); > - break; > - } > - > - return retval; > + error_t err; > + mach_port_t hostpriv; > + time_value_t tv; > + > + if (clock_id != CLOCK_REALTIME) > + return __hurd_fail (EINVAL); > + > + err = __get_privileged_ports (&hostpriv, NULL); > + if (err) > + return __hurd_fail (EPERM); > + > + TIMESPEC_TO_TIME_VALUE (&tv, ts); > + err = __host_set_time (hostpriv, tv); > + __mach_port_deallocate (__mach_task_self (), hostpriv); > + > + return __hurd_fail (err); > } > libc_hidden_def (__clock_settime) > > diff --git a/sysdeps/unix/syscalls.list b/sysdeps/unix/syscalls.list > index 61e5360b4d..5fedd5733d 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/alpha/osf_settimeofday.c b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c > index fb2a36df19..914f5ac57b 100644 > --- a/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c > +++ b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c > @@ -32,9 +32,19 @@ attribute_compat_text_section > __settimeofday_tv32 (const struct timeval32 *tv32, > const struct timezone *tz) > { > - struct timeval tv; > - tv32_to_tv64 (&tv, tv32); > - return __settimeofday (&tv, tz); > + if (__glibc_unlikely (tz != 0)) > + { > + if (tv32 != 0) > + { > + __set_errno (EINVAL); > + return -1; > + } > + return __settimezone (tz); > + } > + > + struct timespec ts; > + tv32_to_ts64 (&ts, tv32); > + return __clock_settime (CLOCK_REALTIME, &ts); > } > > compat_symbol (libc, __settimeofday_tv32, settimeofday, GLIBC_2_0); > diff --git a/sysdeps/unix/sysv/linux/alpha/settimeofday.c b/sysdeps/unix/sysv/linux/alpha/settimeofday.c > new file mode 100644 > index 0000000000..36a6901e4e > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/alpha/settimeofday.c > @@ -0,0 +1,22 @@ > +/* settimeofday -- Set the current time of day. Linux/Alpha/tv64 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/>. */ > + > +/* We can use the generic implementation, but we have to override its > + default symbol version. */ > +#define VERSION_settimeofday GLIBC_2.1 > +#include <time/settimeofday.c> > diff --git a/sysdeps/unix/sysv/linux/alpha/syscalls.list b/sysdeps/unix/sysv/linux/alpha/syscalls.list > index c786aa751e..95a27e18e8 100644 > --- a/sysdeps/unix/sysv/linux/alpha/syscalls.list > +++ b/sysdeps/unix/sysv/linux/alpha/syscalls.list > @@ -24,7 +24,6 @@ pciconfig_iobase EXTRA pciconfig_iobase 3 __pciconfig_iobase pciconfig_iobase > > # timeval64 entry points (see osf_*.c for GLIBC_2.0 timeval32 equivalents) > gettimeofday - gettimeofday i:pP __GI___gettimeofday gettimeofday@@GLIBC_2.1 __gettimeofday@@GLIBC_2.1 > -settimeofday - settimeofday i:PP __settimeofday settimeofday@@GLIBC_2.1 > getitimer - getitimer i:ip __getitimer getitimer@@GLIBC_2.1 > setitimer - setitimer i:ipP __setitimer setitimer@@GLIBC_2.1 > utimes - utimes i:sp __utimes utimes@@GLIBC_2.1 > diff --git a/sysdeps/unix/sysv/linux/settimezone.c b/sysdeps/unix/sysv/linux/settimezone.c > new file mode 100644 > index 0000000000..90b38307c6 > --- /dev/null > +++ b/sysdeps/unix/sysv/linux/settimezone.c > @@ -0,0 +1,36 @@ > +/* Obsolete set system time. Linux 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> > + > +/* Set the system-wide timezone. > + This call is restricted to the super-user. > + This operation is considered obsolete, kernel support may not be > + available on all architectures. */ > +int > +__settimezone (const struct timezone *tz) > +{ > +#ifdef __NR_settimeofday > + return INLINE_SYSCALL_CALL (settimeofday, NULL, tz); > +#else > + __set_errno (ENOSYS); > + return -1 You are missing a semi-colon here. Alistair > +#endif > +} > diff --git a/time/Makefile b/time/Makefile > index ad8844ea34..6de4e418d9 100644 > --- a/time/Makefile > +++ b/time/Makefile > @@ -31,13 +31,13 @@ headers := time.h sys/time.h sys/timeb.h bits/time.h \ > > routines := offtime asctime clock ctime ctime_r difftime \ > gmtime localtime mktime time \ > - gettimeofday settimeofday adjtime tzset \ > - tzfile getitimer setitimer \ > + gettimeofday settimeofday settimezone \ > + adjtime tzset tzfile getitimer setitimer \ > stime dysize timegm ftime \ > getdate strptime strptime_l \ > strftime wcsftime strftime_l wcsftime_l \ > - timespec_get \ > - clock_getcpuclockid clock_getres \ > + timespec_get \ > + clock_getcpuclockid clock_getres \ > clock_gettime clock_settime clock_nanosleep > > aux := era alt_digit lc-time-cleanup > diff --git a/time/settimeofday.c b/time/settimeofday.c > index 6aa4832d65..ad57ad41a1 100644 > --- a/time/settimeofday.c > +++ b/time/settimeofday.c > @@ -16,6 +16,7 @@ > <https://www.gnu.org/licenses/>. */ > > #include <errno.h> > +#include <time.h> > #include <sys/time.h> > > /* Set the current time of day and timezone information. > @@ -23,9 +24,24 @@ > int > __settimeofday (const struct timeval *tv, const struct timezone *tz) > { > - __set_errno (ENOSYS); > - return -1; > + if (__glibc_unlikely (tz != 0)) > + { > + if (tv != 0) > + { > + __set_errno (EINVAL); > + return -1; > + } > + return __settimezone (tz); > + } > + > + struct timespec ts; > + TIMEVAL_TO_TIMESPEC (tv, &ts); > + return __clock_settime (CLOCK_REALTIME, &ts); > } > -stub_warning (settimeofday) > > -weak_alias (__settimeofday, settimeofday) > +#ifdef VERSION_settimeofday > +weak_alias (__settimeofday, __settimeofday_w); > +default_symbol_version (__settimeofday_w, settimeofday, VERSION_settimeofday); > +#else > +weak_alias (__settimeofday, settimeofday); > +#endif > diff --git a/sysdeps/mach/hurd/settimeofday.c b/time/settimezone.c > similarity index 52% > rename from sysdeps/mach/hurd/settimeofday.c > rename to time/settimezone.c > index 31bffcad9d..b9969c9dd5 100644 > --- a/sysdeps/mach/hurd/settimeofday.c > +++ b/time/settimezone.c > @@ -1,4 +1,4 @@ > -/* Copyright (C) 1991-2019 Free Software Foundation, Inc. > +/* 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 > @@ -17,36 +17,12 @@ > > #include <errno.h> > #include <sys/time.h> > -#include <hurd.h> > -#include <hurd/port.h> > > -/* Set the current time of day and timezone information. > +/* Set the system-wide timezone. > This call is restricted to the super-user. */ > int > -__settimeofday (const struct timeval *tv, const struct timezone *tz) > +__settimezone (const struct timezone *tz) > { > - error_t err; > - mach_port_t hostpriv; > - > - if (tz != NULL) > - { > - errno = ENOSYS; > - return -1; > - } > - > - err = __get_privileged_ports (&hostpriv, NULL); > - if (err) > - return __hurd_fail (EPERM); > - > - /* `time_value_t' and `struct timeval' are in fact identical with the > - names changed. */ > - err = __host_set_time (hostpriv, *(time_value_t *) tv); > - __mach_port_deallocate (__mach_task_self (), hostpriv); > - > - if (err) > - return __hurd_fail (err); > - > - return 0; > + __set_errno (ENOSYS); > + return -1; > } > - > -weak_alias (__settimeofday, settimeofday) > -- > 2.17.1 >
25.10.2019 14:08 Adhemerval Zanella <adhemerval.zanella@linaro.org> wrote: > > > From: Zack Weinberg <zackw@panix.com> > > Use clock_settime to implement settimeofday. > > Changes from previous version: > > - Added a NEWS entry. > > -- > > [...] > diff --git a/NEWS b/NEWS > index 8727b5e7f0..0b1476e745 100644 > --- a/NEWS > +++ b/NEWS > @@ -34,6 +34,30 @@ Deprecated and removed features, and other changes > affecting compatibility: > binaries and it has been removed from <time.h> header. This function > has been deprecated in favor of clock_settime. > > +* The settimeofday function can still be used to set a system-wide time > + zone when the operating system supports it. This is because the Linux > + kernel reused the API, on some architectures, to describe a system-wide > + time-zone-like offset between the software clock maintained by the > kernel, > + and the “RTC” clock that keeps time when the system is shut down. That's little off-topic and little nit-picky but are you sure you want to use the Unicode quotes like “” instead of plain ASCII "" ? No problem if this is what you really want but I suspect your editor converted this. > + However, to reduce the odds of this offset being set by accident, > + settimeofday can no longer be used to set the time and the offset > + simultaneously. If both of its two arguments are non-null, the call > + will fail (setting errno to EINVAL). > + > + Callers attempting to set this offset should also be prepared for the > call > + to fail and set errno to ENOSYS; this already happens on the Hurd and > on > + some Linux architectures. The Linux kernel maintainers are discussing > a > + more principled replacement for the reused API. After a replacement > + becomes available, we will change settimeofday to fail with ENOSYS on > all > + platforms when its ‘tzp’ argument is not a null pointer. Same here, the Unicode ‘’ instead of plain ASCII '' . > + Note that settimeofday itself is obsolescent according to POSIX. > + Programs that set the system time should use clock_settime and/or > + the adjtime family of functions instead. We may also cease to make > + settimeofday available to newly linked binaries after there is a > + replacement for Linux’s time-zone-like offset API. Again the Unicode apostrophe ’ instead of plain ASCII ' . Regards, Rafal
On 25/10/2019 12:28, Lukasz Majewski wrote: > On Fri, 25 Oct 2019 09:08:25 -0300 > Adhemerval Zanella <adhemerval.zanella@linaro.org> wrote: > >> From: Zack Weinberg <zackw@panix.com> >> [...] >> fb2a36df19..914f5ac57b 100644 --- >> a/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c +++ >> b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c @@ -32,9 +32,19 @@ >> attribute_compat_text_section __settimeofday_tv32 (const struct >> timeval32 *tv32, const struct timezone *tz) { >> - struct timeval tv; >> - tv32_to_tv64 (&tv, tv32); >> - return __settimeofday (&tv, tz); >> + if (__glibc_unlikely (tz != 0)) >> + { >> + if (tv32 != 0) >> + { >> + __set_errno (EINVAL); >> + return -1; >> + } >> + return __settimezone (tz); >> + } >> + >> + struct timespec ts; >> + tv32_to_ts64 (&ts, tv32); > > This can be replaced with valid_timeval_to_timespec64() from > include/time.h Not really, the timeval32 is alpha-specific.
On 25/10/2019 17:42, Alistair Francis wrote: > On Fri, Oct 25, 2019 at 5:09 AM Adhemerval Zanella > <adhemerval.zanella@linaro.org> wrote: >> >> From: Zack Weinberg <zackw@panix.com> [...] >> + >> +/* Set the system-wide timezone. >> + This call is restricted to the super-user. >> + This operation is considered obsolete, kernel support may not be >> + available on all architectures. */ >> +int >> +__settimezone (const struct timezone *tz) >> +{ >> +#ifdef __NR_settimeofday >> + return INLINE_SYSCALL_CALL (settimeofday, NULL, tz); >> +#else >> + __set_errno (ENOSYS); >> + return -1 > > You are missing a semi-colon here. > > Alistair Ack, fixed.
On 25/10/2019 20:20, Rafal Luzynski wrote: > 25.10.2019 14:08 Adhemerval Zanella <adhemerval.zanella@linaro.org> wrote: >> >> >> From: Zack Weinberg <zackw@panix.com> >> >> Use clock_settime to implement settimeofday. >> >> Changes from previous version: >> >> - Added a NEWS entry. >> >> -- >> >> [...] >> diff --git a/NEWS b/NEWS >> index 8727b5e7f0..0b1476e745 100644 >> --- a/NEWS >> +++ b/NEWS >> @@ -34,6 +34,30 @@ Deprecated and removed features, and other changes >> affecting compatibility: >> binaries and it has been removed from <time.h> header. This function >> has been deprecated in favor of clock_settime. >> >> +* The settimeofday function can still be used to set a system-wide time >> + zone when the operating system supports it. This is because the Linux >> + kernel reused the API, on some architectures, to describe a system-wide >> + time-zone-like offset between the software clock maintained by the >> kernel, >> + and the “RTC” clock that keeps time when the system is shut down. > > That's little off-topic and little nit-picky but are you sure you want to > use the Unicode quotes like “” instead of plain ASCII "" ? No problem if > this is what you really want but I suspect your editor converted this. I think this came from the original patchset from Zack, I have split the last commit that added the NEWS entry for all the changes. I changed to plan ASCII version. > >> + However, to reduce the odds of this offset being set by accident, >> + settimeofday can no longer be used to set the time and the offset >> + simultaneously. If both of its two arguments are non-null, the call >> + will fail (setting errno to EINVAL). >> + >> + Callers attempting to set this offset should also be prepared for the >> call >> + to fail and set errno to ENOSYS; this already happens on the Hurd and >> on >> + some Linux architectures. The Linux kernel maintainers are discussing >> a >> + more principled replacement for the reused API. After a replacement >> + becomes available, we will change settimeofday to fail with ENOSYS on >> all >> + platforms when its ‘tzp’ argument is not a null pointer. > > Same here, the Unicode ‘’ instead of plain ASCII '' . Ack, fixed. > >> + Note that settimeofday itself is obsolescent according to POSIX. >> + Programs that set the system time should use clock_settime and/or >> + the adjtime family of functions instead. We may also cease to make >> + settimeofday available to newly linked binaries after there is a >> + replacement for Linux’s time-zone-like offset API. > > Again the Unicode apostrophe ’ instead of plain ASCII ' . Ack, fixed. > > Regards, > > Rafal >
diff --git a/NEWS b/NEWS index 8727b5e7f0..0b1476e745 100644 --- a/NEWS +++ b/NEWS @@ -34,6 +34,30 @@ Deprecated and removed features, and other changes affecting compatibility: binaries and it has been removed from <time.h> header. This function has been deprecated in favor of clock_settime. +* The settimeofday function can still be used to set a system-wide time + zone when the operating system supports it. This is because the Linux + kernel reused the API, on some architectures, to describe a system-wide + time-zone-like offset between the software clock maintained by the kernel, + and the “RTC” clock that keeps time when the system is shut down. + + However, to reduce the odds of this offset being set by accident, + settimeofday can no longer be used to set the time and the offset + simultaneously. If both of its two arguments are non-null, the call + will fail (setting errno to EINVAL). + + Callers attempting to set this offset should also be prepared for the call + to fail and set errno to ENOSYS; this already happens on the Hurd and on + some Linux architectures. The Linux kernel maintainers are discussing a + more principled replacement for the reused API. After a replacement + becomes available, we will change settimeofday to fail with ENOSYS on all + platforms when its ‘tzp’ argument is not a null pointer. + + Note that settimeofday itself is obsolescent according to POSIX. + Programs that set the system time should use clock_settime and/or + the adjtime family of functions instead. We may also cease to make + settimeofday available to newly linked binaries after there is a + replacement for Linux’s time-zone-like offset API. + Changes to build and runtime requirements: [Add changes to build and runtime requirements here] diff --git a/include/sys/time.h b/include/sys/time.h index 57208afa82..c0e30e70fb 100644 --- a/include/sys/time.h +++ b/include/sys/time.h @@ -24,8 +24,7 @@ extern int __gettimeofday (struct timeval *__tv, struct timezone *__tz); libc_hidden_proto (__gettimeofday) libc_hidden_proto (gettimeofday) -extern int __settimeofday (const struct timeval *__tv, - const struct timezone *__tz) +extern int __settimezone (const struct timezone *__tz) attribute_hidden; extern int __adjtime (const struct timeval *__delta, struct timeval *__olddelta); diff --git a/sysdeps/unix/clock_settime.c b/sysdeps/mach/hurd/clock_settime.c similarity index 65% rename from sysdeps/unix/clock_settime.c rename to sysdeps/mach/hurd/clock_settime.c index 18d7c99864..02239c097a 100644 --- a/sysdeps/unix/clock_settime.c +++ b/sysdeps/mach/hurd/clock_settime.c @@ -1,4 +1,4 @@ -/* Copyright (C) 1999-2019 Free Software Foundation, Inc. +/* Copyright (C) 1991-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 @@ -17,38 +17,31 @@ #include <errno.h> #include <time.h> -#include <sys/time.h> +#include <hurd.h> +#include <hurd/port.h> #include <shlib-compat.h> -/* Set CLOCK to value TP. */ +/* Set the current time of day. + This call is restricted to the super-user. */ int -__clock_settime (clockid_t clock_id, const struct timespec *tp) +__clock_settime (clockid_t clock_id, const struct timespec *ts) { - int retval = -1; - - /* Make sure the time cvalue is OK. */ - if (tp->tv_nsec < 0 || tp->tv_nsec >= 1000000000) - { - __set_errno (EINVAL); - return -1; - } - - switch (clock_id) - { - case CLOCK_REALTIME: - { - struct timeval tv; - TIMESPEC_TO_TIMEVAL (&tv, tp); - retval = __settimeofday (&tv, NULL); - } - break; - - default: - __set_errno (EINVAL); - break; - } - - return retval; + error_t err; + mach_port_t hostpriv; + time_value_t tv; + + if (clock_id != CLOCK_REALTIME) + return __hurd_fail (EINVAL); + + err = __get_privileged_ports (&hostpriv, NULL); + if (err) + return __hurd_fail (EPERM); + + TIMESPEC_TO_TIME_VALUE (&tv, ts); + err = __host_set_time (hostpriv, tv); + __mach_port_deallocate (__mach_task_self (), hostpriv); + + return __hurd_fail (err); } libc_hidden_def (__clock_settime) diff --git a/sysdeps/unix/syscalls.list b/sysdeps/unix/syscalls.list index 61e5360b4d..5fedd5733d 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/alpha/osf_settimeofday.c b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c index fb2a36df19..914f5ac57b 100644 --- a/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c +++ b/sysdeps/unix/sysv/linux/alpha/osf_settimeofday.c @@ -32,9 +32,19 @@ attribute_compat_text_section __settimeofday_tv32 (const struct timeval32 *tv32, const struct timezone *tz) { - struct timeval tv; - tv32_to_tv64 (&tv, tv32); - return __settimeofday (&tv, tz); + if (__glibc_unlikely (tz != 0)) + { + if (tv32 != 0) + { + __set_errno (EINVAL); + return -1; + } + return __settimezone (tz); + } + + struct timespec ts; + tv32_to_ts64 (&ts, tv32); + return __clock_settime (CLOCK_REALTIME, &ts); } compat_symbol (libc, __settimeofday_tv32, settimeofday, GLIBC_2_0); diff --git a/sysdeps/unix/sysv/linux/alpha/settimeofday.c b/sysdeps/unix/sysv/linux/alpha/settimeofday.c new file mode 100644 index 0000000000..36a6901e4e --- /dev/null +++ b/sysdeps/unix/sysv/linux/alpha/settimeofday.c @@ -0,0 +1,22 @@ +/* settimeofday -- Set the current time of day. Linux/Alpha/tv64 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/>. */ + +/* We can use the generic implementation, but we have to override its + default symbol version. */ +#define VERSION_settimeofday GLIBC_2.1 +#include <time/settimeofday.c> diff --git a/sysdeps/unix/sysv/linux/alpha/syscalls.list b/sysdeps/unix/sysv/linux/alpha/syscalls.list index c786aa751e..95a27e18e8 100644 --- a/sysdeps/unix/sysv/linux/alpha/syscalls.list +++ b/sysdeps/unix/sysv/linux/alpha/syscalls.list @@ -24,7 +24,6 @@ pciconfig_iobase EXTRA pciconfig_iobase 3 __pciconfig_iobase pciconfig_iobase # timeval64 entry points (see osf_*.c for GLIBC_2.0 timeval32 equivalents) gettimeofday - gettimeofday i:pP __GI___gettimeofday gettimeofday@@GLIBC_2.1 __gettimeofday@@GLIBC_2.1 -settimeofday - settimeofday i:PP __settimeofday settimeofday@@GLIBC_2.1 getitimer - getitimer i:ip __getitimer getitimer@@GLIBC_2.1 setitimer - setitimer i:ipP __setitimer setitimer@@GLIBC_2.1 utimes - utimes i:sp __utimes utimes@@GLIBC_2.1 diff --git a/sysdeps/unix/sysv/linux/settimezone.c b/sysdeps/unix/sysv/linux/settimezone.c new file mode 100644 index 0000000000..90b38307c6 --- /dev/null +++ b/sysdeps/unix/sysv/linux/settimezone.c @@ -0,0 +1,36 @@ +/* Obsolete set system time. Linux 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> + +/* Set the system-wide timezone. + This call is restricted to the super-user. + This operation is considered obsolete, kernel support may not be + available on all architectures. */ +int +__settimezone (const struct timezone *tz) +{ +#ifdef __NR_settimeofday + return INLINE_SYSCALL_CALL (settimeofday, NULL, tz); +#else + __set_errno (ENOSYS); + return -1 +#endif +} diff --git a/time/Makefile b/time/Makefile index ad8844ea34..6de4e418d9 100644 --- a/time/Makefile +++ b/time/Makefile @@ -31,13 +31,13 @@ headers := time.h sys/time.h sys/timeb.h bits/time.h \ routines := offtime asctime clock ctime ctime_r difftime \ gmtime localtime mktime time \ - gettimeofday settimeofday adjtime tzset \ - tzfile getitimer setitimer \ + gettimeofday settimeofday settimezone \ + adjtime tzset tzfile getitimer setitimer \ stime dysize timegm ftime \ getdate strptime strptime_l \ strftime wcsftime strftime_l wcsftime_l \ - timespec_get \ - clock_getcpuclockid clock_getres \ + timespec_get \ + clock_getcpuclockid clock_getres \ clock_gettime clock_settime clock_nanosleep aux := era alt_digit lc-time-cleanup diff --git a/time/settimeofday.c b/time/settimeofday.c index 6aa4832d65..ad57ad41a1 100644 --- a/time/settimeofday.c +++ b/time/settimeofday.c @@ -16,6 +16,7 @@ <https://www.gnu.org/licenses/>. */ #include <errno.h> +#include <time.h> #include <sys/time.h> /* Set the current time of day and timezone information. @@ -23,9 +24,24 @@ int __settimeofday (const struct timeval *tv, const struct timezone *tz) { - __set_errno (ENOSYS); - return -1; + if (__glibc_unlikely (tz != 0)) + { + if (tv != 0) + { + __set_errno (EINVAL); + return -1; + } + return __settimezone (tz); + } + + struct timespec ts; + TIMEVAL_TO_TIMESPEC (tv, &ts); + return __clock_settime (CLOCK_REALTIME, &ts); } -stub_warning (settimeofday) -weak_alias (__settimeofday, settimeofday) +#ifdef VERSION_settimeofday +weak_alias (__settimeofday, __settimeofday_w); +default_symbol_version (__settimeofday_w, settimeofday, VERSION_settimeofday); +#else +weak_alias (__settimeofday, settimeofday); +#endif diff --git a/sysdeps/mach/hurd/settimeofday.c b/time/settimezone.c similarity index 52% rename from sysdeps/mach/hurd/settimeofday.c rename to time/settimezone.c index 31bffcad9d..b9969c9dd5 100644 --- a/sysdeps/mach/hurd/settimeofday.c +++ b/time/settimezone.c @@ -1,4 +1,4 @@ -/* Copyright (C) 1991-2019 Free Software Foundation, Inc. +/* 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 @@ -17,36 +17,12 @@ #include <errno.h> #include <sys/time.h> -#include <hurd.h> -#include <hurd/port.h> -/* Set the current time of day and timezone information. +/* Set the system-wide timezone. This call is restricted to the super-user. */ int -__settimeofday (const struct timeval *tv, const struct timezone *tz) +__settimezone (const struct timezone *tz) { - error_t err; - mach_port_t hostpriv; - - if (tz != NULL) - { - errno = ENOSYS; - return -1; - } - - err = __get_privileged_ports (&hostpriv, NULL); - if (err) - return __hurd_fail (EPERM); - - /* `time_value_t' and `struct timeval' are in fact identical with the - names changed. */ - err = __host_set_time (hostpriv, *(time_value_t *) tv); - __mach_port_deallocate (__mach_task_self (), hostpriv); - - if (err) - return __hurd_fail (err); - - return 0; + __set_errno (ENOSYS); + return -1; } - -weak_alias (__settimeofday, settimeofday)