aboutsummaryrefslogtreecommitdiffstats
path: root/arch/powerpc/kernel/head_64.S
diff options
context:
space:
mode:
Diffstat (limited to 'arch/powerpc/kernel/head_64.S')
-rw-r--r--arch/powerpc/kernel/head_64.S49
1 files changed, 48 insertions, 1 deletions
diff --git a/arch/powerpc/kernel/head_64.S b/arch/powerpc/kernel/head_64.S
index a5ae04a57c78..b7d140430a41 100644
--- a/arch/powerpc/kernel/head_64.S
+++ b/arch/powerpc/kernel/head_64.S
@@ -376,11 +376,28 @@ label##_common: \
376 bl hdlr; \ 376 bl hdlr; \
377 b .ret_from_except 377 b .ret_from_except
378 378
379/*
380 * Like STD_EXCEPTION_COMMON, but for exceptions that can occur
381 * in the idle task and therefore need the special idle handling.
382 */
383#define STD_EXCEPTION_COMMON_IDLE(trap, label, hdlr) \
384 .align 7; \
385 .globl label##_common; \
386label##_common: \
387 EXCEPTION_PROLOG_COMMON(trap, PACA_EXGEN); \
388 FINISH_NAP; \
389 DISABLE_INTS; \
390 bl .save_nvgprs; \
391 addi r3,r1,STACK_FRAME_OVERHEAD; \
392 bl hdlr; \
393 b .ret_from_except
394
379#define STD_EXCEPTION_COMMON_LITE(trap, label, hdlr) \ 395#define STD_EXCEPTION_COMMON_LITE(trap, label, hdlr) \
380 .align 7; \ 396 .align 7; \
381 .globl label##_common; \ 397 .globl label##_common; \
382label##_common: \ 398label##_common: \
383 EXCEPTION_PROLOG_COMMON(trap, PACA_EXGEN); \ 399 EXCEPTION_PROLOG_COMMON(trap, PACA_EXGEN); \
400 FINISH_NAP; \
384 DISABLE_INTS; \ 401 DISABLE_INTS; \
385 bl .ppc64_runlatch_on; \ 402 bl .ppc64_runlatch_on; \
386 addi r3,r1,STACK_FRAME_OVERHEAD; \ 403 addi r3,r1,STACK_FRAME_OVERHEAD; \
@@ -388,6 +405,25 @@ label##_common: \
388 b .ret_from_except_lite 405 b .ret_from_except_lite
389 406
390/* 407/*
408 * When the idle code in power4_idle puts the CPU into NAP mode,
409 * it has to do so in a loop, and relies on the external interrupt
410 * and decrementer interrupt entry code to get it out of the loop.
411 * It sets the _TLF_NAPPING bit in current_thread_info()->local_flags
412 * to signal that it is in the loop and needs help to get out.
413 */
414#ifdef CONFIG_PPC_970_NAP
415#define FINISH_NAP \
416BEGIN_FTR_SECTION \
417 clrrdi r11,r1,THREAD_SHIFT; \
418 ld r9,TI_LOCAL_FLAGS(r11); \
419 andi. r10,r9,_TLF_NAPPING; \
420 bnel power4_fixup_nap; \
421END_FTR_SECTION_IFSET(CPU_FTR_CAN_NAP)
422#else
423#define FINISH_NAP
424#endif
425
426/*
391 * Start of pSeries system interrupt routines 427 * Start of pSeries system interrupt routines
392 */ 428 */
393 . = 0x100 429 . = 0x100
@@ -772,6 +808,7 @@ hardware_interrupt_iSeries_masked:
772 .globl machine_check_common 808 .globl machine_check_common
773machine_check_common: 809machine_check_common:
774 EXCEPTION_PROLOG_COMMON(0x200, PACA_EXMC) 810 EXCEPTION_PROLOG_COMMON(0x200, PACA_EXMC)
811 FINISH_NAP
775 DISABLE_INTS 812 DISABLE_INTS
776 bl .save_nvgprs 813 bl .save_nvgprs
777 addi r3,r1,STACK_FRAME_OVERHEAD 814 addi r3,r1,STACK_FRAME_OVERHEAD
@@ -783,7 +820,7 @@ machine_check_common:
783 STD_EXCEPTION_COMMON(0xb00, trap_0b, .unknown_exception) 820 STD_EXCEPTION_COMMON(0xb00, trap_0b, .unknown_exception)
784 STD_EXCEPTION_COMMON(0xd00, single_step, .single_step_exception) 821 STD_EXCEPTION_COMMON(0xd00, single_step, .single_step_exception)
785 STD_EXCEPTION_COMMON(0xe00, trap_0e, .unknown_exception) 822 STD_EXCEPTION_COMMON(0xe00, trap_0e, .unknown_exception)
786 STD_EXCEPTION_COMMON(0xf00, performance_monitor, .performance_monitor_exception) 823 STD_EXCEPTION_COMMON_IDLE(0xf00, performance_monitor, .performance_monitor_exception)
787 STD_EXCEPTION_COMMON(0x1300, instruction_breakpoint, .instruction_breakpoint_exception) 824 STD_EXCEPTION_COMMON(0x1300, instruction_breakpoint, .instruction_breakpoint_exception)
788#ifdef CONFIG_ALTIVEC 825#ifdef CONFIG_ALTIVEC
789 STD_EXCEPTION_COMMON(0x1700, altivec_assist, .altivec_assist_exception) 826 STD_EXCEPTION_COMMON(0x1700, altivec_assist, .altivec_assist_exception)
@@ -1034,6 +1071,7 @@ unrecov_slb:
1034 .globl hardware_interrupt_entry 1071 .globl hardware_interrupt_entry
1035hardware_interrupt_common: 1072hardware_interrupt_common:
1036 EXCEPTION_PROLOG_COMMON(0x500, PACA_EXGEN) 1073 EXCEPTION_PROLOG_COMMON(0x500, PACA_EXGEN)
1074 FINISH_NAP
1037hardware_interrupt_entry: 1075hardware_interrupt_entry:
1038 DISABLE_INTS 1076 DISABLE_INTS
1039 bl .ppc64_runlatch_on 1077 bl .ppc64_runlatch_on
@@ -1041,6 +1079,15 @@ hardware_interrupt_entry:
1041 bl .do_IRQ 1079 bl .do_IRQ
1042 b .ret_from_except_lite 1080 b .ret_from_except_lite
1043 1081
1082#ifdef CONFIG_PPC_970_NAP
1083power4_fixup_nap:
1084 andc r9,r9,r10
1085 std r9,TI_LOCAL_FLAGS(r11)
1086 ld r10,_LINK(r1) /* make idle task do the */
1087 std r10,_NIP(r1) /* equivalent of a blr */
1088 blr
1089#endif
1090
1044 .align 7 1091 .align 7
1045 .globl alignment_common 1092 .globl alignment_common
1046alignment_common: 1093alignment_common: