Linux Audio

Check our new training course

Loading...
Note: File does not exist in v3.5.6.
  1// SPDX-License-Identifier: GPL-2.0
  2/*
  3 * Dummy stubs used when CONFIG_POSIX_TIMERS=n
  4 *
  5 * Created by:  Nicolas Pitre, July 2016
  6 * Copyright:   (C) 2016 Linaro Limited
  7 */
  8
  9#include <linux/linkage.h>
 10#include <linux/kernel.h>
 11#include <linux/sched.h>
 12#include <linux/errno.h>
 13#include <linux/syscalls.h>
 14#include <linux/ktime.h>
 15#include <linux/timekeeping.h>
 16#include <linux/posix-timers.h>
 17#include <linux/compat.h>
 18
 19#ifdef CONFIG_ARCH_HAS_SYSCALL_WRAPPER
 20/* Architectures may override SYS_NI and COMPAT_SYS_NI */
 21#include <asm/syscall_wrapper.h>
 22#endif
 23
 24asmlinkage long sys_ni_posix_timers(void)
 25{
 26	pr_err_once("process %d (%s) attempted a POSIX timer syscall "
 27		    "while CONFIG_POSIX_TIMERS is not set\n",
 28		    current->pid, current->comm);
 29	return -ENOSYS;
 30}
 31
 32#ifndef SYS_NI
 33#define SYS_NI(name)  SYSCALL_ALIAS(sys_##name, sys_ni_posix_timers)
 34#endif
 35
 36#ifndef COMPAT_SYS_NI
 37#define COMPAT_SYS_NI(name)  SYSCALL_ALIAS(compat_sys_##name, sys_ni_posix_timers)
 38#endif
 39
 40SYS_NI(timer_create);
 41SYS_NI(timer_gettime);
 42SYS_NI(timer_getoverrun);
 43SYS_NI(timer_settime);
 44SYS_NI(timer_delete);
 45SYS_NI(clock_adjtime);
 46SYS_NI(getitimer);
 47SYS_NI(setitimer);
 48SYS_NI(clock_adjtime32);
 49#ifdef __ARCH_WANT_SYS_ALARM
 50SYS_NI(alarm);
 51#endif
 52
 53/*
 54 * We preserve minimal support for CLOCK_REALTIME and CLOCK_MONOTONIC
 55 * as it is easy to remain compatible with little code. CLOCK_BOOTTIME
 56 * is also included for convenience as at least systemd uses it.
 57 */
 58
 59SYSCALL_DEFINE2(clock_settime, const clockid_t, which_clock,
 60		const struct __kernel_timespec __user *, tp)
 61{
 62	struct timespec64 new_tp;
 63
 64	if (which_clock != CLOCK_REALTIME)
 65		return -EINVAL;
 66	if (get_timespec64(&new_tp, tp))
 67		return -EFAULT;
 68
 69	return do_sys_settimeofday64(&new_tp, NULL);
 70}
 71
 72int do_clock_gettime(clockid_t which_clock, struct timespec64 *tp)
 73{
 74	switch (which_clock) {
 75	case CLOCK_REALTIME:
 76		ktime_get_real_ts64(tp);
 77		break;
 78	case CLOCK_MONOTONIC:
 79		ktime_get_ts64(tp);
 80		break;
 81	case CLOCK_BOOTTIME:
 82		ktime_get_boottime_ts64(tp);
 83		break;
 84	default:
 85		return -EINVAL;
 86	}
 87
 88	return 0;
 89}
 90SYSCALL_DEFINE2(clock_gettime, const clockid_t, which_clock,
 91		struct __kernel_timespec __user *, tp)
 92{
 93	int ret;
 94	struct timespec64 kernel_tp;
 95
 96	ret = do_clock_gettime(which_clock, &kernel_tp);
 97	if (ret)
 98		return ret;
 99
100	if (put_timespec64(&kernel_tp, tp))
101		return -EFAULT;
102	return 0;
103}
104
105SYSCALL_DEFINE2(clock_getres, const clockid_t, which_clock, struct __kernel_timespec __user *, tp)
106{
107	struct timespec64 rtn_tp = {
108		.tv_sec = 0,
109		.tv_nsec = hrtimer_resolution,
110	};
111
112	switch (which_clock) {
113	case CLOCK_REALTIME:
114	case CLOCK_MONOTONIC:
115	case CLOCK_BOOTTIME:
116		if (put_timespec64(&rtn_tp, tp))
117			return -EFAULT;
118		return 0;
119	default:
120		return -EINVAL;
121	}
122}
123
124SYSCALL_DEFINE4(clock_nanosleep, const clockid_t, which_clock, int, flags,
125		const struct __kernel_timespec __user *, rqtp,
126		struct __kernel_timespec __user *, rmtp)
127{
128	struct timespec64 t;
129
130	switch (which_clock) {
131	case CLOCK_REALTIME:
132	case CLOCK_MONOTONIC:
133	case CLOCK_BOOTTIME:
134		break;
135	default:
136		return -EINVAL;
137	}
138
139	if (get_timespec64(&t, rqtp))
140		return -EFAULT;
141	if (!timespec64_valid(&t))
142		return -EINVAL;
143	if (flags & TIMER_ABSTIME)
144		rmtp = NULL;
145	current->restart_block.nanosleep.type = rmtp ? TT_NATIVE : TT_NONE;
146	current->restart_block.nanosleep.rmtp = rmtp;
147	return hrtimer_nanosleep(&t, flags & TIMER_ABSTIME ?
148				 HRTIMER_MODE_ABS : HRTIMER_MODE_REL,
149				 which_clock);
150}
151
152#ifdef CONFIG_COMPAT
153COMPAT_SYS_NI(timer_create);
154COMPAT_SYS_NI(getitimer);
155COMPAT_SYS_NI(setitimer);
156#endif
157
158#ifdef CONFIG_COMPAT_32BIT_TIME
159SYS_NI(timer_settime32);
160SYS_NI(timer_gettime32);
161
162SYSCALL_DEFINE2(clock_settime32, const clockid_t, which_clock,
163		struct old_timespec32 __user *, tp)
164{
165	struct timespec64 new_tp;
166
167	if (which_clock != CLOCK_REALTIME)
168		return -EINVAL;
169	if (get_old_timespec32(&new_tp, tp))
170		return -EFAULT;
171
172	return do_sys_settimeofday64(&new_tp, NULL);
173}
174
175SYSCALL_DEFINE2(clock_gettime32, clockid_t, which_clock,
176		struct old_timespec32 __user *, tp)
177{
178	int ret;
179	struct timespec64 kernel_tp;
180
181	ret = do_clock_gettime(which_clock, &kernel_tp);
182	if (ret)
183		return ret;
184
185	if (put_old_timespec32(&kernel_tp, tp))
186		return -EFAULT;
187	return 0;
188}
189
190SYSCALL_DEFINE2(clock_getres_time32, clockid_t, which_clock,
191		struct old_timespec32 __user *, tp)
192{
193	struct timespec64 rtn_tp = {
194		.tv_sec = 0,
195		.tv_nsec = hrtimer_resolution,
196	};
197
198	switch (which_clock) {
199	case CLOCK_REALTIME:
200	case CLOCK_MONOTONIC:
201	case CLOCK_BOOTTIME:
202		if (put_old_timespec32(&rtn_tp, tp))
203			return -EFAULT;
204		return 0;
205	default:
206		return -EINVAL;
207	}
208}
209
210SYSCALL_DEFINE4(clock_nanosleep_time32, clockid_t, which_clock, int, flags,
211		struct old_timespec32 __user *, rqtp,
212		struct old_timespec32 __user *, rmtp)
213{
214	struct timespec64 t;
215
216	switch (which_clock) {
217	case CLOCK_REALTIME:
218	case CLOCK_MONOTONIC:
219	case CLOCK_BOOTTIME:
220		break;
221	default:
222		return -EINVAL;
223	}
224
225	if (get_old_timespec32(&t, rqtp))
226		return -EFAULT;
227	if (!timespec64_valid(&t))
228		return -EINVAL;
229	if (flags & TIMER_ABSTIME)
230		rmtp = NULL;
231	current->restart_block.nanosleep.type = rmtp ? TT_COMPAT : TT_NONE;
232	current->restart_block.nanosleep.compat_rmtp = rmtp;
233	return hrtimer_nanosleep(&t, flags & TIMER_ABSTIME ?
234				 HRTIMER_MODE_ABS : HRTIMER_MODE_REL,
235				 which_clock);
236}
237#endif