linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] omit POSIX timer stuff from task_struct when disabled
@ 2017-01-09 18:49 Nicolas Pitre
  2017-01-20 22:32 ` John Stultz
  0 siblings, 1 reply; 5+ messages in thread
From: Nicolas Pitre @ 2017-01-09 18:49 UTC (permalink / raw)
  To: Thomas Gleixner; +Cc: John Stultz, linux-kernel

When CONFIG_POSIX_TIMERS is disabled, it is preferable to remove related
structures from struct task_struct and struct signal_struct as they
won't contain anything useful and shouldn't be relied upon by mistake.
Code still referencing those structures is also disabled here.

Signed-off-by: Nicolas Pitre <nico@linaro.org>

diff --git a/fs/proc/base.c b/fs/proc/base.c
index 8e7e61b28f..03deeac1e8 100644
--- a/fs/proc/base.c
+++ b/fs/proc/base.c
@@ -2179,7 +2179,7 @@ static const struct file_operations proc_map_files_operations = {
 	.llseek		= generic_file_llseek,
 };
 
-#ifdef CONFIG_CHECKPOINT_RESTORE
+#if defined(CONFIG_CHECKPOINT_RESTORE) && defined(CONFIG_POSIX_TIMERS)
 struct timers_private {
 	struct pid *pid;
 	struct task_struct *task;
@@ -2936,7 +2936,7 @@ static const struct pid_entry tgid_base_stuff[] = {
 	REG("projid_map", S_IRUGO|S_IWUSR, proc_projid_map_operations),
 	REG("setgroups",  S_IRUGO|S_IWUSR, proc_setgroups_operations),
 #endif
-#ifdef CONFIG_CHECKPOINT_RESTORE
+#if defined(CONFIG_CHECKPOINT_RESTORE) && defined(CONFIG_POSIX_TIMERS)
 	REG("timers",	  S_IRUGO, proc_timers_operations),
 #endif
 	REG("timerslack_ns", S_IRUGO|S_IWUGO, proc_pid_set_timerslack_ns_operations),
diff --git a/include/linux/init_task.h b/include/linux/init_task.h
index 325f649d77..3a85d61f76 100644
--- a/include/linux/init_task.h
+++ b/include/linux/init_task.h
@@ -42,6 +42,27 @@ extern struct fs_struct init_fs;
 #define INIT_PREV_CPUTIME(x)
 #endif
 
+#ifdef CONFIG_POSIX_TIMERS
+#define INIT_POSIX_TIMERS(s)						\
+	.posix_timers = LIST_HEAD_INIT(s.posix_timers),
+#define INIT_CPU_TIMERS(s)						\
+	.cpu_timers = {							\
+		LIST_HEAD_INIT(s.cpu_timers[0]),			\
+		LIST_HEAD_INIT(s.cpu_timers[1]),			\
+		LIST_HEAD_INIT(s.cpu_timers[2]),								\
+	},
+#define INIT_CPUTIMER(s)						\
+	.cputimer	= { 						\
+		.cputime_atomic	= INIT_CPUTIME_ATOMIC,			\
+		.running	= false,				\
+		.checking_timer = false,				\
+	},
+#else
+#define INIT_POSIX_TIMERS(s)
+#define INIT_CPU_TIMERS(s)
+#define INIT_CPUTIMER(s)
+#endif
+
 #define INIT_SIGNALS(sig) {						\
 	.nr_threads	= 1,						\
 	.thread_head	= LIST_HEAD_INIT(init_task.thread_node),	\
@@ -49,14 +70,10 @@ extern struct fs_struct init_fs;
 	.shared_pending	= { 						\
 		.list = LIST_HEAD_INIT(sig.shared_pending.list),	\
 		.signal =  {{0}}},					\
-	.posix_timers	 = LIST_HEAD_INIT(sig.posix_timers),		\
-	.cpu_timers	= INIT_CPU_TIMERS(sig.cpu_timers),		\
+	INIT_POSIX_TIMERS(sig)						\
+	INIT_CPU_TIMERS(sig)						\
 	.rlim		= INIT_RLIMITS,					\
-	.cputimer	= { 						\
-		.cputime_atomic	= INIT_CPUTIME_ATOMIC,			\
-		.running	= false,				\
-		.checking_timer = false,				\
-	},								\
+	INIT_CPUTIMER(sig)						\
 	INIT_PREV_CPUTIME(sig)						\
 	.cred_guard_mutex =						\
 		 __MUTEX_INITIALIZER(sig.cred_guard_mutex),		\
@@ -247,7 +264,7 @@ extern struct task_group root_task_group;
 	.blocked	= {{0}},					\
 	.alloc_lock	= __SPIN_LOCK_UNLOCKED(tsk.alloc_lock),		\
 	.journal_info	= NULL,						\
-	.cpu_timers	= INIT_CPU_TIMERS(tsk.cpu_timers),		\
+	INIT_CPU_TIMERS(tsk)						\
 	.pi_lock	= __RAW_SPIN_LOCK_UNLOCKED(tsk.pi_lock),	\
 	.timer_slack_ns = 50000, /* 50 usec default slack */		\
 	.pids = {							\
@@ -274,13 +291,6 @@ extern struct task_group root_task_group;
 }
 
 
-#define INIT_CPU_TIMERS(cpu_timers)					\
-{									\
-	LIST_HEAD_INIT(cpu_timers[0]),					\
-	LIST_HEAD_INIT(cpu_timers[1]),					\
-	LIST_HEAD_INIT(cpu_timers[2]),					\
-}
-
 /* Attach to the init_task data structure for proper alignment */
 #define __init_task_data __attribute__((__section__(".data..init_task")))
 
diff --git a/include/linux/sched.h b/include/linux/sched.h
index 4d1905245c..e8f6af5972 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -734,13 +734,14 @@ struct signal_struct {
 	unsigned int		is_child_subreaper:1;
 	unsigned int		has_child_subreaper:1;
 
+#ifdef CONFIG_POSIX_TIMERS
+
 	/* POSIX.1b Interval Timers */
 	int			posix_timer_id;
 	struct list_head	posix_timers;
 
 	/* ITIMER_REAL timer for the process */
 	struct hrtimer real_timer;
-	struct pid *leader_pid;
 	ktime_t it_real_incr;
 
 	/*
@@ -759,12 +760,16 @@ struct signal_struct {
 	/* Earliest-expiration cache. */
 	struct task_cputime cputime_expires;
 
+	struct list_head cpu_timers[3];
+
+#endif
+
+	struct pid *leader_pid;
+
 #ifdef CONFIG_NO_HZ_FULL
 	atomic_t tick_dep_mask;
 #endif
 
-	struct list_head cpu_timers[3];
-
 	struct pid *tty_old_pgrp;
 
 	/* boolean value for session group leader */
@@ -1681,8 +1686,10 @@ struct task_struct {
 /* mm fault and swap info: this can arguably be seen as either mm-specific or thread-specific */
 	unsigned long min_flt, maj_flt;
 
+#ifdef CONFIG_POSIX_TIMERS
 	struct task_cputime cputime_expires;
 	struct list_head cpu_timers[3];
+#endif
 
 /* process credentials */
 	const struct cred __rcu *ptracer_cred; /* Tracer's credentials at attach */
diff --git a/kernel/fork.c b/kernel/fork.c
index 11c5c8ab82..8e333e55a9 100644
--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -1309,6 +1309,7 @@ void __cleanup_sighand(struct sighand_struct *sighand)
  */
 static void posix_cpu_timers_init_group(struct signal_struct *sig)
 {
+#ifdef CONFIG_POSIX_TIMERS
 	unsigned long cpu_limit;
 
 	cpu_limit = READ_ONCE(sig->rlim[RLIMIT_CPU].rlim_cur);
@@ -1321,6 +1322,7 @@ static void posix_cpu_timers_init_group(struct signal_struct *sig)
 	INIT_LIST_HEAD(&sig->cpu_timers[0]);
 	INIT_LIST_HEAD(&sig->cpu_timers[1]);
 	INIT_LIST_HEAD(&sig->cpu_timers[2]);
+#endif
 }
 
 static int copy_signal(unsigned long clone_flags, struct task_struct *tsk)
@@ -1346,11 +1348,11 @@ static int copy_signal(unsigned long clone_flags, struct task_struct *tsk)
 	init_waitqueue_head(&sig->wait_chldexit);
 	sig->curr_target = tsk;
 	init_sigpending(&sig->shared_pending);
-	INIT_LIST_HEAD(&sig->posix_timers);
 	seqlock_init(&sig->stats_lock);
 	prev_cputime_init(&sig->prev_cputime);
 
 #ifdef CONFIG_POSIX_TIMERS
+	INIT_LIST_HEAD(&sig->posix_timers);
 	hrtimer_init(&sig->real_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
 	sig->real_timer.function = it_real_fn;
 #endif
@@ -1430,12 +1432,14 @@ static void rt_mutex_init_task(struct task_struct *p)
  */
 static void posix_cpu_timers_init(struct task_struct *tsk)
 {
+#ifdef CONFIG_POSIX_TIMERS
 	tsk->cputime_expires.prof_exp = 0;
 	tsk->cputime_expires.virt_exp = 0;
 	tsk->cputime_expires.sched_exp = 0;
 	INIT_LIST_HEAD(&tsk->cpu_timers[0]);
 	INIT_LIST_HEAD(&tsk->cpu_timers[1]);
 	INIT_LIST_HEAD(&tsk->cpu_timers[2]);
+#endif
 }
 
 static inline void
diff --git a/kernel/sched/rt.c b/kernel/sched/rt.c
index 2516b8df6d..f772e0c100 100644
--- a/kernel/sched/rt.c
+++ b/kernel/sched/rt.c
@@ -2248,6 +2248,7 @@ prio_changed_rt(struct rq *rq, struct task_struct *p, int oldprio)
 
 static void watchdog(struct rq *rq, struct task_struct *p)
 {
+#ifdef CONFIG_POSIX_TIMERS
 	unsigned long soft, hard;
 
 	/* max may change after cur was read, this will be fixed next tick */
@@ -2266,6 +2267,7 @@ static void watchdog(struct rq *rq, struct task_struct *p)
 		if (p->rt.timeout > next)
 			p->cputime_expires.sched_exp = p->se.sum_exec_runtime;
 	}
+#endif
 }
 
 static void task_tick_rt(struct rq *rq, struct task_struct *p, int queued)
diff --git a/kernel/sched/stats.h b/kernel/sched/stats.h
index 34659a8535..32505f71a8 100644
--- a/kernel/sched/stats.h
+++ b/kernel/sched/stats.h
@@ -172,18 +172,19 @@ sched_info_switch(struct rq *rq,
  */
 
 /**
- * cputimer_running - return true if cputimer is running
+ * get_running_cputimer - return &tsk->signal->cputimer if cputimer is running
  *
  * @tsk:	Pointer to target task.
  */
-static inline bool cputimer_running(struct task_struct *tsk)
-
+static inline
+struct thread_group_cputimer *get_running_cputimer(struct task_struct *tsk)
 {
+#ifdef CONFIG_POSIX_TIMERS
 	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
 
 	/* Check if cputimer isn't running. This is accessed without locking. */
 	if (!READ_ONCE(cputimer->running))
-		return false;
+		return NULL;
 
 	/*
 	 * After we flush the task's sum_exec_runtime to sig->sum_sched_runtime
@@ -200,9 +201,12 @@ static inline bool cputimer_running(struct task_struct *tsk)
 	 * clock delta is behind the expiring timer value.
 	 */
 	if (unlikely(!tsk->sighand))
-		return false;
+		return NULL;
 
-	return true;
+	return cputimer;
+#else
+	return NULL;
+#endif
 }
 
 /**
@@ -218,9 +222,9 @@ static inline bool cputimer_running(struct task_struct *tsk)
 static inline void account_group_user_time(struct task_struct *tsk,
 					   cputime_t cputime)
 {
-	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
+	struct thread_group_cputimer *cputimer = get_running_cputimer(tsk);
 
-	if (!cputimer_running(tsk))
+	if (!cputimer)
 		return;
 
 	atomic64_add(cputime, &cputimer->cputime_atomic.utime);
@@ -239,9 +243,9 @@ static inline void account_group_user_time(struct task_struct *tsk,
 static inline void account_group_system_time(struct task_struct *tsk,
 					     cputime_t cputime)
 {
-	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
+	struct thread_group_cputimer *cputimer = get_running_cputimer(tsk);
 
-	if (!cputimer_running(tsk))
+	if (!cputimer)
 		return;
 
 	atomic64_add(cputime, &cputimer->cputime_atomic.stime);
@@ -260,9 +264,9 @@ static inline void account_group_system_time(struct task_struct *tsk,
 static inline void account_group_exec_runtime(struct task_struct *tsk,
 					      unsigned long long ns)
 {
-	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
+	struct thread_group_cputimer *cputimer = get_running_cputimer(tsk);
 
-	if (!cputimer_running(tsk))
+	if (!cputimer)
 		return;
 
 	atomic64_add(ns, &cputimer->cputime_atomic.sum_exec_runtime);

^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [PATCH] omit POSIX timer stuff from task_struct when disabled
  2017-01-09 18:49 [PATCH] omit POSIX timer stuff from task_struct when disabled Nicolas Pitre
@ 2017-01-20 22:32 ` John Stultz
  2017-01-20 22:46   ` Nicolas Pitre
  0 siblings, 1 reply; 5+ messages in thread
From: John Stultz @ 2017-01-20 22:32 UTC (permalink / raw)
  To: Nicolas Pitre; +Cc: Thomas Gleixner, lkml

On Mon, Jan 9, 2017 at 10:49 AM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote:
> When CONFIG_POSIX_TIMERS is disabled, it is preferable to remove related
> structures from struct task_struct and struct signal_struct as they
> won't contain anything useful and shouldn't be relied upon by mistake.
> Code still referencing those structures is also disabled here.
>
> Signed-off-by: Nicolas Pitre <nico@linaro.org>
>
[snip]
> diff --git a/kernel/fork.c b/kernel/fork.c
> index 11c5c8ab82..8e333e55a9 100644
> --- a/kernel/fork.c
> +++ b/kernel/fork.c
> @@ -1309,6 +1309,7 @@ void __cleanup_sighand(struct sighand_struct *sighand)
>   */
>  static void posix_cpu_timers_init_group(struct signal_struct *sig)
>  {
> +#ifdef CONFIG_POSIX_TIMERS
>         unsigned long cpu_limit;
>
>         cpu_limit = READ_ONCE(sig->rlim[RLIMIT_CPU].rlim_cur);
> @@ -1321,6 +1322,7 @@ static void posix_cpu_timers_init_group(struct signal_struct *sig)
>         INIT_LIST_HEAD(&sig->cpu_timers[0]);
>         INIT_LIST_HEAD(&sig->cpu_timers[1]);
>         INIT_LIST_HEAD(&sig->cpu_timers[2]);
> +#endif
>  }

So apologies for not catching this earlier. I was just queuing this
up, when I noticed the style issue here.

Aren't in-function ifdefs frowned upon? Wouldn't it be better to do:
#ifdef CONFIG_POSIX_TIMERS
static void posix_cpu_timers_init_group(struct signal_struct *sig)
{
...
}
#else
static void posix_cpu_timers_init_group(struct signal_struct *sig) {}
#endif

And similar for most of the ifdef'ed out functions in this patch?

thanks
-john

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] omit POSIX timer stuff from task_struct when disabled
  2017-01-20 22:32 ` John Stultz
@ 2017-01-20 22:46   ` Nicolas Pitre
  2017-01-20 22:48     ` John Stultz
  0 siblings, 1 reply; 5+ messages in thread
From: Nicolas Pitre @ 2017-01-20 22:46 UTC (permalink / raw)
  To: John Stultz; +Cc: Thomas Gleixner, lkml

On Fri, 20 Jan 2017, John Stultz wrote:

> On Mon, Jan 9, 2017 at 10:49 AM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote:
> > When CONFIG_POSIX_TIMERS is disabled, it is preferable to remove related
> > structures from struct task_struct and struct signal_struct as they
> > won't contain anything useful and shouldn't be relied upon by mistake.
> > Code still referencing those structures is also disabled here.
> >
> > Signed-off-by: Nicolas Pitre <nico@linaro.org>
> >
> [snip]
> > diff --git a/kernel/fork.c b/kernel/fork.c
> > index 11c5c8ab82..8e333e55a9 100644
> > --- a/kernel/fork.c
> > +++ b/kernel/fork.c
> > @@ -1309,6 +1309,7 @@ void __cleanup_sighand(struct sighand_struct *sighand)
> >   */
> >  static void posix_cpu_timers_init_group(struct signal_struct *sig)
> >  {
> > +#ifdef CONFIG_POSIX_TIMERS
> >         unsigned long cpu_limit;
> >
> >         cpu_limit = READ_ONCE(sig->rlim[RLIMIT_CPU].rlim_cur);
> > @@ -1321,6 +1322,7 @@ static void posix_cpu_timers_init_group(struct signal_struct *sig)
> >         INIT_LIST_HEAD(&sig->cpu_timers[0]);
> >         INIT_LIST_HEAD(&sig->cpu_timers[1]);
> >         INIT_LIST_HEAD(&sig->cpu_timers[2]);
> > +#endif
> >  }
> 
> So apologies for not catching this earlier. I was just queuing this
> up, when I noticed the style issue here.
> 
> Aren't in-function ifdefs frowned upon? Wouldn't it be better to do:
> #ifdef CONFIG_POSIX_TIMERS
> static void posix_cpu_timers_init_group(struct signal_struct *sig)
> {
> ...
> }
> #else
> static void posix_cpu_timers_init_group(struct signal_struct *sig) {}
> #endif
> 
> And similar for most of the ifdef'ed out functions in this patch?

Well... I don't mind either ways.  In this case those functions are 
rather small and doing it the way you suggest doubles the number of 
added lines in this hunk. That's why I opted for the current style.

Just tell me if you prefer that I respin the patch and I'll do it.


Nicolas

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] omit POSIX timer stuff from task_struct when disabled
  2017-01-20 22:46   ` Nicolas Pitre
@ 2017-01-20 22:48     ` John Stultz
  2017-01-21  5:09       ` Nicolas Pitre
  0 siblings, 1 reply; 5+ messages in thread
From: John Stultz @ 2017-01-20 22:48 UTC (permalink / raw)
  To: Nicolas Pitre; +Cc: Thomas Gleixner, lkml

On Fri, Jan 20, 2017 at 2:46 PM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote:
> On Fri, 20 Jan 2017, John Stultz wrote:
>
>> On Mon, Jan 9, 2017 at 10:49 AM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote:
>> > When CONFIG_POSIX_TIMERS is disabled, it is preferable to remove related
>> > structures from struct task_struct and struct signal_struct as they
>> > won't contain anything useful and shouldn't be relied upon by mistake.
>> > Code still referencing those structures is also disabled here.
>> >
>> > Signed-off-by: Nicolas Pitre <nico@linaro.org>
>> >
>> [snip]
>> > diff --git a/kernel/fork.c b/kernel/fork.c
>> > index 11c5c8ab82..8e333e55a9 100644
>> > --- a/kernel/fork.c
>> > +++ b/kernel/fork.c
>> > @@ -1309,6 +1309,7 @@ void __cleanup_sighand(struct sighand_struct *sighand)
>> >   */
>> >  static void posix_cpu_timers_init_group(struct signal_struct *sig)
>> >  {
>> > +#ifdef CONFIG_POSIX_TIMERS
>> >         unsigned long cpu_limit;
>> >
>> >         cpu_limit = READ_ONCE(sig->rlim[RLIMIT_CPU].rlim_cur);
>> > @@ -1321,6 +1322,7 @@ static void posix_cpu_timers_init_group(struct signal_struct *sig)
>> >         INIT_LIST_HEAD(&sig->cpu_timers[0]);
>> >         INIT_LIST_HEAD(&sig->cpu_timers[1]);
>> >         INIT_LIST_HEAD(&sig->cpu_timers[2]);
>> > +#endif
>> >  }
>>
>> So apologies for not catching this earlier. I was just queuing this
>> up, when I noticed the style issue here.
>>
>> Aren't in-function ifdefs frowned upon? Wouldn't it be better to do:
>> #ifdef CONFIG_POSIX_TIMERS
>> static void posix_cpu_timers_init_group(struct signal_struct *sig)
>> {
>> ...
>> }
>> #else
>> static void posix_cpu_timers_init_group(struct signal_struct *sig) {}
>> #endif
>>
>> And similar for most of the ifdef'ed out functions in this patch?
>
> Well... I don't mind either ways.  In this case those functions are
> rather small and doing it the way you suggest doubles the number of
> added lines in this hunk. That's why I opted for the current style.
>
> Just tell me if you prefer that I respin the patch and I'll do it.

Yea. I'm not so finicky but I'm sure I'll probably get yelled at if I
pass it on, so if you don't mind respinning it, I'll get it applied
for testing here quickly :)

thanks
-john

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH] omit POSIX timer stuff from task_struct when disabled
  2017-01-20 22:48     ` John Stultz
@ 2017-01-21  5:09       ` Nicolas Pitre
  0 siblings, 0 replies; 5+ messages in thread
From: Nicolas Pitre @ 2017-01-21  5:09 UTC (permalink / raw)
  To: John Stultz; +Cc: Thomas Gleixner, lkml

On Fri, 20 Jan 2017, John Stultz wrote:

> On Fri, Jan 20, 2017 at 2:46 PM, Nicolas Pitre <nicolas.pitre@linaro.org> wrote:
> > Just tell me if you prefer that I respin the patch and I'll do it.
> 
> Yea. I'm not so finicky but I'm sure I'll probably get yelled at if I
> pass it on, so if you don't mind respinning it, I'll get it applied
> for testing here quickly :)

There you go.

----- >8
Subject: omit POSIX timer stuff from task_struct when disabled

When CONFIG_POSIX_TIMERS is disabled, it is preferable to remove related
structures from struct task_struct and struct signal_struct as they
won't contain anything useful and shouldn't be relied upon by mistake.
Code still referencing those structures is also disabled here.

Signed-off-by: Nicolas Pitre <nico@linaro.org>

diff --git a/fs/proc/base.c b/fs/proc/base.c
index 8e7e61b28f..03deeac1e8 100644
--- a/fs/proc/base.c
+++ b/fs/proc/base.c
@@ -2179,7 +2179,7 @@ static const struct file_operations proc_map_files_operations = {
 	.llseek		= generic_file_llseek,
 };
 
-#ifdef CONFIG_CHECKPOINT_RESTORE
+#if defined(CONFIG_CHECKPOINT_RESTORE) && defined(CONFIG_POSIX_TIMERS)
 struct timers_private {
 	struct pid *pid;
 	struct task_struct *task;
@@ -2936,7 +2936,7 @@ static const struct pid_entry tgid_base_stuff[] = {
 	REG("projid_map", S_IRUGO|S_IWUSR, proc_projid_map_operations),
 	REG("setgroups",  S_IRUGO|S_IWUSR, proc_setgroups_operations),
 #endif
-#ifdef CONFIG_CHECKPOINT_RESTORE
+#if defined(CONFIG_CHECKPOINT_RESTORE) && defined(CONFIG_POSIX_TIMERS)
 	REG("timers",	  S_IRUGO, proc_timers_operations),
 #endif
 	REG("timerslack_ns", S_IRUGO|S_IWUGO, proc_pid_set_timerslack_ns_operations),
diff --git a/include/linux/init_task.h b/include/linux/init_task.h
index 325f649d77..3a85d61f76 100644
--- a/include/linux/init_task.h
+++ b/include/linux/init_task.h
@@ -42,6 +42,27 @@ extern struct fs_struct init_fs;
 #define INIT_PREV_CPUTIME(x)
 #endif
 
+#ifdef CONFIG_POSIX_TIMERS
+#define INIT_POSIX_TIMERS(s)						\
+	.posix_timers = LIST_HEAD_INIT(s.posix_timers),
+#define INIT_CPU_TIMERS(s)						\
+	.cpu_timers = {							\
+		LIST_HEAD_INIT(s.cpu_timers[0]),			\
+		LIST_HEAD_INIT(s.cpu_timers[1]),			\
+		LIST_HEAD_INIT(s.cpu_timers[2]),								\
+	},
+#define INIT_CPUTIMER(s)						\
+	.cputimer	= { 						\
+		.cputime_atomic	= INIT_CPUTIME_ATOMIC,			\
+		.running	= false,				\
+		.checking_timer = false,				\
+	},
+#else
+#define INIT_POSIX_TIMERS(s)
+#define INIT_CPU_TIMERS(s)
+#define INIT_CPUTIMER(s)
+#endif
+
 #define INIT_SIGNALS(sig) {						\
 	.nr_threads	= 1,						\
 	.thread_head	= LIST_HEAD_INIT(init_task.thread_node),	\
@@ -49,14 +70,10 @@ extern struct fs_struct init_fs;
 	.shared_pending	= { 						\
 		.list = LIST_HEAD_INIT(sig.shared_pending.list),	\
 		.signal =  {{0}}},					\
-	.posix_timers	 = LIST_HEAD_INIT(sig.posix_timers),		\
-	.cpu_timers	= INIT_CPU_TIMERS(sig.cpu_timers),		\
+	INIT_POSIX_TIMERS(sig)						\
+	INIT_CPU_TIMERS(sig)						\
 	.rlim		= INIT_RLIMITS,					\
-	.cputimer	= { 						\
-		.cputime_atomic	= INIT_CPUTIME_ATOMIC,			\
-		.running	= false,				\
-		.checking_timer = false,				\
-	},								\
+	INIT_CPUTIMER(sig)						\
 	INIT_PREV_CPUTIME(sig)						\
 	.cred_guard_mutex =						\
 		 __MUTEX_INITIALIZER(sig.cred_guard_mutex),		\
@@ -247,7 +264,7 @@ extern struct task_group root_task_group;
 	.blocked	= {{0}},					\
 	.alloc_lock	= __SPIN_LOCK_UNLOCKED(tsk.alloc_lock),		\
 	.journal_info	= NULL,						\
-	.cpu_timers	= INIT_CPU_TIMERS(tsk.cpu_timers),		\
+	INIT_CPU_TIMERS(tsk)						\
 	.pi_lock	= __RAW_SPIN_LOCK_UNLOCKED(tsk.pi_lock),	\
 	.timer_slack_ns = 50000, /* 50 usec default slack */		\
 	.pids = {							\
@@ -274,13 +291,6 @@ extern struct task_group root_task_group;
 }
 
 
-#define INIT_CPU_TIMERS(cpu_timers)					\
-{									\
-	LIST_HEAD_INIT(cpu_timers[0]),					\
-	LIST_HEAD_INIT(cpu_timers[1]),					\
-	LIST_HEAD_INIT(cpu_timers[2]),					\
-}
-
 /* Attach to the init_task data structure for proper alignment */
 #define __init_task_data __attribute__((__section__(".data..init_task")))
 
diff --git a/include/linux/sched.h b/include/linux/sched.h
index 4d1905245c..e8f6af5972 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -734,13 +734,14 @@ struct signal_struct {
 	unsigned int		is_child_subreaper:1;
 	unsigned int		has_child_subreaper:1;
 
+#ifdef CONFIG_POSIX_TIMERS
+
 	/* POSIX.1b Interval Timers */
 	int			posix_timer_id;
 	struct list_head	posix_timers;
 
 	/* ITIMER_REAL timer for the process */
 	struct hrtimer real_timer;
-	struct pid *leader_pid;
 	ktime_t it_real_incr;
 
 	/*
@@ -759,12 +760,16 @@ struct signal_struct {
 	/* Earliest-expiration cache. */
 	struct task_cputime cputime_expires;
 
+	struct list_head cpu_timers[3];
+
+#endif
+
+	struct pid *leader_pid;
+
 #ifdef CONFIG_NO_HZ_FULL
 	atomic_t tick_dep_mask;
 #endif
 
-	struct list_head cpu_timers[3];
-
 	struct pid *tty_old_pgrp;
 
 	/* boolean value for session group leader */
@@ -1681,8 +1686,10 @@ struct task_struct {
 /* mm fault and swap info: this can arguably be seen as either mm-specific or thread-specific */
 	unsigned long min_flt, maj_flt;
 
+#ifdef CONFIG_POSIX_TIMERS
 	struct task_cputime cputime_expires;
 	struct list_head cpu_timers[3];
+#endif
 
 /* process credentials */
 	const struct cred __rcu *ptracer_cred; /* Tracer's credentials at attach */
diff --git a/kernel/fork.c b/kernel/fork.c
index 11c5c8ab82..105c6676d9 100644
--- a/kernel/fork.c
+++ b/kernel/fork.c
@@ -1304,6 +1304,7 @@ void __cleanup_sighand(struct sighand_struct *sighand)
 	}
 }
 
+#ifdef CONFIG_POSIX_TIMERS
 /*
  * Initialize POSIX timer handling for a thread group.
  */
@@ -1322,6 +1323,9 @@ static void posix_cpu_timers_init_group(struct signal_struct *sig)
 	INIT_LIST_HEAD(&sig->cpu_timers[1]);
 	INIT_LIST_HEAD(&sig->cpu_timers[2]);
 }
+#else
+static inline void posix_cpu_timers_init_group(struct signal_struct *sig) { }
+#endif
 
 static int copy_signal(unsigned long clone_flags, struct task_struct *tsk)
 {
@@ -1346,11 +1350,11 @@ static int copy_signal(unsigned long clone_flags, struct task_struct *tsk)
 	init_waitqueue_head(&sig->wait_chldexit);
 	sig->curr_target = tsk;
 	init_sigpending(&sig->shared_pending);
-	INIT_LIST_HEAD(&sig->posix_timers);
 	seqlock_init(&sig->stats_lock);
 	prev_cputime_init(&sig->prev_cputime);
 
 #ifdef CONFIG_POSIX_TIMERS
+	INIT_LIST_HEAD(&sig->posix_timers);
 	hrtimer_init(&sig->real_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);
 	sig->real_timer.function = it_real_fn;
 #endif
@@ -1425,6 +1429,7 @@ static void rt_mutex_init_task(struct task_struct *p)
 #endif
 }
 
+#ifdef CONFIG_POSIX_TIMERS
 /*
  * Initialize POSIX timer handling for a single task.
  */
@@ -1437,6 +1442,9 @@ static void posix_cpu_timers_init(struct task_struct *tsk)
 	INIT_LIST_HEAD(&tsk->cpu_timers[1]);
 	INIT_LIST_HEAD(&tsk->cpu_timers[2]);
 }
+#else
+static inline void posix_cpu_timers_init(struct task_struct *tsk) { }
+#endif
 
 static inline void
 init_task_pid(struct task_struct *task, enum pid_type type, struct pid *pid)
diff --git a/kernel/sched/rt.c b/kernel/sched/rt.c
index 2516b8df6d..a688a82067 100644
--- a/kernel/sched/rt.c
+++ b/kernel/sched/rt.c
@@ -2246,6 +2246,7 @@ prio_changed_rt(struct rq *rq, struct task_struct *p, int oldprio)
 	}
 }
 
+#ifdef CONFIG_POSIX_TIMERS
 static void watchdog(struct rq *rq, struct task_struct *p)
 {
 	unsigned long soft, hard;
@@ -2267,6 +2268,9 @@ static void watchdog(struct rq *rq, struct task_struct *p)
 			p->cputime_expires.sched_exp = p->se.sum_exec_runtime;
 	}
 }
+#else
+static inline void watchdog(struct rq *rq, struct task_struct *p) { }
+#endif
 
 static void task_tick_rt(struct rq *rq, struct task_struct *p, int queued)
 {
diff --git a/kernel/sched/stats.h b/kernel/sched/stats.h
index 34659a8535..c69a9870ab 100644
--- a/kernel/sched/stats.h
+++ b/kernel/sched/stats.h
@@ -172,18 +172,19 @@ sched_info_switch(struct rq *rq,
  */
 
 /**
- * cputimer_running - return true if cputimer is running
+ * get_running_cputimer - return &tsk->signal->cputimer if cputimer is running
  *
  * @tsk:	Pointer to target task.
  */
-static inline bool cputimer_running(struct task_struct *tsk)
-
+#ifdef CONFIG_POSIX_TIMERS
+static inline
+struct thread_group_cputimer *get_running_cputimer(struct task_struct *tsk)
 {
 	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
 
 	/* Check if cputimer isn't running. This is accessed without locking. */
 	if (!READ_ONCE(cputimer->running))
-		return false;
+		return NULL;
 
 	/*
 	 * After we flush the task's sum_exec_runtime to sig->sum_sched_runtime
@@ -200,10 +201,17 @@ static inline bool cputimer_running(struct task_struct *tsk)
 	 * clock delta is behind the expiring timer value.
 	 */
 	if (unlikely(!tsk->sighand))
-		return false;
+		return NULL;
 
-	return true;
+	return cputimer;
+}
+#else
+static inline
+struct thread_group_cputimer *get_running_cputimer(struct task_struct *tsk)
+{
+	return NULL;
 }
+#endif
 
 /**
  * account_group_user_time - Maintain utime for a thread group.
@@ -218,9 +226,9 @@ static inline bool cputimer_running(struct task_struct *tsk)
 static inline void account_group_user_time(struct task_struct *tsk,
 					   cputime_t cputime)
 {
-	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
+	struct thread_group_cputimer *cputimer = get_running_cputimer(tsk);
 
-	if (!cputimer_running(tsk))
+	if (!cputimer)
 		return;
 
 	atomic64_add(cputime, &cputimer->cputime_atomic.utime);
@@ -239,9 +247,9 @@ static inline void account_group_user_time(struct task_struct *tsk,
 static inline void account_group_system_time(struct task_struct *tsk,
 					     cputime_t cputime)
 {
-	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
+	struct thread_group_cputimer *cputimer = get_running_cputimer(tsk);
 
-	if (!cputimer_running(tsk))
+	if (!cputimer)
 		return;
 
 	atomic64_add(cputime, &cputimer->cputime_atomic.stime);
@@ -260,9 +268,9 @@ static inline void account_group_system_time(struct task_struct *tsk,
 static inline void account_group_exec_runtime(struct task_struct *tsk,
 					      unsigned long long ns)
 {
-	struct thread_group_cputimer *cputimer = &tsk->signal->cputimer;
+	struct thread_group_cputimer *cputimer = get_running_cputimer(tsk);
 
-	if (!cputimer_running(tsk))
+	if (!cputimer)
 		return;
 
 	atomic64_add(ns, &cputimer->cputime_atomic.sum_exec_runtime);

^ permalink raw reply related	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2017-01-21  6:20 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2017-01-09 18:49 [PATCH] omit POSIX timer stuff from task_struct when disabled Nicolas Pitre
2017-01-20 22:32 ` John Stultz
2017-01-20 22:46   ` Nicolas Pitre
2017-01-20 22:48     ` John Stultz
2017-01-21  5:09       ` Nicolas Pitre

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).