[PATCH v6 08/11] powerpc/powernv: Add platform support for stop instruction
POWER ISA v3 defines a new idle processor core mechanism. In summary, a) new instruction named stop is added. This instruction replaces instructions like nap, sleep, rvwinkle. b) new per thread SPR named Processor Stop Status and Control Register (PSSCR) is added which controls the behavior of stop instruction. PSSCR layout: -- | PLS | /// | SD | ESL | EC | PSLL | /// | TR | MTL | RL | -- 0 4 41 4243 44 4854 5660 PSSCR key fields: Bits 0:3 - Power-Saving Level Status. This field indicates the lowest power-saving state the thread entered since stop instruction was last executed. Bit 42 - Enable State Loss 0 - No state is lost irrespective of other fields 1 - Allows state loss Bits 44:47 - Power-Saving Level Limit This limits the power-saving level that can be entered into. Bits 60:63 - Requested Level Used to specify which power-saving level must be entered on executing stop instruction This patch adds support for stop instruction and PSSCR handling. Reviewed-by: Gautham R. ShenoySigned-off-by: Shreyas B. Prabhu --- Changes in v6 = - Save/restore new P9 SPRs when using deep idle states Changes in v4: == - Added PSSCR layout to commit message - Improved / Fixed comments - Fixed whitespace error in paca.h - Using MAX_POSSIBLE_STOP_STATE macro instead of hardcoding 0xF as max possible stop state Changes in v3: == - Instead of introducing new file idle_power_stop.S, P9 idle support is added to idle_power_common.S using CPU_FTR sections. - Fixed r4 reg clobbering in power_stop0 - Improved comments Changes in v2: == - Using CPU_FTR_ARCH_300 bit instead of CPU_FTR_STOP_INST arch/powerpc/include/asm/cpuidle.h| 2 + arch/powerpc/include/asm/kvm_book3s_asm.h | 2 +- arch/powerpc/include/asm/machdep.h| 1 + arch/powerpc/include/asm/opal-api.h | 11 +- arch/powerpc/include/asm/paca.h | 2 + arch/powerpc/include/asm/ppc-opcode.h | 4 + arch/powerpc/include/asm/processor.h | 1 + arch/powerpc/include/asm/reg.h| 14 +++ arch/powerpc/kernel/asm-offsets.c | 2 + arch/powerpc/kernel/idle_power_common.S | 175 +++--- arch/powerpc/platforms/powernv/idle.c | 84 -- 11 files changed, 265 insertions(+), 33 deletions(-) diff --git a/arch/powerpc/include/asm/cpuidle.h b/arch/powerpc/include/asm/cpuidle.h index d2f99ca..3d7fc06 100644 --- a/arch/powerpc/include/asm/cpuidle.h +++ b/arch/powerpc/include/asm/cpuidle.h @@ -13,6 +13,8 @@ #ifndef __ASSEMBLY__ extern u32 pnv_fastsleep_workaround_at_entry[]; extern u32 pnv_fastsleep_workaround_at_exit[]; + +extern u64 pnv_first_deep_stop_state; #endif #endif diff --git a/arch/powerpc/include/asm/kvm_book3s_asm.h b/arch/powerpc/include/asm/kvm_book3s_asm.h index 72b6225..d318d43 100644 --- a/arch/powerpc/include/asm/kvm_book3s_asm.h +++ b/arch/powerpc/include/asm/kvm_book3s_asm.h @@ -162,7 +162,7 @@ struct kvmppc_book3s_shadow_vcpu { /* Values for kvm_state */ #define KVM_HWTHREAD_IN_KERNEL 0 -#define KVM_HWTHREAD_IN_NAP1 +#define KVM_HWTHREAD_IN_IDLE 1 #define KVM_HWTHREAD_IN_KVM2 #endif /* __ASM_KVM_BOOK3S_ASM_H__ */ diff --git a/arch/powerpc/include/asm/machdep.h b/arch/powerpc/include/asm/machdep.h index 6bdcd0d..ae3b155 100644 --- a/arch/powerpc/include/asm/machdep.h +++ b/arch/powerpc/include/asm/machdep.h @@ -262,6 +262,7 @@ struct machdep_calls { extern void e500_idle(void); extern void power4_idle(void); extern void power7_idle(void); +extern void power_stop0(void); extern void ppc6xx_idle(void); extern void book3e_idle(void); diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/include/asm/opal-api.h index 9bb8ddf..7f3f8c6 100644 --- a/arch/powerpc/include/asm/opal-api.h +++ b/arch/powerpc/include/asm/opal-api.h @@ -162,13 +162,20 @@ /* Device tree flags */ -/* Flags set in power-mgmt nodes in device tree if - * respective idle states are supported in the platform. +/* + * Flags set in power-mgmt nodes in device tree describing + * idle states that are supported in the platform. */ + +#define OPAL_PM_TIMEBASE_STOP 0x0002 +#define OPAL_PM_LOSE_HYP_CONTEXT 0x2000 +#define OPAL_PM_LOSE_FULL_CONTEXT 0x4000 #define OPAL_PM_NAP_ENABLED0x0001 #define OPAL_PM_SLEEP_ENABLED 0x0002 #define OPAL_PM_WINKLE_ENABLED 0x0004 #define OPAL_PM_SLEEP_ENABLED_ER1 0x0008 /* with workaround */ +#define OPAL_PM_STOP_INST_FAST 0x0010 +#define OPAL_PM_STOP_INST_DEEP 0x0020 /* * OPAL_CONFIG_CPU_IDLE_STATE parameters diff --git
[PATCH v6 08/11] powerpc/powernv: Add platform support for stop instruction
POWER ISA v3 defines a new idle processor core mechanism. In summary, a) new instruction named stop is added. This instruction replaces instructions like nap, sleep, rvwinkle. b) new per thread SPR named Processor Stop Status and Control Register (PSSCR) is added which controls the behavior of stop instruction. PSSCR layout: -- | PLS | /// | SD | ESL | EC | PSLL | /// | TR | MTL | RL | -- 0 4 41 4243 44 4854 5660 PSSCR key fields: Bits 0:3 - Power-Saving Level Status. This field indicates the lowest power-saving state the thread entered since stop instruction was last executed. Bit 42 - Enable State Loss 0 - No state is lost irrespective of other fields 1 - Allows state loss Bits 44:47 - Power-Saving Level Limit This limits the power-saving level that can be entered into. Bits 60:63 - Requested Level Used to specify which power-saving level must be entered on executing stop instruction This patch adds support for stop instruction and PSSCR handling. Reviewed-by: Gautham R. Shenoy Signed-off-by: Shreyas B. Prabhu --- Changes in v6 = - Save/restore new P9 SPRs when using deep idle states Changes in v4: == - Added PSSCR layout to commit message - Improved / Fixed comments - Fixed whitespace error in paca.h - Using MAX_POSSIBLE_STOP_STATE macro instead of hardcoding 0xF as max possible stop state Changes in v3: == - Instead of introducing new file idle_power_stop.S, P9 idle support is added to idle_power_common.S using CPU_FTR sections. - Fixed r4 reg clobbering in power_stop0 - Improved comments Changes in v2: == - Using CPU_FTR_ARCH_300 bit instead of CPU_FTR_STOP_INST arch/powerpc/include/asm/cpuidle.h| 2 + arch/powerpc/include/asm/kvm_book3s_asm.h | 2 +- arch/powerpc/include/asm/machdep.h| 1 + arch/powerpc/include/asm/opal-api.h | 11 +- arch/powerpc/include/asm/paca.h | 2 + arch/powerpc/include/asm/ppc-opcode.h | 4 + arch/powerpc/include/asm/processor.h | 1 + arch/powerpc/include/asm/reg.h| 14 +++ arch/powerpc/kernel/asm-offsets.c | 2 + arch/powerpc/kernel/idle_power_common.S | 175 +++--- arch/powerpc/platforms/powernv/idle.c | 84 -- 11 files changed, 265 insertions(+), 33 deletions(-) diff --git a/arch/powerpc/include/asm/cpuidle.h b/arch/powerpc/include/asm/cpuidle.h index d2f99ca..3d7fc06 100644 --- a/arch/powerpc/include/asm/cpuidle.h +++ b/arch/powerpc/include/asm/cpuidle.h @@ -13,6 +13,8 @@ #ifndef __ASSEMBLY__ extern u32 pnv_fastsleep_workaround_at_entry[]; extern u32 pnv_fastsleep_workaround_at_exit[]; + +extern u64 pnv_first_deep_stop_state; #endif #endif diff --git a/arch/powerpc/include/asm/kvm_book3s_asm.h b/arch/powerpc/include/asm/kvm_book3s_asm.h index 72b6225..d318d43 100644 --- a/arch/powerpc/include/asm/kvm_book3s_asm.h +++ b/arch/powerpc/include/asm/kvm_book3s_asm.h @@ -162,7 +162,7 @@ struct kvmppc_book3s_shadow_vcpu { /* Values for kvm_state */ #define KVM_HWTHREAD_IN_KERNEL 0 -#define KVM_HWTHREAD_IN_NAP1 +#define KVM_HWTHREAD_IN_IDLE 1 #define KVM_HWTHREAD_IN_KVM2 #endif /* __ASM_KVM_BOOK3S_ASM_H__ */ diff --git a/arch/powerpc/include/asm/machdep.h b/arch/powerpc/include/asm/machdep.h index 6bdcd0d..ae3b155 100644 --- a/arch/powerpc/include/asm/machdep.h +++ b/arch/powerpc/include/asm/machdep.h @@ -262,6 +262,7 @@ struct machdep_calls { extern void e500_idle(void); extern void power4_idle(void); extern void power7_idle(void); +extern void power_stop0(void); extern void ppc6xx_idle(void); extern void book3e_idle(void); diff --git a/arch/powerpc/include/asm/opal-api.h b/arch/powerpc/include/asm/opal-api.h index 9bb8ddf..7f3f8c6 100644 --- a/arch/powerpc/include/asm/opal-api.h +++ b/arch/powerpc/include/asm/opal-api.h @@ -162,13 +162,20 @@ /* Device tree flags */ -/* Flags set in power-mgmt nodes in device tree if - * respective idle states are supported in the platform. +/* + * Flags set in power-mgmt nodes in device tree describing + * idle states that are supported in the platform. */ + +#define OPAL_PM_TIMEBASE_STOP 0x0002 +#define OPAL_PM_LOSE_HYP_CONTEXT 0x2000 +#define OPAL_PM_LOSE_FULL_CONTEXT 0x4000 #define OPAL_PM_NAP_ENABLED0x0001 #define OPAL_PM_SLEEP_ENABLED 0x0002 #define OPAL_PM_WINKLE_ENABLED 0x0004 #define OPAL_PM_SLEEP_ENABLED_ER1 0x0008 /* with workaround */ +#define OPAL_PM_STOP_INST_FAST 0x0010 +#define OPAL_PM_STOP_INST_DEEP 0x0020 /* * OPAL_CONFIG_CPU_IDLE_STATE parameters diff --git a/arch/powerpc/include/asm/paca.h b/arch/powerpc/include/asm/paca.h index