aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--arch/powerpc/kernel/exceptions-64e.S82
1 files changed, 46 insertions, 36 deletions
diff --git a/arch/powerpc/kernel/exceptions-64e.S b/arch/powerpc/kernel/exceptions-64e.S
index 89e1133b0185..0204c39f438e 100644
--- a/arch/powerpc/kernel/exceptions-64e.S
+++ b/arch/powerpc/kernel/exceptions-64e.S
@@ -151,7 +151,7 @@
151/* Core exception code for all exceptions except TLB misses. 151/* Core exception code for all exceptions except TLB misses.
152 * XXX: Needs to make SPRN_SPRG_GEN depend on exception type 152 * XXX: Needs to make SPRN_SPRG_GEN depend on exception type
153 */ 153 */
154#define EXCEPTION_COMMON(n, excf, ints) \ 154#define EXCEPTION_COMMON(n, excf) \
155exc_##n##_common: \ 155exc_##n##_common: \
156 std r0,GPR0(r1); /* save r0 in stackframe */ \ 156 std r0,GPR0(r1); /* save r0 in stackframe */ \
157 std r2,GPR2(r1); /* save r2 in stackframe */ \ 157 std r2,GPR2(r1); /* save r2 in stackframe */ \
@@ -188,24 +188,20 @@ exc_##n##_common: \
188 std r11,SOFTE(r1); /* and save it to stackframe */ \ 188 std r11,SOFTE(r1); /* and save it to stackframe */ \
189 std r12,STACK_FRAME_OVERHEAD-16(r1); /* mark the frame */ \ 189 std r12,STACK_FRAME_OVERHEAD-16(r1); /* mark the frame */ \
190 std r3,_TRAP(r1); /* set trap number */ \ 190 std r3,_TRAP(r1); /* set trap number */ \
191 std r0,RESULT(r1); /* clear regs->result */ \ 191 std r0,RESULT(r1); /* clear regs->result */
192 ints;
193 192
194/* Variants for the "ints" argument. This one does nothing when we want 193/*
195 * to keep interrupts in their original state 194 * This is meant for exceptions that don't immediately hard-enable. We
196 */ 195 * set a bit in paca->irq_happened to ensure that a subsequent call to
197#define INTS_KEEP 196 * arch_local_irq_restore() will properly hard-enable and avoid the
198 197 * fast-path, and then reconcile irq state.
199/* This second version is meant for exceptions that don't immediately
200 * hard-enable. We set a bit in paca->irq_happened to ensure that
201 * a subsequent call to arch_local_irq_restore() will properly
202 * hard-enable and avoid the fast-path, and then reconcile irq state.
203 */ 198 */
204#define INTS_DISABLE RECONCILE_IRQ_STATE(r3,r4) 199#define INTS_DISABLE RECONCILE_IRQ_STATE(r3,r4)
205 200
206/* This is called by exceptions that used INTS_KEEP (that did not touch 201/*
207 * irq indicators in the PACA). This will restore MSR:EE to it's previous 202 * This is called by exceptions that don't use INTS_DISABLE (that did not
208 * value 203 * touch irq indicators in the PACA). This will restore MSR:EE to it's
204 * previous value
209 * 205 *
210 * XXX In the long run, we may want to open-code it in order to separate the 206 * XXX In the long run, we may want to open-code it in order to separate the
211 * load from the wrtee, thus limiting the latency caused by the dependency 207 * load from the wrtee, thus limiting the latency caused by the dependency
@@ -263,7 +259,8 @@ exc_##n##_bad_stack: \
263#define MASKABLE_EXCEPTION(trapnum, intnum, label, hdlr, ack) \ 259#define MASKABLE_EXCEPTION(trapnum, intnum, label, hdlr, ack) \
264 START_EXCEPTION(label); \ 260 START_EXCEPTION(label); \
265 NORMAL_EXCEPTION_PROLOG(trapnum, intnum, PROLOG_ADDITION_MASKABLE)\ 261 NORMAL_EXCEPTION_PROLOG(trapnum, intnum, PROLOG_ADDITION_MASKABLE)\
266 EXCEPTION_COMMON(trapnum, PACA_EXGEN, INTS_DISABLE) \ 262 EXCEPTION_COMMON(trapnum, PACA_EXGEN) \
263 INTS_DISABLE; \
267 ack(r8); \ 264 ack(r8); \
268 CHECK_NAPPING(); \ 265 CHECK_NAPPING(); \
269 addi r3,r1,STACK_FRAME_OVERHEAD; \ 266 addi r3,r1,STACK_FRAME_OVERHEAD; \
@@ -318,7 +315,8 @@ interrupt_end_book3e:
318 START_EXCEPTION(critical_input); 315 START_EXCEPTION(critical_input);
319 CRIT_EXCEPTION_PROLOG(0x100, BOOKE_INTERRUPT_CRITICAL, 316 CRIT_EXCEPTION_PROLOG(0x100, BOOKE_INTERRUPT_CRITICAL,
320 PROLOG_ADDITION_NONE) 317 PROLOG_ADDITION_NONE)
321// EXCEPTION_COMMON(0x100, PACA_EXCRIT, INTS_DISABLE) 318// EXCEPTION_COMMON(0x100, PACA_EXCRIT)
319// INTS_DISABLE
322// bl special_reg_save_crit 320// bl special_reg_save_crit
323// CHECK_NAPPING(); 321// CHECK_NAPPING();
324// addi r3,r1,STACK_FRAME_OVERHEAD 322// addi r3,r1,STACK_FRAME_OVERHEAD
@@ -330,7 +328,8 @@ interrupt_end_book3e:
330 START_EXCEPTION(machine_check); 328 START_EXCEPTION(machine_check);
331 MC_EXCEPTION_PROLOG(0x000, BOOKE_INTERRUPT_MACHINE_CHECK, 329 MC_EXCEPTION_PROLOG(0x000, BOOKE_INTERRUPT_MACHINE_CHECK,
332 PROLOG_ADDITION_NONE) 330 PROLOG_ADDITION_NONE)
333// EXCEPTION_COMMON(0x000, PACA_EXMC, INTS_DISABLE) 331// EXCEPTION_COMMON(0x000, PACA_EXMC)
332// INTS_DISABLE
334// bl special_reg_save_mc 333// bl special_reg_save_mc
335// addi r3,r1,STACK_FRAME_OVERHEAD 334// addi r3,r1,STACK_FRAME_OVERHEAD
336// CHECK_NAPPING(); 335// CHECK_NAPPING();
@@ -344,7 +343,8 @@ interrupt_end_book3e:
344 PROLOG_ADDITION_2REGS) 343 PROLOG_ADDITION_2REGS)
345 mfspr r14,SPRN_DEAR 344 mfspr r14,SPRN_DEAR
346 mfspr r15,SPRN_ESR 345 mfspr r15,SPRN_ESR
347 EXCEPTION_COMMON(0x300, PACA_EXGEN, INTS_DISABLE) 346 EXCEPTION_COMMON(0x300, PACA_EXGEN)
347 INTS_DISABLE
348 b storage_fault_common 348 b storage_fault_common
349 349
350/* Instruction Storage Interrupt */ 350/* Instruction Storage Interrupt */
@@ -353,7 +353,8 @@ interrupt_end_book3e:
353 PROLOG_ADDITION_2REGS) 353 PROLOG_ADDITION_2REGS)
354 li r15,0 354 li r15,0
355 mr r14,r10 355 mr r14,r10
356 EXCEPTION_COMMON(0x400, PACA_EXGEN, INTS_DISABLE) 356 EXCEPTION_COMMON(0x400, PACA_EXGEN)
357 INTS_DISABLE
357 b storage_fault_common 358 b storage_fault_common
358 359
359/* External Input Interrupt */ 360/* External Input Interrupt */
@@ -366,7 +367,7 @@ interrupt_end_book3e:
366 PROLOG_ADDITION_2REGS) 367 PROLOG_ADDITION_2REGS)
367 mfspr r14,SPRN_DEAR 368 mfspr r14,SPRN_DEAR
368 mfspr r15,SPRN_ESR 369 mfspr r15,SPRN_ESR
369 EXCEPTION_COMMON(0x600, PACA_EXGEN, INTS_KEEP) 370 EXCEPTION_COMMON(0x600, PACA_EXGEN)
370 b alignment_more /* no room, go out of line */ 371 b alignment_more /* no room, go out of line */
371 372
372/* Program Interrupt */ 373/* Program Interrupt */
@@ -374,7 +375,8 @@ interrupt_end_book3e:
374 NORMAL_EXCEPTION_PROLOG(0x700, BOOKE_INTERRUPT_PROGRAM, 375 NORMAL_EXCEPTION_PROLOG(0x700, BOOKE_INTERRUPT_PROGRAM,
375 PROLOG_ADDITION_1REG) 376 PROLOG_ADDITION_1REG)
376 mfspr r14,SPRN_ESR 377 mfspr r14,SPRN_ESR
377 EXCEPTION_COMMON(0x700, PACA_EXGEN, INTS_DISABLE) 378 EXCEPTION_COMMON(0x700, PACA_EXGEN)
379 INTS_DISABLE
378 std r14,_DSISR(r1) 380 std r14,_DSISR(r1)
379 addi r3,r1,STACK_FRAME_OVERHEAD 381 addi r3,r1,STACK_FRAME_OVERHEAD
380 ld r14,PACA_EXGEN+EX_R14(r13) 382 ld r14,PACA_EXGEN+EX_R14(r13)
@@ -387,7 +389,7 @@ interrupt_end_book3e:
387 NORMAL_EXCEPTION_PROLOG(0x800, BOOKE_INTERRUPT_FP_UNAVAIL, 389 NORMAL_EXCEPTION_PROLOG(0x800, BOOKE_INTERRUPT_FP_UNAVAIL,
388 PROLOG_ADDITION_NONE) 390 PROLOG_ADDITION_NONE)
389 /* we can probably do a shorter exception entry for that one... */ 391 /* we can probably do a shorter exception entry for that one... */
390 EXCEPTION_COMMON(0x800, PACA_EXGEN, INTS_KEEP) 392 EXCEPTION_COMMON(0x800, PACA_EXGEN)
391 ld r12,_MSR(r1) 393 ld r12,_MSR(r1)
392 andi. r0,r12,MSR_PR; 394 andi. r0,r12,MSR_PR;
393 beq- 1f 395 beq- 1f
@@ -404,7 +406,7 @@ interrupt_end_book3e:
404 NORMAL_EXCEPTION_PROLOG(0x200, BOOKE_INTERRUPT_SPE_ALTIVEC_UNAVAIL, 406 NORMAL_EXCEPTION_PROLOG(0x200, BOOKE_INTERRUPT_SPE_ALTIVEC_UNAVAIL,
405 PROLOG_ADDITION_NONE) 407 PROLOG_ADDITION_NONE)
406 /* we can probably do a shorter exception entry for that one... */ 408 /* we can probably do a shorter exception entry for that one... */
407 EXCEPTION_COMMON(0x200, PACA_EXGEN, INTS_KEEP) 409 EXCEPTION_COMMON(0x200, PACA_EXGEN)
408#ifdef CONFIG_ALTIVEC 410#ifdef CONFIG_ALTIVEC
409BEGIN_FTR_SECTION 411BEGIN_FTR_SECTION
410 ld r12,_MSR(r1) 412 ld r12,_MSR(r1)
@@ -426,7 +428,8 @@ END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC)
426 NORMAL_EXCEPTION_PROLOG(0x220, 428 NORMAL_EXCEPTION_PROLOG(0x220,
427 BOOKE_INTERRUPT_SPE_FP_DATA_ALTIVEC_ASSIST, 429 BOOKE_INTERRUPT_SPE_FP_DATA_ALTIVEC_ASSIST,
428 PROLOG_ADDITION_NONE) 430 PROLOG_ADDITION_NONE)
429 EXCEPTION_COMMON(0x220, PACA_EXGEN, INTS_DISABLE) 431 EXCEPTION_COMMON(0x220, PACA_EXGEN)
432 INTS_DISABLE
430 bl .save_nvgprs 433 bl .save_nvgprs
431 addi r3,r1,STACK_FRAME_OVERHEAD 434 addi r3,r1,STACK_FRAME_OVERHEAD
432#ifdef CONFIG_ALTIVEC 435#ifdef CONFIG_ALTIVEC
@@ -451,7 +454,8 @@ END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC)
451 START_EXCEPTION(watchdog); 454 START_EXCEPTION(watchdog);
452 CRIT_EXCEPTION_PROLOG(0x9f0, BOOKE_INTERRUPT_WATCHDOG, 455 CRIT_EXCEPTION_PROLOG(0x9f0, BOOKE_INTERRUPT_WATCHDOG,
453 PROLOG_ADDITION_NONE) 456 PROLOG_ADDITION_NONE)
454// EXCEPTION_COMMON(0x9f0, PACA_EXCRIT, INTS_DISABLE) 457// EXCEPTION_COMMON(0x9f0, PACA_EXCRIT)
458// INTS_DISABLE
455// bl special_reg_save_crit 459// bl special_reg_save_crit
456// CHECK_NAPPING(); 460// CHECK_NAPPING();
457// addi r3,r1,STACK_FRAME_OVERHEAD 461// addi r3,r1,STACK_FRAME_OVERHEAD
@@ -471,7 +475,8 @@ END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC)
471 START_EXCEPTION(ap_unavailable); 475 START_EXCEPTION(ap_unavailable);
472 NORMAL_EXCEPTION_PROLOG(0xf20, BOOKE_INTERRUPT_AP_UNAVAIL, 476 NORMAL_EXCEPTION_PROLOG(0xf20, BOOKE_INTERRUPT_AP_UNAVAIL,
473 PROLOG_ADDITION_NONE) 477 PROLOG_ADDITION_NONE)
474 EXCEPTION_COMMON(0xf20, PACA_EXGEN, INTS_DISABLE) 478 EXCEPTION_COMMON(0xf20, PACA_EXGEN)
479 INTS_DISABLE
475 bl .save_nvgprs 480 bl .save_nvgprs
476 addi r3,r1,STACK_FRAME_OVERHEAD 481 addi r3,r1,STACK_FRAME_OVERHEAD
477 bl .unknown_exception 482 bl .unknown_exception
@@ -530,7 +535,8 @@ END_FTR_SECTION_IFSET(CPU_FTR_ALTIVEC)
530 mfspr r15,SPRN_SPRG_CRIT_SCRATCH 535 mfspr r15,SPRN_SPRG_CRIT_SCRATCH
531 mtspr SPRN_SPRG_GEN_SCRATCH,r15 536 mtspr SPRN_SPRG_GEN_SCRATCH,r15
532 mfspr r14,SPRN_DBSR 537 mfspr r14,SPRN_DBSR
533 EXCEPTION_COMMON(0xd00, PACA_EXCRIT, INTS_DISABLE) 538 EXCEPTION_COMMON(0xd00, PACA_EXCRIT)
539 INTS_DISABLE
534 std r14,_DSISR(r1) 540 std r14,_DSISR(r1)
535 addi r3,r1,STACK_FRAME_OVERHEAD 541 addi r3,r1,STACK_FRAME_OVERHEAD
536 mr r4,r14 542 mr r4,r14
@@ -596,7 +602,8 @@ kernel_dbg_exc:
596 mfspr r15,SPRN_SPRG_DBG_SCRATCH 602 mfspr r15,SPRN_SPRG_DBG_SCRATCH
597 mtspr SPRN_SPRG_GEN_SCRATCH,r15 603 mtspr SPRN_SPRG_GEN_SCRATCH,r15
598 mfspr r14,SPRN_DBSR 604 mfspr r14,SPRN_DBSR
599 EXCEPTION_COMMON(0xd08, PACA_EXDBG, INTS_DISABLE) 605 EXCEPTION_COMMON(0xd08, PACA_EXDBG)
606 INTS_DISABLE
600 std r14,_DSISR(r1) 607 std r14,_DSISR(r1)
601 addi r3,r1,STACK_FRAME_OVERHEAD 608 addi r3,r1,STACK_FRAME_OVERHEAD
602 mr r4,r14 609 mr r4,r14
@@ -609,7 +616,8 @@ kernel_dbg_exc:
609 START_EXCEPTION(perfmon); 616 START_EXCEPTION(perfmon);
610 NORMAL_EXCEPTION_PROLOG(0x260, BOOKE_INTERRUPT_PERFORMANCE_MONITOR, 617 NORMAL_EXCEPTION_PROLOG(0x260, BOOKE_INTERRUPT_PERFORMANCE_MONITOR,
611 PROLOG_ADDITION_NONE) 618 PROLOG_ADDITION_NONE)
612 EXCEPTION_COMMON(0x260, PACA_EXGEN, INTS_DISABLE) 619 EXCEPTION_COMMON(0x260, PACA_EXGEN)
620 INTS_DISABLE
613 CHECK_NAPPING() 621 CHECK_NAPPING()
614 addi r3,r1,STACK_FRAME_OVERHEAD 622 addi r3,r1,STACK_FRAME_OVERHEAD
615 bl .performance_monitor_exception 623 bl .performance_monitor_exception
@@ -623,7 +631,8 @@ kernel_dbg_exc:
623 START_EXCEPTION(doorbell_crit); 631 START_EXCEPTION(doorbell_crit);
624 CRIT_EXCEPTION_PROLOG(0x2a0, BOOKE_INTERRUPT_DOORBELL_CRITICAL, 632 CRIT_EXCEPTION_PROLOG(0x2a0, BOOKE_INTERRUPT_DOORBELL_CRITICAL,
625 PROLOG_ADDITION_NONE) 633 PROLOG_ADDITION_NONE)
626// EXCEPTION_COMMON(0x2a0, PACA_EXCRIT, INTS_DISABLE) 634// EXCEPTION_COMMON(0x2a0, PACA_EXCRIT)
635// INTS_DISABLE
627// bl special_reg_save_crit 636// bl special_reg_save_crit
628// CHECK_NAPPING(); 637// CHECK_NAPPING();
629// addi r3,r1,STACK_FRAME_OVERHEAD 638// addi r3,r1,STACK_FRAME_OVERHEAD
@@ -638,7 +647,7 @@ kernel_dbg_exc:
638 START_EXCEPTION(guest_doorbell); 647 START_EXCEPTION(guest_doorbell);
639 GDBELL_EXCEPTION_PROLOG(0x2c0, BOOKE_INTERRUPT_GUEST_DBELL, 648 GDBELL_EXCEPTION_PROLOG(0x2c0, BOOKE_INTERRUPT_GUEST_DBELL,
640 PROLOG_ADDITION_NONE) 649 PROLOG_ADDITION_NONE)
641 EXCEPTION_COMMON(0x2c0, PACA_EXGEN, INTS_KEEP) 650 EXCEPTION_COMMON(0x2c0, PACA_EXGEN)
642 addi r3,r1,STACK_FRAME_OVERHEAD 651 addi r3,r1,STACK_FRAME_OVERHEAD
643 bl .save_nvgprs 652 bl .save_nvgprs
644 INTS_RESTORE_HARD 653 INTS_RESTORE_HARD
@@ -649,7 +658,8 @@ kernel_dbg_exc:
649 START_EXCEPTION(guest_doorbell_crit); 658 START_EXCEPTION(guest_doorbell_crit);
650 CRIT_EXCEPTION_PROLOG(0x2e0, BOOKE_INTERRUPT_GUEST_DBELL_CRIT, 659 CRIT_EXCEPTION_PROLOG(0x2e0, BOOKE_INTERRUPT_GUEST_DBELL_CRIT,
651 PROLOG_ADDITION_NONE) 660 PROLOG_ADDITION_NONE)
652// EXCEPTION_COMMON(0x2e0, PACA_EXCRIT, INTS_DISABLE) 661// EXCEPTION_COMMON(0x2e0, PACA_EXCRIT)
662// INTS_DISABLE
653// bl special_reg_save_crit 663// bl special_reg_save_crit
654// CHECK_NAPPING(); 664// CHECK_NAPPING();
655// addi r3,r1,STACK_FRAME_OVERHEAD 665// addi r3,r1,STACK_FRAME_OVERHEAD
@@ -661,7 +671,7 @@ kernel_dbg_exc:
661 START_EXCEPTION(hypercall); 671 START_EXCEPTION(hypercall);
662 NORMAL_EXCEPTION_PROLOG(0x310, BOOKE_INTERRUPT_HV_SYSCALL, 672 NORMAL_EXCEPTION_PROLOG(0x310, BOOKE_INTERRUPT_HV_SYSCALL,
663 PROLOG_ADDITION_NONE) 673 PROLOG_ADDITION_NONE)
664 EXCEPTION_COMMON(0x310, PACA_EXGEN, INTS_KEEP) 674 EXCEPTION_COMMON(0x310, PACA_EXGEN)
665 addi r3,r1,STACK_FRAME_OVERHEAD 675 addi r3,r1,STACK_FRAME_OVERHEAD
666 bl .save_nvgprs 676 bl .save_nvgprs
667 INTS_RESTORE_HARD 677 INTS_RESTORE_HARD
@@ -672,7 +682,7 @@ kernel_dbg_exc:
672 START_EXCEPTION(ehpriv); 682 START_EXCEPTION(ehpriv);
673 NORMAL_EXCEPTION_PROLOG(0x320, BOOKE_INTERRUPT_HV_PRIV, 683 NORMAL_EXCEPTION_PROLOG(0x320, BOOKE_INTERRUPT_HV_PRIV,
674 PROLOG_ADDITION_NONE) 684 PROLOG_ADDITION_NONE)
675 EXCEPTION_COMMON(0x320, PACA_EXGEN, INTS_KEEP) 685 EXCEPTION_COMMON(0x320, PACA_EXGEN)
676 addi r3,r1,STACK_FRAME_OVERHEAD 686 addi r3,r1,STACK_FRAME_OVERHEAD
677 bl .save_nvgprs 687 bl .save_nvgprs
678 INTS_RESTORE_HARD 688 INTS_RESTORE_HARD
@@ -683,7 +693,7 @@ kernel_dbg_exc:
683 START_EXCEPTION(lrat_error); 693 START_EXCEPTION(lrat_error);
684 NORMAL_EXCEPTION_PROLOG(0x340, BOOKE_INTERRUPT_LRAT_ERROR, 694 NORMAL_EXCEPTION_PROLOG(0x340, BOOKE_INTERRUPT_LRAT_ERROR,
685 PROLOG_ADDITION_NONE) 695 PROLOG_ADDITION_NONE)
686 EXCEPTION_COMMON(0x340, PACA_EXGEN, INTS_KEEP) 696 EXCEPTION_COMMON(0x340, PACA_EXGEN)
687 addi r3,r1,STACK_FRAME_OVERHEAD 697 addi r3,r1,STACK_FRAME_OVERHEAD
688 bl .save_nvgprs 698 bl .save_nvgprs
689 INTS_RESTORE_HARD 699 INTS_RESTORE_HARD