Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

powernv:idle: Add IDLE_STATE_ENTER_SEQ_NORET macro

Currently all the low-power idle states are expected to wake up
at reset vector 0x100. Which is why the macro IDLE_STATE_ENTER_SEQ
that puts the CPU to an idle state and never returns.

On ISA v3.0, when the ESL and EC bits in the PSSCR are zero, the CPU
is expected to wake up at the next instruction of the idle
instruction.

This patch adds a new macro named IDLE_STATE_ENTER_SEQ_NORET for the
no-return variant and reuses the name IDLE_STATE_ENTER_SEQ
for a variant that allows resuming operation at the instruction next
to the idle-instruction.

Acked-by: Balbir Singh <bsingharora@gmail.com>
Signed-off-by: Gautham R. Shenoy <ego@linux.vnet.ibm.com>
Signed-off-by: Michael Ellerman <mpe@ellerman.id.au>

authored by

Gautham R. Shenoy and committed by
Michael Ellerman
823b7bd5 616badd2

+12 -9
+4 -1
arch/powerpc/include/asm/cpuidle.h
··· 21 21 22 22 /* Idle state entry routines */ 23 23 #ifdef CONFIG_PPC_P7_NAP 24 - #define IDLE_STATE_ENTER_SEQ(IDLE_INST) \ 24 + #define IDLE_STATE_ENTER_SEQ(IDLE_INST) \ 25 25 /* Magic NAP/SLEEP/WINKLE mode enter sequence */ \ 26 26 std r0,0(r1); \ 27 27 ptesync; \ ··· 29 29 1: cmpd cr0,r0,r0; \ 30 30 bne 1b; \ 31 31 IDLE_INST; \ 32 + 33 + #define IDLE_STATE_ENTER_SEQ_NORET(IDLE_INST) \ 34 + IDLE_STATE_ENTER_SEQ(IDLE_INST) \ 32 35 b . 33 36 #endif /* CONFIG_PPC_P7_NAP */ 34 37
+3 -3
arch/powerpc/kernel/exceptions-64s.S
··· 381 381 lbz r3,PACA_THREAD_IDLE_STATE(r13) 382 382 cmpwi r3,PNV_THREAD_NAP 383 383 bgt 10f 384 - IDLE_STATE_ENTER_SEQ(PPC_NAP) 384 + IDLE_STATE_ENTER_SEQ_NORET(PPC_NAP) 385 385 /* No return */ 386 386 10: 387 387 cmpwi r3,PNV_THREAD_SLEEP 388 388 bgt 2f 389 - IDLE_STATE_ENTER_SEQ(PPC_SLEEP) 389 + IDLE_STATE_ENTER_SEQ_NORET(PPC_SLEEP) 390 390 /* No return */ 391 391 392 392 2: ··· 400 400 */ 401 401 ori r13,r13,1 402 402 SET_PACA(r13) 403 - IDLE_STATE_ENTER_SEQ(PPC_WINKLE) 403 + IDLE_STATE_ENTER_SEQ_NORET(PPC_WINKLE) 404 404 /* No return */ 405 405 4: 406 406 #endif
+5 -5
arch/powerpc/kernel/idle_book3s.S
··· 205 205 stb r3,PACA_THREAD_IDLE_STATE(r13) 206 206 cmpwi cr3,r3,PNV_THREAD_SLEEP 207 207 bge cr3,2f 208 - IDLE_STATE_ENTER_SEQ(PPC_NAP) 208 + IDLE_STATE_ENTER_SEQ_NORET(PPC_NAP) 209 209 /* No return */ 210 210 2: 211 211 /* Sleep or winkle */ ··· 239 239 240 240 common_enter: /* common code for all the threads entering sleep or winkle */ 241 241 bgt cr3,enter_winkle 242 - IDLE_STATE_ENTER_SEQ(PPC_SLEEP) 242 + IDLE_STATE_ENTER_SEQ_NORET(PPC_SLEEP) 243 243 244 244 fastsleep_workaround_at_entry: 245 245 ori r15,r15,PNV_CORE_IDLE_LOCK_BIT ··· 261 261 enter_winkle: 262 262 bl save_sprs_to_stack 263 263 264 - IDLE_STATE_ENTER_SEQ(PPC_WINKLE) 264 + IDLE_STATE_ENTER_SEQ_NORET(PPC_WINKLE) 265 265 266 266 /* 267 267 * r3 - requested stop state ··· 280 280 ld r4,ADDROFF(pnv_first_deep_stop_state)(r5) 281 281 cmpd r3,r4 282 282 bge 2f 283 - IDLE_STATE_ENTER_SEQ(PPC_STOP) 283 + IDLE_STATE_ENTER_SEQ_NORET(PPC_STOP) 284 284 2: 285 285 /* 286 286 * Entering deep idle state. ··· 302 302 303 303 bl save_sprs_to_stack 304 304 305 - IDLE_STATE_ENTER_SEQ(PPC_STOP) 305 + IDLE_STATE_ENTER_SEQ_NORET(PPC_STOP) 306 306 307 307 _GLOBAL(power7_idle) 308 308 /* Now check if user or arch enabled NAP mode */