From: Nicolas Pitre <hidden> Date: 2014-01-29 17:45:23
As everyone should know by now, we want to integrate the cpuidle
governor with the scheduler for a more efficient idling of CPUs.
In order to help the transition, this small patch series moves the
existing interaction with cpuidle from architecture code to generic
core code. The ARM, PPC, SH and X86 architectures are concerned.
No functional change should have occurred yet.
@peterz: Are you willing to pick up those patches?
Change from v1:
- dropped removal of arch_cpu_idle_prepare()
arch/arm/kernel/process.c | 16 +++------
arch/powerpc/platforms/pseries/processor_idle.c | 5 +++
arch/powerpc/platforms/pseries/setup.c | 34 ++++++++-----------
arch/sh/kernel/idle.c | 4 +--
arch/x86/kernel/process.c | 5 +--
kernel/Makefile | 1 -
kernel/cpu/Makefile | 1 -
kernel/sched/Makefile | 2 +-
kernel/{cpu => sched}/idle.c | 4 ++-
9 files changed, 30 insertions(+), 42 deletions(-)
Nicolas
From: Nicolas Pitre <hidden> Date: 2014-01-29 17:45:24
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
---
kernel/cpu/idle.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
From: Nicolas Pitre <hidden> Date: 2014-01-29 17:45:26
The core idle loop now takes care of it.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
---
arch/arm/kernel/process.c | 16 +++++-----------
1 file changed, 5 insertions(+), 11 deletions(-)
From: Nicolas Pitre <hidden> Date: 2014-01-29 17:45:27
The core idle loop now takes care of it.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
---
arch/sh/kernel/idle.c | 4 +---
1 file changed, 1 insertion(+), 3 deletions(-)
From: Nicolas Pitre <hidden> Date: 2014-01-29 17:46:13
Integration of cpuidle with the scheduler requires that the idle loop be
closely integrated with the scheduler proper. Moving cpu/idle.c into the
sched directory will allow for a smoother integration, and eliminate a
subdirectory which contained only one source file.
Signed-off-by: Nicolas Pitre <redacted>
---
kernel/Makefile | 1 -
kernel/cpu/Makefile | 1 -
kernel/sched/Makefile | 2 +-
kernel/{cpu => sched}/idle.c | 0
4 files changed, 1 insertion(+), 3 deletions(-)
delete mode 100644 kernel/cpu/Makefile
rename kernel/{cpu => sched}/idle.c (100%)
diff --git a/kernel/cpu/idle.c b/kernel/sched/idle.csimilarity index 100%rename from kernel/cpu/idle.crename to kernel/sched/idle.c
--
1.8.4.108.g55ea5f6
From: Nicolas Pitre <hidden> Date: 2014-01-29 17:46:40
The core idle loop now takes care of it.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
---
arch/x86/kernel/process.c | 5 +----
1 file changed, 1 insertion(+), 4 deletions(-)
From: Nicolas Pitre <hidden> Date: 2014-01-29 17:47:00
The core idle loop now takes care of it. However a few things need
checking:
- Invocation of cpuidle_idle_call() in pseries_lpar_idle() happened
through arch_cpu_idle() and was therefore always preceded by a call
to ppc64_runlatch_off(). To preserve this property now that
cpuidle_idle_call() is invoked directly from core code, a call to
ppc64_runlatch_off() has been added to idle_loop_prolog() in
platforms/pseries/processor_idle.c.
- Similarly, cpuidle_idle_call() was followed by ppc64_runlatch_off()
so a call to the later has been added to idle_loop_epilog().
- And since arch_cpu_idle() always made sure to re-enable IRQs if they
were not enabled, this is now
done in idle_loop_epilog() as well.
The above was made in order to keep the execution flow close to the
original. I don't know if that was strictly necessary. Someone well
aquainted with the platform details might find some room for possible
optimizations.
Signed-off-by: Nicolas Pitre <redacted>
Reviewed-by: Preeti U Murthy <redacted>
---
arch/powerpc/platforms/pseries/processor_idle.c | 5 ++++
arch/powerpc/platforms/pseries/setup.c | 34 ++++++++++---------------
2 files changed, 19 insertions(+), 20 deletions(-)
@@ -356,29 +355,24 @@ early_initcall(alloc_dispatch_log_kmem_cache);staticvoidpseries_lpar_idle(void){-/* This would call on the cpuidle framework, and the back-end pseries-*drivertogotoidlestates+/*+*Defaulthandlertogointolowthreadpriorityandpossibly+*lowpowermodebycedeingprocessortohypervisor*/-if(cpuidle_idle_call()){-/* On error, execute default handler-*togointolowthreadpriorityandpossibly-*lowpowermodebycedeingprocessortohypervisor-*/-/* Indicate to hypervisor that we are idle. */-get_lppaca()->idle=1;+/* Indicate to hypervisor that we are idle. */+get_lppaca()->idle=1;-/*-*Yieldtheprocessortothehypervisor.Wereturnif-*anexternalinterruptoccurs(whicharedrivenprior-*toreturninghere)orifaprodoccursfromanother-*processor.Whenreturninghere,externalinterrupts-*areenabled.-*/-cede_processor();+/*+*Yieldtheprocessortothehypervisor.Wereturnif+*anexternalinterruptoccurs(whicharedrivenprior+*toreturninghere)orifaprodoccursfromanother+*processor.Whenreturninghere,externalinterrupts+*areenabled.+*/+cede_processor();-get_lppaca()->idle=0;-}+get_lppaca()->idle=0;}/*
From: Olof Johansson <hidden> Date: 2014-01-29 19:02:32
Hi,
On Wed, Jan 29, 2014 at 9:45 AM, Nicolas Pitre [off-list ref] wrote:
quoted hunk
The core idle loop now takes care of it.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
---
arch/x86/kernel/process.c | 5 +----
1 file changed, 1 insertion(+), 4 deletions(-)
You're taking out the local_irq_enable() here but I don't see the
equivalent of adding it back in the 1/6 patch that moves the
cpuidle_idle_call() up to common code. It seems that one of the call
paths through cpuidle_idle_call() don't re-enable it on its own.
Even if this is the right thing to do, why it's OK to do so should
probably be documented in the patch description.
-Olof
From: Nicolas Pitre <hidden> Date: 2014-01-29 20:14:45
On Wed, 29 Jan 2014, Olof Johansson wrote:
Hi,
On Wed, Jan 29, 2014 at 9:45 AM, Nicolas Pitre [off-list ref] wrote:
quoted
The core idle loop now takes care of it.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
---
arch/x86/kernel/process.c | 5 +----
1 file changed, 1 insertion(+), 4 deletions(-)
You're taking out the local_irq_enable() here but I don't see the
equivalent of adding it back in the 1/6 patch that moves the
cpuidle_idle_call() up to common code. It seems that one of the call
paths through cpuidle_idle_call() don't re-enable it on its own.
When cpuidle_idle_call() returns non-zero, IRQs are left disabled. When
it returns zero then IRQs should be disabled. Same goes for cpuidle
drivers. That's the theory at least.
Looking into some cpuidle drivers for x86 I found at least one that
doesn't respect this convention. Damn.
Even if this is the right thing to do, why it's OK to do so should
probably be documented in the patch description.
Better yet, I'm going to amend patch 1/6 with the below to make things
more reliable while still identifying misbehaving drivers.
From: Nicolas Pitre <hidden> Date: 2014-01-29 20:31:42
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
allowing for the warning to trig.
Signed-off-by: Nicolas Pitre <redacted>
From: Preeti U Murthy <hidden> Date: 2014-01-30 03:42:26
Hi Nicolas,
On 01/30/2014 02:01 AM, Nicolas Pitre wrote:
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
quoted
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
Why would this patch allow for removing the forced IRQ enable that are
being done on some archs in arch_cpu_idle()? Isn't this patch expecting
the default arch_cpu_idle() to have re-enabled the interrupts after
exiting from the default idle state? Its supposed to only catch faulty
cpuidle drivers that haven't enabled IRQs on exit from idle state but
are expected to have done so, isn't it?
Thanks
Regards
Preeti U Murthy
quoted hunk
allowing for the warning to trig.
Signed-off-by: Nicolas Pitre <redacted>
From: Nicolas Pitre <hidden> Date: 2014-01-30 05:28:09
On Thu, 30 Jan 2014, Preeti U Murthy wrote:
Hi Nicolas,
On 01/30/2014 02:01 AM, Nicolas Pitre wrote:
quoted
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
quoted
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
Why would this patch allow for removing the forced IRQ enable that are
being done on some archs in arch_cpu_idle()? Isn't this patch expecting
the default arch_cpu_idle() to have re-enabled the interrupts after
exiting from the default idle state? Its supposed to only catch faulty
cpuidle drivers that haven't enabled IRQs on exit from idle state but
are expected to have done so, isn't it?
Exact. However x86 currently does this:
if (cpuidle_idle_call())
x86_idle();
else
local_irq_enable();
So whenever cpuidle_idle_call() is successful then IRQs are
unconditionally enabled whether or not the underlying cpuidle driver has
properly done it or not. And the reason is that some of the x86 cpuidle
do fail to enable IRQs before returning.
So the idea is to get rid of this unconditional IRQ enabling and let the
core issue a warning instead (as well as enabling IRQs to allow the
system to run).
Nicolas
From: Preeti U Murthy <hidden> Date: 2014-01-30 05:53:57
Hi Nicolas,
On 01/30/2014 10:58 AM, Nicolas Pitre wrote:
On Thu, 30 Jan 2014, Preeti U Murthy wrote:
quoted
Hi Nicolas,
On 01/30/2014 02:01 AM, Nicolas Pitre wrote:
quoted
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
quoted
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
Why would this patch allow for removing the forced IRQ enable that are
being done on some archs in arch_cpu_idle()? Isn't this patch expecting
the default arch_cpu_idle() to have re-enabled the interrupts after
exiting from the default idle state? Its supposed to only catch faulty
cpuidle drivers that haven't enabled IRQs on exit from idle state but
are expected to have done so, isn't it?
Exact. However x86 currently does this:
if (cpuidle_idle_call())
x86_idle();
else
local_irq_enable();
So whenever cpuidle_idle_call() is successful then IRQs are
unconditionally enabled whether or not the underlying cpuidle driver has
properly done it or not. And the reason is that some of the x86 cpuidle
do fail to enable IRQs before returning.
So the idea is to get rid of this unconditional IRQ enabling and let the
core issue a warning instead (as well as enabling IRQs to allow the
system to run).
Oh ok, thank you for clarifying this:)
Regards
Preeti U Murthy
From: Peter Zijlstra <peterz@infradead.org> Date: 2014-01-30 09:29:06
On Wed, Jan 29, 2014 at 12:45:07PM -0500, Nicolas Pitre wrote:
As everyone should know by now, we want to integrate the cpuidle
governor with the scheduler for a more efficient idling of CPUs.
In order to help the transition, this small patch series moves the
existing interaction with cpuidle from architecture code to generic
core code. The ARM, PPC, SH and X86 architectures are concerned.
No functional change should have occurred yet.
@peterz: Are you willing to pick up those patches?
Yeah.. no objections. Should I pick these up or will you be sending
another round?
From: Nicolas Pitre <hidden> Date: 2014-01-30 13:31:57
On Thu, 30 Jan 2014, Peter Zijlstra wrote:
On Wed, Jan 29, 2014 at 12:45:07PM -0500, Nicolas Pitre wrote:
quoted
As everyone should know by now, we want to integrate the cpuidle
governor with the scheduler for a more efficient idling of CPUs.
In order to help the transition, this small patch series moves the
existing interaction with cpuidle from architecture code to generic
core code. The ARM, PPC, SH and X86 architectures are concerned.
No functional change should have occurred yet.
@peterz: Are you willing to pick up those patches?
Yeah.. no objections. Should I pick these up or will you be sending
another round?
I think you could pick them now, taking care of picking up the amended
#1/6.
Nicolas
From: Daniel Lezcano <hidden> Date: 2014-01-30 13:44:04
On 01/30/2014 06:28 AM, Nicolas Pitre wrote:
On Thu, 30 Jan 2014, Preeti U Murthy wrote:
quoted
Hi Nicolas,
On 01/30/2014 02:01 AM, Nicolas Pitre wrote:
quoted
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
quoted
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
Why would this patch allow for removing the forced IRQ enable that are
being done on some archs in arch_cpu_idle()? Isn't this patch expecting
the default arch_cpu_idle() to have re-enabled the interrupts after
exiting from the default idle state? Its supposed to only catch faulty
cpuidle drivers that haven't enabled IRQs on exit from idle state but
are expected to have done so, isn't it?
Exact. However x86 currently does this:
if (cpuidle_idle_call())
x86_idle();
else
local_irq_enable();
So whenever cpuidle_idle_call() is successful then IRQs are
unconditionally enabled whether or not the underlying cpuidle driver has
properly done it or not. And the reason is that some of the x86 cpuidle
do fail to enable IRQs before returning.
So the idea is to get rid of this unconditional IRQ enabling and let the
core issue a warning instead (as well as enabling IRQs to allow the
system to run).
But what I don't get with your comment is the local_irq_enable is done
from the cpuidle common framework in 'cpuidle_enter_state' it is not
done from the arch specific backend cpuidle driver.
So the code above could be:
if (cpuidle_idle_call())
x86_idle();
without the else section, this local_irq_enable is pointless. Or may be
I missed something ?
--
<http://www.linaro.org/> Linaro.org │ Open source software for ARM SoCs
Follow Linaro: <http://www.facebook.com/pages/Linaro> Facebook |
<http://twitter.com/#!/linaroorg> Twitter |
<http://www.linaro.org/linaro-blog/> Blog
From: Peter Zijlstra <peterz@infradead.org> Date: 2014-01-30 15:25:36
On Wed, Jan 29, 2014 at 12:45:13PM -0500, Nicolas Pitre wrote:
Integration of cpuidle with the scheduler requires that the idle loop be
closely integrated with the scheduler proper. Moving cpu/idle.c into the
sched directory will allow for a smoother integration, and eliminate a
subdirectory which contained only one source file.
Signed-off-by: Nicolas Pitre <redacted>
---
kernel/Makefile | 1 -
kernel/cpu/Makefile | 1 -
kernel/sched/Makefile | 2 +-
kernel/{cpu => sched}/idle.c | 0
4 files changed, 1 insertion(+), 3 deletions(-)
delete mode 100644 kernel/cpu/Makefile
rename kernel/{cpu => sched}/idle.c (100%)
From: Nicolas Pitre <hidden> Date: 2014-01-30 16:03:36
On Thu, 30 Jan 2014, Peter Zijlstra wrote:
On Wed, Jan 29, 2014 at 12:45:13PM -0500, Nicolas Pitre wrote:
quoted
Integration of cpuidle with the scheduler requires that the idle loop be
closely integrated with the scheduler proper. Moving cpu/idle.c into the
sched directory will allow for a smoother integration, and eliminate a
subdirectory which contained only one source file.
Signed-off-by: Nicolas Pitre <redacted>
---
kernel/Makefile | 1 -
kernel/cpu/Makefile | 1 -
kernel/sched/Makefile | 2 +-
kernel/{cpu => sched}/idle.c | 0
4 files changed, 1 insertion(+), 3 deletions(-)
delete mode 100644 kernel/cpu/Makefile
rename kernel/{cpu => sched}/idle.c (100%)
diff --git a/kernel/cpu/idle.c b/kernel/sched/idle.csimilarity index 100%rename from kernel/cpu/idle.crename to kernel/sched/idle.c
This is not a valid patch for PATCH(1). Please try again.
Don't you use git? ;-)
Here's a plain patch:
----- >8
From 1bf40eb80a44633094e94986a74bd5ffa222f9d4 Mon Sep 17 00:00:00 2001
From: Nicolas Pitre <redacted>
Date: Sun, 26 Jan 2014 23:42:01 -0500
Subject: [PATCH] cpu/idle.c: move to sched/idle.c
Integration of cpuidle with the scheduler requires that the idle loop be
closely integrated with the scheduler proper. Moving cpu/idle.c into the
sched directory will allow for a smoother integration, and eliminate a
subdirectory which contained only one source file.
Signed-off-by: Nicolas Pitre <redacted>
---
kernel/Makefile | 1 -
kernel/cpu/Makefile | 1 -
kernel/cpu/idle.c | 144 --------------------------------------------------
kernel/sched/Makefile | 2 +-
kernel/sched/idle.c | 144 ++++++++++++++++++++++++++++++++++++++++++++++++++
5 files changed, 145 insertions(+), 147 deletions(-)
delete mode 100644 kernel/cpu/Makefile
delete mode 100644 kernel/cpu/idle.c
create mode 100644 kernel/sched/idle.c
@@ -1,144 +0,0 @@-/*- * Generic entry point for the idle threads- */-#include <linux/sched.h>-#include <linux/cpu.h>-#include <linux/cpuidle.h>-#include <linux/tick.h>-#include <linux/mm.h>-#include <linux/stackprotector.h>--#include <asm/tlb.h>--#include <trace/events/power.h>--static int __read_mostly cpu_idle_force_poll;--void cpu_idle_poll_ctrl(bool enable)-{- if (enable) {- cpu_idle_force_poll++;- } else {- cpu_idle_force_poll--;- WARN_ON_ONCE(cpu_idle_force_poll < 0);- }-}--#ifdef CONFIG_GENERIC_IDLE_POLL_SETUP-static int __init cpu_idle_poll_setup(char *__unused)-{- cpu_idle_force_poll = 1;- return 1;-}-__setup("nohlt", cpu_idle_poll_setup);--static int __init cpu_idle_nopoll_setup(char *__unused)-{- cpu_idle_force_poll = 0;- return 1;-}-__setup("hlt", cpu_idle_nopoll_setup);-#endif--static inline int cpu_idle_poll(void)-{- rcu_idle_enter();- trace_cpu_idle_rcuidle(0, smp_processor_id());- local_irq_enable();- while (!tif_need_resched())- cpu_relax();- trace_cpu_idle_rcuidle(PWR_EVENT_EXIT, smp_processor_id());- rcu_idle_exit();- return 1;-}--/* Weak implementations for optional arch specific functions */-void __weak arch_cpu_idle_prepare(void) { }-void __weak arch_cpu_idle_enter(void) { }-void __weak arch_cpu_idle_exit(void) { }-void __weak arch_cpu_idle_dead(void) { }-void __weak arch_cpu_idle(void)-{- cpu_idle_force_poll = 1;- local_irq_enable();-}--/*- * Generic idle loop implementation- */-static void cpu_idle_loop(void)-{- while (1) {- tick_nohz_idle_enter();-- while (!need_resched()) {- check_pgt_cache();- rmb();-- if (cpu_is_offline(smp_processor_id()))- arch_cpu_idle_dead();-- local_irq_disable();- arch_cpu_idle_enter();-- /*- * In poll mode we reenable interrupts and spin.- *- * Also if we detected in the wakeup from idle- * path that the tick broadcast device expired- * for us, we don't want to go deep idle as we- * know that the IPI is going to arrive right- * away- */- if (cpu_idle_force_poll || tick_check_broadcast_expired()) {- cpu_idle_poll();- } else {- if (!current_clr_polling_and_test()) {- stop_critical_timings();- rcu_idle_enter();- if (cpuidle_idle_call())- arch_cpu_idle();- if (WARN_ON_ONCE(irqs_disabled()))- local_irq_enable();- rcu_idle_exit();- start_critical_timings();- } else {- local_irq_enable();- }- __current_set_polling();- }- arch_cpu_idle_exit();- /*- * We need to test and propagate the TIF_NEED_RESCHED- * bit here because we might not have send the- * reschedule IPI to idle tasks.- */- if (tif_need_resched())- set_preempt_need_resched();- }- tick_nohz_idle_exit();- schedule_preempt_disabled();- }-}--void cpu_startup_entry(enum cpuhp_state state)-{- /*- * This #ifdef needs to die, but it's too late in the cycle to- * make this generic (arm and sh have never invoked the canary- * init for the non boot cpus!). Will be fixed in 3.11- */-#ifdef CONFIG_X86- /*- * If we're the non-boot CPU, nothing set the stack canary up- * for us. The boot CPU already has it initialized but no harm- * in doing it again. This is a good place for updating it, as- * we wont ever return from this function (so the invalid- * canaries already on the stack wont ever trigger).- */- boot_init_stack_canary();-#endif- __current_set_polling();- arch_cpu_idle_prepare();- cpu_idle_loop();-}
From: Nicolas Pitre <hidden> Date: 2014-01-30 16:07:54
On Thu, 30 Jan 2014, Daniel Lezcano wrote:
On 01/30/2014 06:28 AM, Nicolas Pitre wrote:
quoted
On Thu, 30 Jan 2014, Preeti U Murthy wrote:
quoted
Hi Nicolas,
On 01/30/2014 02:01 AM, Nicolas Pitre wrote:
quoted
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
quoted
In order to integrate cpuidle with the scheduler, we must have a
better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
Why would this patch allow for removing the forced IRQ enable that are
being done on some archs in arch_cpu_idle()? Isn't this patch expecting
the default arch_cpu_idle() to have re-enabled the interrupts after
exiting from the default idle state? Its supposed to only catch faulty
cpuidle drivers that haven't enabled IRQs on exit from idle state but
are expected to have done so, isn't it?
Exact. However x86 currently does this:
if (cpuidle_idle_call())
x86_idle();
else
local_irq_enable();
So whenever cpuidle_idle_call() is successful then IRQs are
unconditionally enabled whether or not the underlying cpuidle driver has
properly done it or not. And the reason is that some of the x86 cpuidle
do fail to enable IRQs before returning.
So the idea is to get rid of this unconditional IRQ enabling and let the
core issue a warning instead (as well as enabling IRQs to allow the
system to run).
But what I don't get with your comment is the local_irq_enable is done from
the cpuidle common framework in 'cpuidle_enter_state' it is not done from the
arch specific backend cpuidle driver.
Oh well... This certainly means we'll have to clean this mess as some
drivers do it on their own while some others don't. Some drivers also
loop on !need_resched() while some others simply return on the first
interrupt.
So the code above could be:
if (cpuidle_idle_call())
x86_idle();
without the else section, this local_irq_enable is pointless. Or may be I
missed something ?
A later patch removes it anyway. But if it is really necessary to
enable interrupts then the core will do it but with a warning now.
Nicolas
From: Joe Perches <joe@perches.com> Date: 2014-01-30 16:41:25
On Thu, 2014-01-30 at 17:27 +0100, Peter Zijlstra wrote:
On Thu, Jan 30, 2014 at 11:03:31AM -0500, Nicolas Pitre wrote:
quoted
quoted
This is not a valid patch for PATCH(1). Please try again.
Don't you use git? ;-)
Nah, git and me don't get along well.
Perhaps you could use a newer version of patch
http://savannah.gnu.org/forum/forum.php?forum_id=7361
GNU patch version 2.7 released
Item posted by Andreas Gruenbacher <agruen> on Wed 12 Sep 2012 02:18:14
PM UTC.
I am pleased to announce that version 2.7 of GNU patch has been
released. The following significant changes have happened since the last
stable release in December 2009:
* Support for most features of the "diff --git" format, including
renames and copies, permission changes, and symlink diffs.
Binary diffs are not supported yet; patch will complain and skip
them.
From: Daniel Lezcano <hidden> Date: 2014-01-30 17:28:54
On 01/30/2014 05:07 PM, Nicolas Pitre wrote:
On Thu, 30 Jan 2014, Daniel Lezcano wrote:
quoted
On 01/30/2014 06:28 AM, Nicolas Pitre wrote:
quoted
On Thu, 30 Jan 2014, Preeti U Murthy wrote:
quoted
Hi Nicolas,
On 01/30/2014 02:01 AM, Nicolas Pitre wrote:
quoted
On Wed, 29 Jan 2014, Nicolas Pitre wrote:
quoted
In order to integrate cpuidle with the scheduler, we must have a
better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
Signed-off-by: Nicolas Pitre <redacted>
Acked-by: Daniel Lezcano <redacted>
As mentioned in my reply to Olof's comment on patch #5/6, here's a new
version of this patch adding the safety local_irq_enable() to the core
code.
----- >8
From: Nicolas Pitre <redacted>
Subject: idle: move the cpuidle entry point to the generic idle loop
In order to integrate cpuidle with the scheduler, we must have a better
proximity in the core code with what cpuidle is doing and not delegate
such interaction to arch code.
Architectures implementing arch_cpu_idle() should simply enter
a cheap idle mode in the absence of a proper cpuidle driver.
In both cases i.e. whether it is a cpuidle driver or the default
arch_cpu_idle(), the calling convention expects IRQs to be disabled
on entry and enabled on exit. There is a warning in place already but
let's add a forced IRQ enable here as well. This will allow for
removing the forced IRQ enable some implementations do locally and
Why would this patch allow for removing the forced IRQ enable that are
being done on some archs in arch_cpu_idle()? Isn't this patch expecting
the default arch_cpu_idle() to have re-enabled the interrupts after
exiting from the default idle state? Its supposed to only catch faulty
cpuidle drivers that haven't enabled IRQs on exit from idle state but
are expected to have done so, isn't it?
Exact. However x86 currently does this:
if (cpuidle_idle_call())
x86_idle();
else
local_irq_enable();
So whenever cpuidle_idle_call() is successful then IRQs are
unconditionally enabled whether or not the underlying cpuidle driver has
properly done it or not. And the reason is that some of the x86 cpuidle
do fail to enable IRQs before returning.
So the idea is to get rid of this unconditional IRQ enabling and let the
core issue a warning instead (as well as enabling IRQs to allow the
system to run).
But what I don't get with your comment is the local_irq_enable is done from
the cpuidle common framework in 'cpuidle_enter_state' it is not done from the
arch specific backend cpuidle driver.
Oh well... This certainly means we'll have to clean this mess as some
drivers do it on their own while some others don't. Some drivers also
loop on !need_resched() while some others simply return on the first
interrupt.
Ok, I think the mess is coming from 'default_idle' which does not
re-enable the local_irq but used from different places like
amd_e400_idle and apm_cpu_idle.
void default_idle(void)
{
trace_cpu_idle_rcuidle(1, smp_processor_id());
safe_halt();
trace_cpu_idle_rcuidle(PWR_EVENT_EXIT, smp_processor_id());
}
Considering the system configured without cpuidle because this one
*always* enable the local irq, we have the different cases:
x86_idle = default_idle();
==> local_irq_enable is missing
x86_idle = amd_e400_idle();
==> it calls local_irq_disable(); but in the idle loop context where the
local irqs are already disabled.
==> if amd_e400_c1e_detected is true, the local_irq are enabled
==> otherwise no
==> default_idle is called from there and does not enable local_irqs
quoted
So the code above could be:
if (cpuidle_idle_call())
x86_idle();
without the else section, this local_irq_enable is pointless. Or may be I
missed something ?
A later patch removes it anyway. But if it is really necessary to
enable interrupts then the core will do it but with a warning now.
This WARN should disappear. It was there because it was up to the
backend cpuidle driver to enable the irq. But in the meantime, that was
consolidated into a single place in the cpuidle framework so no need to
try to catch errors.
What about (based on this patchset).
--
<http://www.linaro.org/> Linaro.org │ Open source software for ARM SoCs
Follow Linaro: <http://www.facebook.com/pages/Linaro> Facebook |
<http://twitter.com/#!/linaroorg> Twitter |
<http://www.linaro.org/linaro-blog/> Blog
From: Peter Zijlstra <peterz@infradead.org> Date: 2014-01-30 18:07:34
On Thu, Jan 30, 2014 at 06:28:52PM +0100, Daniel Lezcano wrote:
Ok, I think the mess is coming from 'default_idle' which does not re-enable
the local_irq but used from different places like amd_e400_idle and
apm_cpu_idle.
void default_idle(void)
{
trace_cpu_idle_rcuidle(1, smp_processor_id());
safe_halt();
trace_cpu_idle_rcuidle(PWR_EVENT_EXIT, smp_processor_id());
}
Considering the system configured without cpuidle because this one *always*
enable the local irq, we have the different cases:
x86_idle = default_idle();
==> local_irq_enable is missing
safe_halt() is "sti; hlt" and so very much does the irq_enable.
From: Nicolas Pitre <hidden> Date: 2014-01-30 19:24:24
On Thu, 30 Jan 2014, Daniel Lezcano wrote:
On 01/30/2014 05:07 PM, Nicolas Pitre wrote:
quoted
On Thu, 30 Jan 2014, Daniel Lezcano wrote:
quoted
But what I don't get with your comment is the local_irq_enable is done
from
the cpuidle common framework in 'cpuidle_enter_state' it is not done from
the
arch specific backend cpuidle driver.
Oh well... This certainly means we'll have to clean this mess as some
drivers do it on their own while some others don't. Some drivers also
loop on !need_resched() while some others simply return on the first
interrupt.
Ok, I think the mess is coming from 'default_idle' which does not re-enable
the local_irq but used from different places like amd_e400_idle and
apm_cpu_idle.
Yet if you look at the code path before my patches you'll see that IRQs
were enabled only after cpuidle_idle_call() had returned success.
void default_idle(void)
{
trace_cpu_idle_rcuidle(1, smp_processor_id());
safe_halt();
trace_cpu_idle_rcuidle(PWR_EVENT_EXIT, smp_processor_id());
}
Considering the system configured without cpuidle because this one *always*
enable the local irq,
Yet this is discutable. Given that some hardware do have IRQs turned on
upon exiting idle mode, I think we should generalize it so that
the explicit enabling
of IRQs, when needed, should be done as close as possible to the
operation that caused idle mode to be entered.
we have the different cases:
x86_idle = default_idle();
==> local_irq_enable is missing
According to Peter it is not.
x86_idle = amd_e400_idle();
==> it calls local_irq_disable(); but in the idle loop context where the
local irqs are already disabled.
Since it returned from default_idle() then IRQs are enabled.
==> if amd_e400_c1e_detected is true, the local_irq are enabled
==> otherwise no
==> default_idle is called from there and does not enable local_irqs
Again, it does.
quoted
quoted
So the code above could be:
if (cpuidle_idle_call())
x86_idle();
without the else section, this local_irq_enable is pointless. Or may be I
missed something ?
A later patch removes it anyway. But if it is really necessary to
enable interrupts then the core will do it but with a warning now.
This WARN should disappear. It was there because it was up to the backend
cpuidle driver to enable the irq. But in the meantime, that was consolidated
into a single place in the cpuidle framework so no need to try to catch
errors.
And that consolidation was a mistake IMHO. We should assume that the
exiting of idle mode has IRQs enabled already, and do so manually in the
backend driver if it is not the case on particular hardware. That's the
only way to ensure uniformity at a higher level.
Yet, if a code path is buggy in that regard, whether this is through
cpuidle when enabled, or the default idle function otherwise, then the
warning is there in cpu_idle_loop() to catch them all.
From: Nicolas Pitre <hidden> Date: 2014-02-06 14:10:08
On Thu, 30 Jan 2014, Peter Zijlstra wrote:
On Thu, Jan 30, 2014 at 11:03:31AM -0500, Nicolas Pitre wrote:
quoted
quoted
This is not a valid patch for PATCH(1). Please try again.
Don't you use git? ;-)
Nah, git and me don't get along well.
quoted
Here's a plain patch:
Thanks!
Hi Peter,
Did you merge those patches in your tree? If so, is it published
somewhere? That would be a good idea if that could appear in linux-next
so to prevent people from adding more calls to cpuidle_idle_call() from
architecture code. I'm sending you 2 additional patches right away to
remove those that appeared in v3.14-rc1.
Nicolas
From: Peter Zijlstra <peterz@infradead.org> Date: 2014-02-06 16:44:10
On Thu, Feb 06, 2014 at 02:09:59PM +0000, Nicolas Pitre wrote:
Hi Peter,
Did you merge those patches in your tree?
tree, tree, what's in a word. Its in my patch stack yes. I should get
some of that into tip I suppose, been side-tracked a bit this week.
Sorry for the delay.
That would be a good idea if that could appear in linux-next
so to prevent people from adding more calls to cpuidle_idle_call() from
architecture code. I'm sending you 2 additional patches right away to
remove those that appeared in v3.14-rc1.
Yeah, once they land in tip they'll end up in -next automagically. I'll
try and get that sorted tomorrow somewhere.
From: Nicolas Pitre <hidden> Date: 2014-02-07 11:09:28
On Thu, 6 Feb 2014, Peter Zijlstra wrote:
On Thu, Feb 06, 2014 at 02:09:59PM +0000, Nicolas Pitre wrote:
quoted
Hi Peter,
Did you merge those patches in your tree?
tree, tree, what's in a word.
Something you may plant on a patch of grass? "Merging" becomes a
strange concept in that context though. :-)
Its in my patch stack yes.
Quilt I suppose?? (yet another word.)
I should get some of that into tip I suppose, been side-tracked a bit
this week. Sorry for the delay.
If you prefer we pile those patches (and future ones after revew)
ourselves just let me know. Future patches are likely to be more
intimate with the scheduler so I just need to know who to upstream them
through afterwards.
Nicolas
From: Peter Zijlstra <peterz@infradead.org> Date: 2014-02-07 12:33:10
On Fri, Feb 07, 2014 at 11:09:23AM +0000, Nicolas Pitre wrote:
On Thu, 6 Feb 2014, Peter Zijlstra wrote:
quoted
tree, tree, what's in a word.
Something you may plant on a patch of grass? "Merging" becomes a
strange concept in that context though. :-)
I do know some farmers who splice trees thought :-)
quoted
Its in my patch stack yes.
Quilt I suppose?? (yet another word.)
Yes, I'm one of the refugee Quilt users. Comes in handy when cold too
:-)
quoted
I should get some of that into tip I suppose, been side-tracked a bit
this week. Sorry for the delay.
If you prefer we pile those patches (and future ones after revew)
ourselves just let me know. Future patches are likely to be more
intimate with the scheduler so I just need to know who to upstream them
through afterwards.
Normally I get Ingo to pick up the queue 1-2 times a week so latency
shouldn't be too bad. But we just had the merge window and then I got
side-tracked rewriting all atomic implementations.
So usually submit patches against tip/master unless you know there's
other pending bits that conflict, in which case you can grab my queue on
top of tip/master -- but I try to make sure that's usually not needed.