Commit 60e38303 authored by Linus Torvalds's avatar Linus Torvalds

Merge branch 'sched-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull scheduler fixes from Ingo Molnar:
 "Two scheduler debugging fixes"

* 'sched-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
  sched/debug: Fix 'schedstats=enable' cmdline option
  sched/debug: Fix /proc/sched_debug regression
parents 7fcbc230 4698f88c
...@@ -2253,9 +2253,11 @@ int sysctl_numa_balancing(struct ctl_table *table, int write, ...@@ -2253,9 +2253,11 @@ int sysctl_numa_balancing(struct ctl_table *table, int write,
#endif #endif
#endif #endif
#ifdef CONFIG_SCHEDSTATS
DEFINE_STATIC_KEY_FALSE(sched_schedstats); DEFINE_STATIC_KEY_FALSE(sched_schedstats);
static bool __initdata __sched_schedstats = false;
#ifdef CONFIG_SCHEDSTATS
static void set_schedstats(bool enabled) static void set_schedstats(bool enabled)
{ {
if (enabled) if (enabled)
...@@ -2278,11 +2280,16 @@ static int __init setup_schedstats(char *str) ...@@ -2278,11 +2280,16 @@ static int __init setup_schedstats(char *str)
if (!str) if (!str)
goto out; goto out;
/*
* This code is called before jump labels have been set up, so we can't
* change the static branch directly just yet. Instead set a temporary
* variable so init_schedstats() can do it later.
*/
if (!strcmp(str, "enable")) { if (!strcmp(str, "enable")) {
set_schedstats(true); __sched_schedstats = true;
ret = 1; ret = 1;
} else if (!strcmp(str, "disable")) { } else if (!strcmp(str, "disable")) {
set_schedstats(false); __sched_schedstats = false;
ret = 1; ret = 1;
} }
out: out:
...@@ -2293,6 +2300,11 @@ static int __init setup_schedstats(char *str) ...@@ -2293,6 +2300,11 @@ static int __init setup_schedstats(char *str)
} }
__setup("schedstats=", setup_schedstats); __setup("schedstats=", setup_schedstats);
static void __init init_schedstats(void)
{
set_schedstats(__sched_schedstats);
}
#ifdef CONFIG_PROC_SYSCTL #ifdef CONFIG_PROC_SYSCTL
int sysctl_schedstats(struct ctl_table *table, int write, int sysctl_schedstats(struct ctl_table *table, int write,
void __user *buffer, size_t *lenp, loff_t *ppos) void __user *buffer, size_t *lenp, loff_t *ppos)
...@@ -2313,8 +2325,10 @@ int sysctl_schedstats(struct ctl_table *table, int write, ...@@ -2313,8 +2325,10 @@ int sysctl_schedstats(struct ctl_table *table, int write,
set_schedstats(state); set_schedstats(state);
return err; return err;
} }
#endif #endif /* CONFIG_PROC_SYSCTL */
#endif #else /* !CONFIG_SCHEDSTATS */
static inline void init_schedstats(void) {}
#endif /* CONFIG_SCHEDSTATS */
/* /*
* fork()/clone()-time setup: * fork()/clone()-time setup:
...@@ -7487,6 +7501,8 @@ void __init sched_init(void) ...@@ -7487,6 +7501,8 @@ void __init sched_init(void)
#endif #endif
init_sched_fair_class(); init_sched_fair_class();
init_schedstats();
scheduler_running = 1; scheduler_running = 1;
} }
......
...@@ -427,19 +427,12 @@ print_task(struct seq_file *m, struct rq *rq, struct task_struct *p) ...@@ -427,19 +427,12 @@ print_task(struct seq_file *m, struct rq *rq, struct task_struct *p)
SPLIT_NS(p->se.vruntime), SPLIT_NS(p->se.vruntime),
(long long)(p->nvcsw + p->nivcsw), (long long)(p->nvcsw + p->nivcsw),
p->prio); p->prio);
#ifdef CONFIG_SCHEDSTATS
if (schedstat_enabled()) {
SEQ_printf(m, "%9Ld.%06ld %9Ld.%06ld %9Ld.%06ld",
SPLIT_NS(p->se.statistics.wait_sum),
SPLIT_NS(p->se.sum_exec_runtime),
SPLIT_NS(p->se.statistics.sum_sleep_runtime));
}
#else
SEQ_printf(m, "%9Ld.%06ld %9Ld.%06ld %9Ld.%06ld", SEQ_printf(m, "%9Ld.%06ld %9Ld.%06ld %9Ld.%06ld",
0LL, 0L, SPLIT_NS(schedstat_val(p, se.statistics.wait_sum)),
SPLIT_NS(p->se.sum_exec_runtime), SPLIT_NS(p->se.sum_exec_runtime),
0LL, 0L); SPLIT_NS(schedstat_val(p, se.statistics.sum_sleep_runtime)));
#endif
#ifdef CONFIG_NUMA_BALANCING #ifdef CONFIG_NUMA_BALANCING
SEQ_printf(m, " %d %d", task_node(p), task_numa_group_id(p)); SEQ_printf(m, " %d %d", task_node(p), task_numa_group_id(p));
#endif #endif
......
...@@ -33,6 +33,8 @@ rq_sched_info_dequeued(struct rq *rq, unsigned long long delta) ...@@ -33,6 +33,8 @@ rq_sched_info_dequeued(struct rq *rq, unsigned long long delta)
# define schedstat_inc(rq, field) do { if (schedstat_enabled()) { (rq)->field++; } } while (0) # define schedstat_inc(rq, field) do { if (schedstat_enabled()) { (rq)->field++; } } while (0)
# define schedstat_add(rq, field, amt) do { if (schedstat_enabled()) { (rq)->field += (amt); } } while (0) # define schedstat_add(rq, field, amt) do { if (schedstat_enabled()) { (rq)->field += (amt); } } while (0)
# define schedstat_set(var, val) do { if (schedstat_enabled()) { var = (val); } } while (0) # define schedstat_set(var, val) do { if (schedstat_enabled()) { var = (val); } } while (0)
# define schedstat_val(rq, field) ((schedstat_enabled()) ? (rq)->field : 0)
#else /* !CONFIG_SCHEDSTATS */ #else /* !CONFIG_SCHEDSTATS */
static inline void static inline void
rq_sched_info_arrive(struct rq *rq, unsigned long long delta) rq_sched_info_arrive(struct rq *rq, unsigned long long delta)
...@@ -47,6 +49,7 @@ rq_sched_info_depart(struct rq *rq, unsigned long long delta) ...@@ -47,6 +49,7 @@ rq_sched_info_depart(struct rq *rq, unsigned long long delta)
# define schedstat_inc(rq, field) do { } while (0) # define schedstat_inc(rq, field) do { } while (0)
# define schedstat_add(rq, field, amt) do { } while (0) # define schedstat_add(rq, field, amt) do { } while (0)
# define schedstat_set(var, val) do { } while (0) # define schedstat_set(var, val) do { } while (0)
# define schedstat_val(rq, field) 0
#endif #endif
#ifdef CONFIG_SCHED_INFO #ifdef CONFIG_SCHED_INFO
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment