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 24 asmlinkage 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 40 SYS_NI(timer_create); 41 SYS_NI(timer_gettime); 42 SYS_NI(timer_getoverrun); 43 SYS_NI(timer_settime); 44 SYS_NI(timer_delete); 45 SYS_NI(clock_adjtime); 46 SYS_NI(getitimer); 47 SYS_NI(setitimer); 48 #ifdef __ARCH_WANT_SYS_ALARM 49 SYS_NI(alarm); 50 #endif 51 52 /* 53 * We preserve minimal support for CLOCK_REALTIME and CLOCK_MONOTONIC 54 * as it is easy to remain compatible with little code. CLOCK_BOOTTIME 55 * is also included for convenience as at least systemd uses it. 56 */ 57 58 SYSCALL_DEFINE2(clock_settime, const clockid_t, which_clock, 59 const struct __kernel_timespec __user *, tp) 60 { 61 struct timespec64 new_tp; 62 63 if (which_clock != CLOCK_REALTIME) 64 return -EINVAL; 65 if (get_timespec64(&new_tp, tp)) 66 return -EFAULT; 67 68 return do_sys_settimeofday64(&new_tp, NULL); 69 } 70 71 int do_clock_gettime(clockid_t which_clock, struct timespec64 *tp) 72 { 73 switch (which_clock) { 74 case CLOCK_REALTIME: 75 ktime_get_real_ts64(tp); 76 break; 77 case CLOCK_MONOTONIC: 78 ktime_get_ts64(tp); 79 break; 80 case CLOCK_BOOTTIME: 81 ktime_get_boottime_ts64(tp); 82 break; 83 default: 84 return -EINVAL; 85 } 86 87 return 0; 88 } 89 SYSCALL_DEFINE2(clock_gettime, const clockid_t, which_clock, 90 struct __kernel_timespec __user *, tp) 91 { 92 int ret; 93 struct timespec64 kernel_tp; 94 95 ret = do_clock_gettime(which_clock, &kernel_tp); 96 if (ret) 97 return ret; 98 99 if (put_timespec64(&kernel_tp, tp)) 100 return -EFAULT; 101 return 0; 102 } 103 104 SYSCALL_DEFINE2(clock_getres, const clockid_t, which_clock, struct __kernel_timespec __user *, tp) 105 { 106 struct timespec64 rtn_tp = { 107 .tv_sec = 0, 108 .tv_nsec = hrtimer_resolution, 109 }; 110 111 switch (which_clock) { 112 case CLOCK_REALTIME: 113 case CLOCK_MONOTONIC: 114 case CLOCK_BOOTTIME: 115 if (put_timespec64(&rtn_tp, tp)) 116 return -EFAULT; 117 return 0; 118 default: 119 return -EINVAL; 120 } 121 } 122 123 SYSCALL_DEFINE4(clock_nanosleep, const clockid_t, which_clock, int, flags, 124 const struct __kernel_timespec __user *, rqtp, 125 struct __kernel_timespec __user *, rmtp) 126 { 127 struct timespec64 t; 128 129 switch (which_clock) { 130 case CLOCK_REALTIME: 131 case CLOCK_MONOTONIC: 132 case CLOCK_BOOTTIME: 133 break; 134 default: 135 return -EINVAL; 136 } 137 138 if (get_timespec64(&t, rqtp)) 139 return -EFAULT; 140 if (!timespec64_valid(&t)) 141 return -EINVAL; 142 if (flags & TIMER_ABSTIME) 143 rmtp = NULL; 144 current->restart_block.nanosleep.type = rmtp ? TT_NATIVE : TT_NONE; 145 current->restart_block.nanosleep.rmtp = rmtp; 146 return hrtimer_nanosleep(&t, flags & TIMER_ABSTIME ? 147 HRTIMER_MODE_ABS : HRTIMER_MODE_REL, 148 which_clock); 149 } 150 151 #ifdef CONFIG_COMPAT 152 COMPAT_SYS_NI(timer_create); 153 COMPAT_SYS_NI(clock_adjtime); 154 COMPAT_SYS_NI(timer_settime); 155 COMPAT_SYS_NI(timer_gettime); 156 COMPAT_SYS_NI(getitimer); 157 COMPAT_SYS_NI(setitimer); 158 #endif 159 160 #ifdef CONFIG_COMPAT_32BIT_TIME 161 COMPAT_SYSCALL_DEFINE2(clock_settime, const clockid_t, which_clock, 162 struct old_timespec32 __user *, tp) 163 { 164 struct timespec64 new_tp; 165 166 if (which_clock != CLOCK_REALTIME) 167 return -EINVAL; 168 if (get_old_timespec32(&new_tp, tp)) 169 return -EFAULT; 170 171 return do_sys_settimeofday64(&new_tp, NULL); 172 } 173 174 COMPAT_SYSCALL_DEFINE2(clock_gettime, clockid_t, which_clock, 175 struct old_timespec32 __user *, tp) 176 { 177 int ret; 178 struct timespec64 kernel_tp; 179 180 ret = do_clock_gettime(which_clock, &kernel_tp); 181 if (ret) 182 return ret; 183 184 if (put_old_timespec32(&kernel_tp, tp)) 185 return -EFAULT; 186 return 0; 187 } 188 189 COMPAT_SYSCALL_DEFINE2(clock_getres, clockid_t, which_clock, 190 struct old_timespec32 __user *, tp) 191 { 192 struct timespec64 rtn_tp = { 193 .tv_sec = 0, 194 .tv_nsec = hrtimer_resolution, 195 }; 196 197 switch (which_clock) { 198 case CLOCK_REALTIME: 199 case CLOCK_MONOTONIC: 200 case CLOCK_BOOTTIME: 201 if (put_old_timespec32(&rtn_tp, tp)) 202 return -EFAULT; 203 return 0; 204 default: 205 return -EINVAL; 206 } 207 } 208 209 COMPAT_SYSCALL_DEFINE4(clock_nanosleep, clockid_t, which_clock, int, flags, 210 struct old_timespec32 __user *, rqtp, 211 struct old_timespec32 __user *, rmtp) 212 { 213 struct timespec64 t; 214 215 switch (which_clock) { 216 case CLOCK_REALTIME: 217 case CLOCK_MONOTONIC: 218 case CLOCK_BOOTTIME: 219 break; 220 default: 221 return -EINVAL; 222 } 223 224 if (get_old_timespec32(&t, rqtp)) 225 return -EFAULT; 226 if (!timespec64_valid(&t)) 227 return -EINVAL; 228 if (flags & TIMER_ABSTIME) 229 rmtp = NULL; 230 current->restart_block.nanosleep.type = rmtp ? TT_COMPAT : TT_NONE; 231 current->restart_block.nanosleep.compat_rmtp = rmtp; 232 return hrtimer_nanosleep(&t, flags & TIMER_ABSTIME ? 233 HRTIMER_MODE_ABS : HRTIMER_MODE_REL, 234 which_clock); 235 } 236 #endif 237