summaryrefslogtreecommitdiffstats
path: root/kernel/time/time.c
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2017-07-03 19:14:51 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2017-07-03 19:14:51 -0400
commit1b044f1cfc65a7d90b209dfabd57e16d98b58c5b (patch)
treead657c911b563f9176b17578c0b88a1ea9916a02 /kernel/time/time.c
parente0f3e8f14da868047c524a0cf11e08b95fd1b008 (diff)
parent2287d8664fe7345ead891017eccd879fc605305e (diff)
Merge branch 'timers-core-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip
Pull timer updates from Thomas Gleixner: "A rather large update for timers/timekeeping: - compat syscall consolidation (Al Viro) - Posix timer consolidation (Christoph Helwig / Thomas Gleixner) - Cleanup of the device tree based initialization for clockevents and clocksources (Daniel Lezcano) - Consolidation of the FTTMR010 clocksource/event driver (Linus Walleij) - The usual set of small fixes and updates all over the place" * 'timers-core-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: (93 commits) timers: Make the cpu base lock raw clocksource/drivers/mips-gic-timer: Fix an error code in 'gic_clocksource_of_init()' clocksource/drivers/fsl_ftm_timer: Unmap region obtained by of_iomap clocksource/drivers/tcb_clksrc: Make IO endian agnostic clocksource/drivers/sun4i: Switch to the timer-of common init clocksource/drivers/timer-of: Fix invalid iomap check Revert "ktime: Simplify ktime_compare implementation" clocksource/drivers: Fix uninitialized variable use in timer_of_init kselftests: timers: Add test for frequency step kselftests: timers: Fix inconsistency-check to not ignore first timestamp time: Add warning about imminent deprecation of CONFIG_GENERIC_TIME_VSYSCALL_OLD time: Clean up CLOCK_MONOTONIC_RAW time handling posix-cpu-timers: Make timespec to nsec conversion safe itimer: Make timeval to nsec conversion range limited timers: Fix parameter description of try_to_del_timer_sync() ktime: Simplify ktime_compare implementation clocksource/drivers/fttmr010: Factor out clock read code clocksource/drivers/fttmr010: Implement delay timer clocksource/drivers: Add timer-of common init routine clocksource/drivers/tcb_clksrc: Save timer context on suspend/resume ...
Diffstat (limited to 'kernel/time/time.c')
-rw-r--r--kernel/time/time.c106
1 files changed, 105 insertions, 1 deletions
diff --git a/kernel/time/time.c b/kernel/time/time.c
index 49c73c6ed648..7c89e437c4d7 100644
--- a/kernel/time/time.c
+++ b/kernel/time/time.c
@@ -39,6 +39,7 @@
39#include <linux/ptrace.h> 39#include <linux/ptrace.h>
40 40
41#include <linux/uaccess.h> 41#include <linux/uaccess.h>
42#include <linux/compat.h>
42#include <asm/unistd.h> 43#include <asm/unistd.h>
43 44
44#include <generated/timeconst.h> 45#include <generated/timeconst.h>
@@ -99,6 +100,47 @@ SYSCALL_DEFINE1(stime, time_t __user *, tptr)
99 100
100#endif /* __ARCH_WANT_SYS_TIME */ 101#endif /* __ARCH_WANT_SYS_TIME */
101 102
103#ifdef CONFIG_COMPAT
104#ifdef __ARCH_WANT_COMPAT_SYS_TIME
105
106/* compat_time_t is a 32 bit "long" and needs to get converted. */
107COMPAT_SYSCALL_DEFINE1(time, compat_time_t __user *, tloc)
108{
109 struct timeval tv;
110 compat_time_t i;
111
112 do_gettimeofday(&tv);
113 i = tv.tv_sec;
114
115 if (tloc) {
116 if (put_user(i,tloc))
117 return -EFAULT;
118 }
119 force_successful_syscall_return();
120 return i;
121}
122
123COMPAT_SYSCALL_DEFINE1(stime, compat_time_t __user *, tptr)
124{
125 struct timespec tv;
126 int err;
127
128 if (get_user(tv.tv_sec, tptr))
129 return -EFAULT;
130
131 tv.tv_nsec = 0;
132
133 err = security_settime(&tv, NULL);
134 if (err)
135 return err;
136
137 do_settimeofday(&tv);
138 return 0;
139}
140
141#endif /* __ARCH_WANT_COMPAT_SYS_TIME */
142#endif
143
102SYSCALL_DEFINE2(gettimeofday, struct timeval __user *, tv, 144SYSCALL_DEFINE2(gettimeofday, struct timeval __user *, tv,
103 struct timezone __user *, tz) 145 struct timezone __user *, tz)
104{ 146{
@@ -215,6 +257,47 @@ SYSCALL_DEFINE2(settimeofday, struct timeval __user *, tv,
215 return do_sys_settimeofday64(tv ? &new_ts : NULL, tz ? &new_tz : NULL); 257 return do_sys_settimeofday64(tv ? &new_ts : NULL, tz ? &new_tz : NULL);
216} 258}
217 259
260#ifdef CONFIG_COMPAT
261COMPAT_SYSCALL_DEFINE2(gettimeofday, struct compat_timeval __user *, tv,
262 struct timezone __user *, tz)
263{
264 if (tv) {
265 struct timeval ktv;
266
267 do_gettimeofday(&ktv);
268 if (compat_put_timeval(&ktv, tv))
269 return -EFAULT;
270 }
271 if (tz) {
272 if (copy_to_user(tz, &sys_tz, sizeof(sys_tz)))
273 return -EFAULT;
274 }
275
276 return 0;
277}
278
279COMPAT_SYSCALL_DEFINE2(settimeofday, struct compat_timeval __user *, tv,
280 struct timezone __user *, tz)
281{
282 struct timespec64 new_ts;
283 struct timeval user_tv;
284 struct timezone new_tz;
285
286 if (tv) {
287 if (compat_get_timeval(&user_tv, tv))
288 return -EFAULT;
289 new_ts.tv_sec = user_tv.tv_sec;
290 new_ts.tv_nsec = user_tv.tv_usec * NSEC_PER_USEC;
291 }
292 if (tz) {
293 if (copy_from_user(&new_tz, tz, sizeof(*tz)))
294 return -EFAULT;
295 }
296
297 return do_sys_settimeofday64(tv ? &new_ts : NULL, tz ? &new_tz : NULL);
298}
299#endif
300
218SYSCALL_DEFINE1(adjtimex, struct timex __user *, txc_p) 301SYSCALL_DEFINE1(adjtimex, struct timex __user *, txc_p)
219{ 302{
220 struct timex txc; /* Local copy of parameter */ 303 struct timex txc; /* Local copy of parameter */
@@ -224,12 +307,33 @@ SYSCALL_DEFINE1(adjtimex, struct timex __user *, txc_p)
224 * structure. But bear in mind that the structures 307 * structure. But bear in mind that the structures
225 * may change 308 * may change
226 */ 309 */
227 if(copy_from_user(&txc, txc_p, sizeof(struct timex))) 310 if (copy_from_user(&txc, txc_p, sizeof(struct timex)))
228 return -EFAULT; 311 return -EFAULT;
229 ret = do_adjtimex(&txc); 312 ret = do_adjtimex(&txc);
230 return copy_to_user(txc_p, &txc, sizeof(struct timex)) ? -EFAULT : ret; 313 return copy_to_user(txc_p, &txc, sizeof(struct timex)) ? -EFAULT : ret;
231} 314}
232 315
316#ifdef CONFIG_COMPAT
317
318COMPAT_SYSCALL_DEFINE1(adjtimex, struct compat_timex __user *, utp)
319{
320 struct timex txc;
321 int err, ret;
322
323 err = compat_get_timex(&txc, utp);
324 if (err)
325 return err;
326
327 ret = do_adjtimex(&txc);
328
329 err = compat_put_timex(utp, &txc);
330 if (err)
331 return err;
332
333 return ret;
334}
335#endif
336
233/* 337/*
234 * Convert jiffies to milliseconds and back. 338 * Convert jiffies to milliseconds and back.
235 * 339 *