aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDaniel Lezcano <daniel.lezcano@linaro.org>2014-03-03 02:48:52 -0500
committerIngo Molnar <mingo@kernel.org>2014-03-11 06:52:47 -0400
commitc8cc7d4de7a4f2fb1f8774ec2de5b49c46c42e64 (patch)
treec36d18f956ac91dd23e14bde0012d7645e253804
parent30cdd69e2a266505ca8229c944d361ff350a6959 (diff)
sched/idle: Reorganize the idle loop
Now that we have the main cpuidle function in idle.c, move some code from the idle mainloop to this function for the sake of clarity. That removes if then else indentation difficult to follow when looking at the code. This patch does not change the current behavior. Signed-off-by: Daniel Lezcano <daniel.lezcano@linaro.org> Acked-by: Nicolas Pitre <nico@linaro.org> Signed-off-by: Peter Zijlstra <peterz@infradead.org> Cc: tglx@linutronix.de Cc: rjw@rjwysocki.net Cc: preeti@linux.vnet.ibm.com Link: http://lkml.kernel.org/r/1393832934-11625-3-git-send-email-daniel.lezcano@linaro.org Signed-off-by: Ingo Molnar <mingo@kernel.org>
-rw-r--r--include/linux/cpuidle.h2
-rw-r--r--kernel/sched/idle.c33
2 files changed, 17 insertions, 18 deletions
diff --git a/include/linux/cpuidle.h b/include/linux/cpuidle.h
index 8d97962d6d64..b0238cba440b 100644
--- a/include/linux/cpuidle.h
+++ b/include/linux/cpuidle.h
@@ -180,6 +180,8 @@ static inline int cpuidle_enable_device(struct cpuidle_device *dev)
180{return -ENODEV; } 180{return -ENODEV; }
181static inline void cpuidle_disable_device(struct cpuidle_device *dev) { } 181static inline void cpuidle_disable_device(struct cpuidle_device *dev) { }
182static inline int cpuidle_play_dead(void) {return -ENODEV; } 182static inline int cpuidle_play_dead(void) {return -ENODEV; }
183static inline struct cpuidle_driver *cpuidle_get_cpu_driver(
184 struct cpuidle_device *dev) {return NULL; }
183#endif 185#endif
184 186
185#ifdef CONFIG_ARCH_NEEDS_CPU_IDLE_COUPLED 187#ifdef CONFIG_ARCH_NEEDS_CPU_IDLE_COUPLED
diff --git a/kernel/sched/idle.c b/kernel/sched/idle.c
index d5aaf5eb4531..dc8a2466418f 100644
--- a/kernel/sched/idle.c
+++ b/kernel/sched/idle.c
@@ -63,7 +63,6 @@ void __weak arch_cpu_idle(void)
63 local_irq_enable(); 63 local_irq_enable();
64} 64}
65 65
66#ifdef CONFIG_CPU_IDLE
67/** 66/**
68 * cpuidle_idle_call - the main idle function 67 * cpuidle_idle_call - the main idle function
69 * 68 *
@@ -77,9 +76,14 @@ static int cpuidle_idle_call(void)
77 int next_state, entered_state, ret; 76 int next_state, entered_state, ret;
78 bool broadcast; 77 bool broadcast;
79 78
79 stop_critical_timings();
80 rcu_idle_enter();
81
80 ret = cpuidle_enabled(drv, dev); 82 ret = cpuidle_enabled(drv, dev);
81 if (ret < 0) 83 if (ret < 0) {
82 return ret; 84 arch_cpu_idle();
85 goto out;
86 }
83 87
84 /* ask the governor for the next state */ 88 /* ask the governor for the next state */
85 next_state = cpuidle_select(drv, dev); 89 next_state = cpuidle_select(drv, dev);
@@ -89,7 +93,7 @@ static int cpuidle_idle_call(void)
89 /* give the governor an opportunity to reflect on the outcome */ 93 /* give the governor an opportunity to reflect on the outcome */
90 cpuidle_reflect(dev, next_state); 94 cpuidle_reflect(dev, next_state);
91 local_irq_enable(); 95 local_irq_enable();
92 return 0; 96 goto out;
93 } 97 }
94 98
95 broadcast = !!(drv->states[next_state].flags & CPUIDLE_FLAG_TIMER_STOP); 99 broadcast = !!(drv->states[next_state].flags & CPUIDLE_FLAG_TIMER_STOP);
@@ -109,15 +113,15 @@ static int cpuidle_idle_call(void)
109 113
110 /* give the governor an opportunity to reflect on the outcome */ 114 /* give the governor an opportunity to reflect on the outcome */
111 cpuidle_reflect(dev, entered_state); 115 cpuidle_reflect(dev, entered_state);
116out:
117 if (WARN_ON_ONCE(irqs_disabled()))
118 local_irq_enable();
119
120 rcu_idle_exit();
121 start_critical_timings();
112 122
113 return 0; 123 return 0;
114} 124}
115#else
116static inline int cpuidle_idle_call(void)
117{
118 return -ENODEV;
119}
120#endif
121 125
122/* 126/*
123 * Generic idle loop implementation 127 * Generic idle loop implementation
@@ -150,14 +154,7 @@ static void cpu_idle_loop(void)
150 cpu_idle_poll(); 154 cpu_idle_poll();
151 } else { 155 } else {
152 if (!current_clr_polling_and_test()) { 156 if (!current_clr_polling_and_test()) {
153 stop_critical_timings(); 157 cpuidle_idle_call();
154 rcu_idle_enter();
155 if (cpuidle_idle_call())
156 arch_cpu_idle();
157 if (WARN_ON_ONCE(irqs_disabled()))
158 local_irq_enable();
159 rcu_idle_exit();
160 start_critical_timings();
161 } else { 158 } else {
162 local_irq_enable(); 159 local_irq_enable();
163 } 160 }