Message ID | alpine.LFD.2.20.1609142340540.14769@knanqh.ubzr |
---|---|
State | Superseded |
Headers | show |
On Wed, Sep 14, 2016 at 8:47 PM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote: > Many embedded systems typically don't need them. This removes about > 22KB from the kernel binary size on ARM when configured out. > > Corresponding syscalls are routed to a stub logging the attempt to > use those syscalls which should be enough of a clue if they were > disabled without proper consideration. They are: timer_create, > timer_gettime: timer_getoverrun, timer_settime, timer_delete, > clock_adjtime. > > The clock_settime, clock_gettime, clock_getres and clock_nanosleep syscalls > are replaced by simple wrappers compatible with CLOCK_REALTIME, > CLOCK_MONOTONIC and CLOCK_BOOTTIME only. Thanks for re-sending. I'm happier that you're keeping some basic functionality here. No real objections at this point. I need to apply it for testing and take a closer look, but its on my to-queue list. However, with an upcoming conference, as being a little later in the cycle I can't promise it will make it for the 4.9 merge window. But we'll see. thanks! -john
On Thu, 15 Sep 2016, John Stultz wrote: > On Wed, Sep 14, 2016 at 8:47 PM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote: > > Many embedded systems typically don't need them. This removes about > > 22KB from the kernel binary size on ARM when configured out. > > > > Corresponding syscalls are routed to a stub logging the attempt to > > use those syscalls which should be enough of a clue if they were > > disabled without proper consideration. They are: timer_create, > > timer_gettime: timer_getoverrun, timer_settime, timer_delete, > > clock_adjtime. > > > > The clock_settime, clock_gettime, clock_getres and clock_nanosleep syscalls > > are replaced by simple wrappers compatible with CLOCK_REALTIME, > > CLOCK_MONOTONIC and CLOCK_BOOTTIME only. > > Thanks for re-sending. I'm happier that you're keeping some basic > functionality here. No real objections at this point. > > I need to apply it for testing and take a closer look, but its on my > to-queue list. However, with an upcoming conference, as being a little > later in the cycle I can't promise it will make it for the 4.9 merge > window. But we'll see. Thanks. I'll buy you a beer in 2 weeks. :-) Nicolas
> diff --git a/kernel/time/Kconfig b/kernel/time/Kconfig > index 62824f2fe4..62504a2c9f 100644 > --- a/kernel/time/Kconfig > +++ b/kernel/time/Kconfig > @@ -195,3 +195,21 @@ config HIGH_RES_TIMERS > > endmenu > endif > + > +config POSIX_TIMERS > + bool "Posix Clocks & timers" if EMBEDDED > + default y > + help > + This includes native support for POSIX timers to the kernel. > + Most embedded systems may have no use for them and therefore they > + can be configured out to reduce the size of the kernel image. > + > + When this option is disabled, the following syscalls won't be > + available: timer_create, timer_gettime: timer_getoverrun, > + timer_settime, timer_delete, clock_adjtime. Furthermore, the > + clock_settime, clock_gettime, clock_getres and clock_nanosleep > + syscalls will be limited to CLOCK_REALTIME and CLOCK_MONOTONIC > + only. > + > + If unsure say y. > One thought.. Should this go under: Configure standard kernel features (expert users) rather then a top level item under General Setup ? thanks -john
On Thu, 15 Sep 2016, John Stultz wrote: > > diff --git a/kernel/time/Kconfig b/kernel/time/Kconfig > > index 62824f2fe4..62504a2c9f 100644 > > --- a/kernel/time/Kconfig > > +++ b/kernel/time/Kconfig > > @@ -195,3 +195,21 @@ config HIGH_RES_TIMERS > > > > endmenu > > endif > > + > > +config POSIX_TIMERS > > + bool "Posix Clocks & timers" if EMBEDDED > > + default y > > + help > > + This includes native support for POSIX timers to the kernel. > > + Most embedded systems may have no use for them and therefore they > > + can be configured out to reduce the size of the kernel image. > > + > > + When this option is disabled, the following syscalls won't be > > + available: timer_create, timer_gettime: timer_getoverrun, > > + timer_settime, timer_delete, clock_adjtime. Furthermore, the > > + clock_settime, clock_gettime, clock_getres and clock_nanosleep > > + syscalls will be limited to CLOCK_REALTIME and CLOCK_MONOTONIC > > + only. > > + > > + If unsure say y. > > > > One thought.. Should this go under: > Configure standard kernel features (expert users) > rather then a top level item under General Setup ? Hmmm... probably yes. Do you need that I repost the patch? Nicolas
On Thu, Sep 15, 2016 at 11:28 AM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote: > On Thu, 15 Sep 2016, John Stultz wrote: > >> > diff --git a/kernel/time/Kconfig b/kernel/time/Kconfig >> > index 62824f2fe4..62504a2c9f 100644 >> > --- a/kernel/time/Kconfig >> > +++ b/kernel/time/Kconfig >> > @@ -195,3 +195,21 @@ config HIGH_RES_TIMERS >> > >> > endmenu >> > endif >> > + >> > +config POSIX_TIMERS >> > + bool "Posix Clocks & timers" if EMBEDDED >> > + default y >> > + help >> > + This includes native support for POSIX timers to the kernel. >> > + Most embedded systems may have no use for them and therefore they >> > + can be configured out to reduce the size of the kernel image. >> > + >> > + When this option is disabled, the following syscalls won't be >> > + available: timer_create, timer_gettime: timer_getoverrun, >> > + timer_settime, timer_delete, clock_adjtime. Furthermore, the >> > + clock_settime, clock_gettime, clock_getres and clock_nanosleep >> > + syscalls will be limited to CLOCK_REALTIME and CLOCK_MONOTONIC >> > + only. >> > + >> > + If unsure say y. >> > >> >> One thought.. Should this go under: >> Configure standard kernel features (expert users) >> rather then a top level item under General Setup ? > > Hmmm... probably yes. > > Do you need that I repost the patch? I can see about moving it.. thanks -john
On Thu, 15 Sep 2016, John Stultz wrote: > On Thu, Sep 15, 2016 at 11:28 AM, Nicolas Pitre > <nicolas.pitre@linaro.org> wrote: > > On Thu, 15 Sep 2016, John Stultz wrote: > > > >> > diff --git a/kernel/time/Kconfig b/kernel/time/Kconfig > >> > index 62824f2fe4..62504a2c9f 100644 > >> > --- a/kernel/time/Kconfig > >> > +++ b/kernel/time/Kconfig > >> > @@ -195,3 +195,21 @@ config HIGH_RES_TIMERS > >> > > >> > endmenu > >> > endif > >> > + > >> > +config POSIX_TIMERS > >> > + bool "Posix Clocks & timers" if EMBEDDED > >> > + default y > >> > + help > >> > + This includes native support for POSIX timers to the kernel. > >> > + Most embedded systems may have no use for them and therefore they > >> > + can be configured out to reduce the size of the kernel image. > >> > + > >> > + When this option is disabled, the following syscalls won't be > >> > + available: timer_create, timer_gettime: timer_getoverrun, > >> > + timer_settime, timer_delete, clock_adjtime. Furthermore, the > >> > + clock_settime, clock_gettime, clock_getres and clock_nanosleep > >> > + syscalls will be limited to CLOCK_REALTIME and CLOCK_MONOTONIC > >> > + only. > >> > + > >> > + If unsure say y. > >> > > >> > >> One thought.. Should this go under: > >> Configure standard kernel features (expert users) > >> rather then a top level item under General Setup ? > > > > Hmmm... probably yes. > > > > Do you need that I repost the patch? > > I can see about moving it.. OK. Making it conditional on EXPERT rather than EMBEDDED would also be more inline with the other similar options there. Nicolas
On Thu, Sep 15, 2016 at 11:37 AM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote: > On Thu, 15 Sep 2016, John Stultz wrote: > >> On Thu, Sep 15, 2016 at 11:28 AM, Nicolas Pitre >> <nicolas.pitre@linaro.org> wrote: >> > On Thu, 15 Sep 2016, John Stultz wrote: >> > >> >> > diff --git a/kernel/time/Kconfig b/kernel/time/Kconfig >> >> > index 62824f2fe4..62504a2c9f 100644 >> >> > --- a/kernel/time/Kconfig >> >> > +++ b/kernel/time/Kconfig >> >> > @@ -195,3 +195,21 @@ config HIGH_RES_TIMERS >> >> > >> >> > endmenu >> >> > endif >> >> > + >> >> > +config POSIX_TIMERS >> >> > + bool "Posix Clocks & timers" if EMBEDDED >> >> > + default y >> >> > + help >> >> > + This includes native support for POSIX timers to the kernel. >> >> > + Most embedded systems may have no use for them and therefore they >> >> > + can be configured out to reduce the size of the kernel image. >> >> > + >> >> > + When this option is disabled, the following syscalls won't be >> >> > + available: timer_create, timer_gettime: timer_getoverrun, >> >> > + timer_settime, timer_delete, clock_adjtime. Furthermore, the >> >> > + clock_settime, clock_gettime, clock_getres and clock_nanosleep >> >> > + syscalls will be limited to CLOCK_REALTIME and CLOCK_MONOTONIC >> >> > + only. >> >> > + >> >> > + If unsure say y. >> >> > >> >> >> >> One thought.. Should this go under: >> >> Configure standard kernel features (expert users) >> >> rather then a top level item under General Setup ? >> > >> > Hmmm... probably yes. >> > >> > Do you need that I repost the patch? >> >> I can see about moving it.. > > OK. > > Making it conditional on EXPERT rather than EMBEDDED would also be more > inline with the other similar options there. Ack. Although I'm also seeing some Kconfig noise when I disable it: warning: (SFC && TILE_NET && AMD_XGBE && BFIN_MAC_USE_HWSTAMP && TIGON3 && BNX2X && LIQUIDIO && FEC && E1000E && IGB && IXGBE && I40E && FM10K && MLX4_EN && MLX5_CORE_EN && RAVB && SXGBE_ETH && STMMAC_ETH && TI_CPTS && PTP_1588_CLOCK_GIANFAR && PTP_1588_CLOCK_IXP46X && DP83640_PHY && PTP_1588_CLOCK_PCH) selects PTP_1588_CLOCK which has unmet direct dependencies (NET && POSIX_TIMERS) warning: (SFC && TILE_NET && AMD_XGBE && BFIN_MAC_USE_HWSTAMP && TIGON3 && BNX2X && LIQUIDIO && FEC && E1000E && IGB && IXGBE && I40E && FM10K && MLX4_EN && MLX5_CORE_EN && RAVB && SXGBE_ETH && STMMAC_ETH && TI_CPTS && PTP_1588_CLOCK_GIANFAR && PTP_1588_CLOCK_IXP46X && DP83640_PHY && PTP_1588_CLOCK_PCH) selects PTP_1588_CLOCK which has unmet direct dependencies (NET && POSIX_TIMERS) Not sure if this is just expected given we can't do reverse dependency checking on select... Maybe PTP_1588_CLOCK needs to select POSIX_TIMERS instead of just depend on it? thanks -john
diff --git a/drivers/ptp/Kconfig b/drivers/ptp/Kconfig index ee3de3421f..00e6098e9a 100644 --- a/drivers/ptp/Kconfig +++ b/drivers/ptp/Kconfig @@ -6,7 +6,7 @@ menu "PTP clock support" config PTP_1588_CLOCK tristate "PTP clock support" - depends on NET + depends on NET && POSIX_TIMERS select PPS select NET_PTP_CLASSIFY help diff --git a/include/linux/posix-timers.h b/include/linux/posix-timers.h index 62d44c1760..2288c5c557 100644 --- a/include/linux/posix-timers.h +++ b/include/linux/posix-timers.h @@ -118,6 +118,8 @@ struct k_clock { extern struct k_clock clock_posix_cpu; extern struct k_clock clock_posix_dynamic; +#ifdef CONFIG_POSIX_TIMERS + void posix_timers_register_clock(const clockid_t clock_id, struct k_clock *new_clock); /* function to call to trigger timer event */ @@ -131,8 +133,30 @@ void posix_cpu_timers_exit_group(struct task_struct *task); void set_process_cpu_timer(struct task_struct *task, unsigned int clock_idx, cputime_t *newval, cputime_t *oldval); -long clock_nanosleep_restart(struct restart_block *restart_block); - void update_rlimit_cpu(struct task_struct *task, unsigned long rlim_new); +#else + +#include <linux/random.h> + +static inline void posix_timers_register_clock(const clockid_t clock_id, + struct k_clock *new_clock) {} +static inline int posix_timer_event(struct k_itimer *timr, int si_private) +{ return 0; } +static inline void run_posix_cpu_timers(struct task_struct *task) {} +static inline void posix_cpu_timers_exit(struct task_struct *task) +{ + add_device_randomness((const void*) &task->se.sum_exec_runtime, + sizeof(unsigned long long)); +} +static inline void posix_cpu_timers_exit_group(struct task_struct *task) {} +static inline void set_process_cpu_timer(struct task_struct *task, + unsigned int clock_idx, cputime_t *newval, cputime_t *oldval) {} +static inline void update_rlimit_cpu(struct task_struct *task, + unsigned long rlim_new) {} + +#endif + +long clock_nanosleep_restart(struct restart_block *restart_block); + #endif diff --git a/include/linux/sched.h b/include/linux/sched.h index 54182d52a0..39a1d6d3f5 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -2924,8 +2924,13 @@ static inline void exit_thread(struct task_struct *tsk) extern void exit_files(struct task_struct *); extern void __cleanup_sighand(struct sighand_struct *); +#ifdef CONFIG_POSIX_TIMERS extern void exit_itimers(struct signal_struct *); extern void flush_itimer_signals(void); +#else +static inline void exit_itimers(struct signal_struct *s) {} +static inline void flush_itimer_signals(void) {} +#endif extern void do_group_exit(int); @@ -3382,7 +3387,12 @@ static __always_inline bool need_resched(void) * Thread group CPU time accounting. */ void thread_group_cputime(struct task_struct *tsk, struct task_cputime *times); +#ifdef CONFIG_POSIX_TIMERS void thread_group_cputimer(struct task_struct *tsk, struct task_cputime *times); +#else +static inline void thread_group_cputimer(struct task_struct *tsk, + struct task_cputime *times) {} +#endif /* * Reevaluate whether the task has signals pending delivery. diff --git a/kernel/signal.c b/kernel/signal.c index af21afc00d..ea75065e29 100644 --- a/kernel/signal.c +++ b/kernel/signal.c @@ -427,6 +427,7 @@ void flush_signals(struct task_struct *t) spin_unlock_irqrestore(&t->sighand->siglock, flags); } +#ifdef CONFIG_POSIX_TIMERS static void __flush_itimer_signals(struct sigpending *pending) { sigset_t signal, retain; @@ -460,6 +461,7 @@ void flush_itimer_signals(void) __flush_itimer_signals(&tsk->signal->shared_pending); spin_unlock_irqrestore(&tsk->sighand->siglock, flags); } +#endif void ignore_signals(struct task_struct *t) { @@ -611,6 +613,7 @@ int dequeue_signal(struct task_struct *tsk, sigset_t *mask, siginfo_t *info) */ current->jobctl |= JOBCTL_STOP_DEQUEUED; } +#ifdef CONFIG_POSIX_TIMERS if ((info->si_code & __SI_MASK) == __SI_TIMER && info->si_sys_private) { /* * Release the siglock to ensure proper locking order @@ -622,6 +625,7 @@ int dequeue_signal(struct task_struct *tsk, sigset_t *mask, siginfo_t *info) do_schedule_next_timer(info); spin_lock(&tsk->sighand->siglock); } +#endif return signr; } diff --git a/kernel/time/Kconfig b/kernel/time/Kconfig index 62824f2fe4..62504a2c9f 100644 --- a/kernel/time/Kconfig +++ b/kernel/time/Kconfig @@ -195,3 +195,21 @@ config HIGH_RES_TIMERS endmenu endif + +config POSIX_TIMERS + bool "Posix Clocks & timers" if EMBEDDED + default y + help + This includes native support for POSIX timers to the kernel. + Most embedded systems may have no use for them and therefore they + can be configured out to reduce the size of the kernel image. + + When this option is disabled, the following syscalls won't be + available: timer_create, timer_gettime: timer_getoverrun, + timer_settime, timer_delete, clock_adjtime. Furthermore, the + clock_settime, clock_gettime, clock_getres and clock_nanosleep + syscalls will be limited to CLOCK_REALTIME and CLOCK_MONOTONIC + only. + + If unsure say y. + diff --git a/kernel/time/Makefile b/kernel/time/Makefile index 49eca0beed..fc26c308f5 100644 --- a/kernel/time/Makefile +++ b/kernel/time/Makefile @@ -1,6 +1,12 @@ -obj-y += time.o timer.o hrtimer.o itimer.o posix-timers.o posix-cpu-timers.o +obj-y += time.o timer.o hrtimer.o itimer.o obj-y += timekeeping.o ntp.o clocksource.o jiffies.o timer_list.o -obj-y += timeconv.o timecounter.o posix-clock.o alarmtimer.o +obj-y += timeconv.o timecounter.o alarmtimer.o + +ifeq ($(CONFIG_POSIX_TIMERS),y) + obj-y += posix-timers.o posix-cpu-timers.o posix-clock.o +else + obj-y += posix-stubs.o +endif obj-$(CONFIG_GENERIC_CLOCKEVENTS) += clockevents.o tick-common.o ifeq ($(CONFIG_GENERIC_CLOCKEVENTS_BROADCAST),y) diff --git a/kernel/time/posix-stubs.c b/kernel/time/posix-stubs.c new file mode 100644 index 0000000000..fe857bd4a0 --- /dev/null +++ b/kernel/time/posix-stubs.c @@ -0,0 +1,118 @@ +/* + * Dummy stubs used when CONFIG_POSIX_TIMERS=n + * + * Created by: Nicolas Pitre, July 2016 + * Copyright: (C) 2016 Linaro Limited + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + */ + +#include <linux/linkage.h> +#include <linux/kernel.h> +#include <linux/sched.h> +#include <linux/errno.h> +#include <linux/syscalls.h> +#include <linux/ktime.h> +#include <linux/timekeeping.h> +#include <linux/posix-timers.h> + +asmlinkage long sys_ni_posix_timers(void) +{ + pr_err_once("process %d (%s) attempted a POSIX timer syscall " + "while CONFIG_POSIX_TIMERS is not set\n", + current->pid, current->comm); + return -ENOSYS; +} + +#define SYS_NI(name) SYSCALL_ALIAS(sys_##name, sys_ni_posix_timers) + +SYS_NI(timer_create); +SYS_NI(timer_gettime); +SYS_NI(timer_getoverrun); +SYS_NI(timer_settime); +SYS_NI(timer_delete); +SYS_NI(clock_adjtime); + +/* + * We preserve minimal support for CLOCK_REALTIME and CLOCK_MONOTONIC + * as it is easy to remain compatible with little code. CLOCK_BOOTTIME + * is also included for convenience as at least systemd uses it. + */ + +SYSCALL_DEFINE2(clock_settime, const clockid_t, which_clock, + const struct timespec __user *, tp) +{ + struct timespec new_tp; + + if (which_clock != CLOCK_REALTIME) + return -EINVAL; + if (copy_from_user(&new_tp, tp, sizeof (*tp))) + return -EFAULT; + return do_sys_settimeofday(&new_tp, NULL); +} + +SYSCALL_DEFINE2(clock_gettime, const clockid_t, which_clock, + struct timespec __user *,tp) +{ + struct timespec kernel_tp; + + switch (which_clock) { + case CLOCK_REALTIME: ktime_get_real_ts(&kernel_tp); break; + case CLOCK_MONOTONIC: ktime_get_ts(&kernel_tp); break; + case CLOCK_BOOTTIME: get_monotonic_boottime(&kernel_tp); break; + default: return -EINVAL; + } + if (copy_to_user(tp, &kernel_tp, sizeof (kernel_tp))) + return -EFAULT; + return 0; +} + +SYSCALL_DEFINE2(clock_getres, const clockid_t, which_clock, struct timespec __user *, tp) +{ + struct timespec rtn_tp = { + .tv_sec = 0, + .tv_nsec = hrtimer_resolution, + }; + + switch (which_clock) { + case CLOCK_REALTIME: + case CLOCK_MONOTONIC: + case CLOCK_BOOTTIME: + if (copy_to_user(tp, &rtn_tp, sizeof(rtn_tp))) + return -EFAULT; + return 0; + default: + return -EINVAL; + } +} + +SYSCALL_DEFINE4(clock_nanosleep, const clockid_t, which_clock, int, flags, + const struct timespec __user *, rqtp, + struct timespec __user *, rmtp) +{ + struct timespec t; + + switch (which_clock) { + case CLOCK_REALTIME: + case CLOCK_MONOTONIC: + case CLOCK_BOOTTIME: + if (copy_from_user(&t, rqtp, sizeof (struct timespec))) + return -EFAULT; + if (!timespec_valid(&t)) + return -EINVAL; + return hrtimer_nanosleep(&t, rmtp, flags & TIMER_ABSTIME ? + HRTIMER_MODE_ABS : HRTIMER_MODE_REL, + which_clock); + default: + return -EINVAL; + } +} + +#ifdef CONFIG_COMPAT +long clock_nanosleep_restart(struct restart_block *restart_block) +{ + return hrtimer_nanosleep_restart(restart_block); +} +#endif
Many embedded systems typically don't need them. This removes about 22KB from the kernel binary size on ARM when configured out. Corresponding syscalls are routed to a stub logging the attempt to use those syscalls which should be enough of a clue if they were disabled without proper consideration. They are: timer_create, timer_gettime: timer_getoverrun, timer_settime, timer_delete, clock_adjtime. The clock_settime, clock_gettime, clock_getres and clock_nanosleep syscalls are replaced by simple wrappers compatible with CLOCK_REALTIME, CLOCK_MONOTONIC and CLOCK_BOOTTIME only. Signed-off-by: Nicolas Pitre <nico@linaro.org> --- Changes from v2: - Fix compilation with CONFIG_COMPAT=y due to missing clock_nanosleep_restart(), found by kbuild test robot. Changes from RFC/v1: - Stubbed-out functions moved to static inlines. - The timer signal handling code is now removed. - The list of removed syscalls is explicitly documented. - The clock_settime, clock_gettime, clock_getres and clock_nanosleep syscalls are minimally preserved as this required very little code. I'm now able to boot a copy of Fedora 21 with this patch and CONFIG_POSIX_TIMERS=n with no apparent issues.