summaryrefslogtreecommitdiff
path: root/sysdeps/unix
diff options
context:
space:
mode:
authorAlbert ARIBAUD (3ADEV) <albert.aribaud@3adev.fr>2017-09-08 00:41:37 +0200
committerAlbert ARIBAUD (3ADEV) <albert.aribaud@3adev.fr>2018-06-13 09:06:53 +0200
commit1e99ca0383cd75ee87e7eac79039f76194daef75 (patch)
tree35aa390f1e7923a06868ccd4ca21eb86d0709f61 /sysdeps/unix
parent0f0d8664249036ad7d0b7bada1abe45fa2699ca8 (diff)
downloadglibc-1e99ca0383cd75ee87e7eac79039f76194daef75.tar.gz
Y2038: add function __clock_nanosleep64
Linux does not provide a 64-bit-time clock_nanosleep syscall, so __clock_nanosleep64 is a wrapper calling __clock_nanosleep, with one conversion before the call and possibly one after. Note: There is no point in implementing __clock_nanosleep64 directly around the 32-bit-time syscall and making __clock_nanosleep a wrapper around __clock_nanosleep64, because __clock_nanosleep64 would still need one or two conversions, and __clock_nanosleep would now also need those, adding a cost of 2 to 4 conversions in the worst case.
Diffstat (limited to 'sysdeps/unix')
-rw-r--r--sysdeps/unix/sysv/linux/clock_nanosleep.c49
1 files changed, 48 insertions, 1 deletions
diff --git a/sysdeps/unix/sysv/linux/clock_nanosleep.c b/sysdeps/unix/sysv/linux/clock_nanosleep.c
index 93d5d6ef12..6878da9065 100644
--- a/sysdeps/unix/sysv/linux/clock_nanosleep.c
+++ b/sysdeps/unix/sysv/linux/clock_nanosleep.c
@@ -21,7 +21,6 @@
#include <sysdep-cancel.h>
#include "kernel-posix-cpu-timers.h"
-
/* We can simply use the syscall. The CPU clocks are not supported
with this function. */
int
@@ -52,3 +51,51 @@ __clock_nanosleep (clockid_t clock_id, int flags, const struct timespec *req,
? INTERNAL_SYSCALL_ERRNO (r, err) : 0);
}
weak_alias (__clock_nanosleep, clock_nanosleep)
+
+/* 64-bit time version */
+
+/* We don't have a 64-bit-time syscall yet, so just convert arguments
+ * between 64-bit and 32-bit time, and use the 32-bit implementation.
+ *
+ * We could do the reverse and make the 32-bit time implementation a
+ * wrapper around the 64-bit-time implementation, but then 32-bit-time
+ * uses would incur four conversions instead of zero right now.
+ */
+int
+__clock_nanosleep64 (clockid_t clock_id, int flags,
+ const struct __timespec64 *req,
+ struct __timespec64 *rem)
+{
+ int res;
+ struct timespec req32, rem32, *rem32p = NULL;
+
+ if (req == NULL)
+ {
+ __set_errno (EFAULT);
+ return -1;
+ }
+
+ if (req->tv_sec > INT32_MAX || req->tv_sec < INT32_MIN)
+ {
+ __set_errno (EOVERFLOW);
+ return -1;
+ }
+
+ /* For now, use the 32-bit-time implementation above */
+
+ req32.tv_sec = req->tv_sec;
+ req32.tv_nsec = req->tv_nsec;
+
+ if (rem != NULL)
+ rem32p = &rem32;
+
+ res = __clock_nanosleep (clock_id, flags, &req32, rem32p);
+
+ if (res == 0 && rem != NULL)
+ {
+ rem->tv_sec = rem32.tv_sec;
+ rem->tv_nsec = rem32.tv_nsec;
+ }
+
+ return res;
+}