diff options
-rw-r--r-- | arch/i386/kernel/process.c | 30 | ||||
-rw-r--r-- | arch/x86_64/kernel/process.c | 30 |
2 files changed, 18 insertions, 42 deletions
diff --git a/arch/i386/kernel/process.c b/arch/i386/kernel/process.c index 8749b10d3805..8f42659ef9d2 100644 --- a/arch/i386/kernel/process.c +++ b/arch/i386/kernel/process.c | |||
@@ -100,22 +100,18 @@ EXPORT_SYMBOL(enable_hlt); | |||
100 | */ | 100 | */ |
101 | void default_idle(void) | 101 | void default_idle(void) |
102 | { | 102 | { |
103 | local_irq_enable(); | ||
104 | |||
105 | if (!hlt_counter && boot_cpu_data.hlt_works_ok) { | 103 | if (!hlt_counter && boot_cpu_data.hlt_works_ok) { |
106 | current_thread_info()->status &= ~TS_POLLING; | 104 | current_thread_info()->status &= ~TS_POLLING; |
107 | smp_mb__after_clear_bit(); | 105 | smp_mb__after_clear_bit(); |
108 | while (!need_resched()) { | 106 | local_irq_disable(); |
109 | local_irq_disable(); | 107 | if (!need_resched()) |
110 | if (!need_resched()) | 108 | safe_halt(); /* enables interrupts racelessly */ |
111 | safe_halt(); | 109 | else |
112 | else | 110 | local_irq_enable(); |
113 | local_irq_enable(); | ||
114 | } | ||
115 | current_thread_info()->status |= TS_POLLING; | 111 | current_thread_info()->status |= TS_POLLING; |
116 | } else { | 112 | } else { |
117 | while (!need_resched()) | 113 | /* loop is done by the caller */ |
118 | cpu_relax(); | 114 | cpu_relax(); |
119 | } | 115 | } |
120 | } | 116 | } |
121 | #ifdef CONFIG_APM_MODULE | 117 | #ifdef CONFIG_APM_MODULE |
@@ -129,14 +125,7 @@ EXPORT_SYMBOL(default_idle); | |||
129 | */ | 125 | */ |
130 | static void poll_idle (void) | 126 | static void poll_idle (void) |
131 | { | 127 | { |
132 | local_irq_enable(); | 128 | cpu_relax(); |
133 | |||
134 | asm volatile( | ||
135 | "2:" | ||
136 | "testl %0, %1;" | ||
137 | "rep; nop;" | ||
138 | "je 2b;" | ||
139 | : : "i"(_TIF_NEED_RESCHED), "m" (current_thread_info()->flags)); | ||
140 | } | 129 | } |
141 | 130 | ||
142 | #ifdef CONFIG_HOTPLUG_CPU | 131 | #ifdef CONFIG_HOTPLUG_CPU |
@@ -257,8 +246,7 @@ void mwait_idle_with_hints(unsigned long eax, unsigned long ecx) | |||
257 | static void mwait_idle(void) | 246 | static void mwait_idle(void) |
258 | { | 247 | { |
259 | local_irq_enable(); | 248 | local_irq_enable(); |
260 | while (!need_resched()) | 249 | mwait_idle_with_hints(0, 0); |
261 | mwait_idle_with_hints(0, 0); | ||
262 | } | 250 | } |
263 | 251 | ||
264 | void __devinit select_idle_routine(const struct cpuinfo_x86 *c) | 252 | void __devinit select_idle_routine(const struct cpuinfo_x86 *c) |
diff --git a/arch/x86_64/kernel/process.c b/arch/x86_64/kernel/process.c index 7451a4c43c16..0b7b4caa4f74 100644 --- a/arch/x86_64/kernel/process.c +++ b/arch/x86_64/kernel/process.c | |||
@@ -108,17 +108,15 @@ void exit_idle(void) | |||
108 | */ | 108 | */ |
109 | static void default_idle(void) | 109 | static void default_idle(void) |
110 | { | 110 | { |
111 | local_irq_enable(); | ||
112 | |||
113 | current_thread_info()->status &= ~TS_POLLING; | 111 | current_thread_info()->status &= ~TS_POLLING; |
114 | smp_mb__after_clear_bit(); | 112 | smp_mb__after_clear_bit(); |
115 | while (!need_resched()) { | 113 | local_irq_disable(); |
116 | local_irq_disable(); | 114 | if (!need_resched()) { |
117 | if (!need_resched()) | 115 | /* Enables interrupts one instruction before HLT. |
118 | safe_halt(); | 116 | x86 special cases this so there is no race. */ |
119 | else | 117 | safe_halt(); |
120 | local_irq_enable(); | 118 | } else |
121 | } | 119 | local_irq_enable(); |
122 | current_thread_info()->status |= TS_POLLING; | 120 | current_thread_info()->status |= TS_POLLING; |
123 | } | 121 | } |
124 | 122 | ||
@@ -129,16 +127,7 @@ static void default_idle(void) | |||
129 | */ | 127 | */ |
130 | static void poll_idle (void) | 128 | static void poll_idle (void) |
131 | { | 129 | { |
132 | local_irq_enable(); | 130 | cpu_relax(); |
133 | |||
134 | asm volatile( | ||
135 | "2:" | ||
136 | "testl %0,%1;" | ||
137 | "rep; nop;" | ||
138 | "je 2b;" | ||
139 | : : | ||
140 | "i" (_TIF_NEED_RESCHED), | ||
141 | "m" (current_thread_info()->flags)); | ||
142 | } | 131 | } |
143 | 132 | ||
144 | void cpu_idle_wait(void) | 133 | void cpu_idle_wait(void) |
@@ -257,8 +246,7 @@ void mwait_idle_with_hints(unsigned long eax, unsigned long ecx) | |||
257 | static void mwait_idle(void) | 246 | static void mwait_idle(void) |
258 | { | 247 | { |
259 | local_irq_enable(); | 248 | local_irq_enable(); |
260 | while (!need_resched()) | 249 | mwait_idle_with_hints(0,0); |
261 | mwait_idle_with_hints(0,0); | ||
262 | } | 250 | } |
263 | 251 | ||
264 | void __cpuinit select_idle_routine(const struct cpuinfo_x86 *c) | 252 | void __cpuinit select_idle_routine(const struct cpuinfo_x86 *c) |