Commit b0a779de authored by Paul Mackerras's avatar Paul Mackerras

[POWERPC] Make sure interrupt enable gets restored properly

The lazy IRQ disable patch missed a couple of places where the
interrupt enable flags need to be restored correctly.  First, we
weren't restoring the paca->hard_enabled flag on interrupt exit.
Instead of saving it on entry, we compute it from the MSR_EE bit
in the MSR we are restoring at exit.  Secondly, the MMU hash miss
code was clearing both paca->soft_enabled and paca->hard_enabled
but not restoring them in the case where hash_page was able to
resolve the miss from the Linux page tables.
Signed-off-by: default avatarPaul Mackerras <paulus@samba.org>
parent 035223fb
...@@ -489,6 +489,10 @@ END_FW_FTR_SECTION_IFSET(FW_FEATURE_ISERIES) ...@@ -489,6 +489,10 @@ END_FW_FTR_SECTION_IFSET(FW_FEATURE_ISERIES)
andi. r0,r3,MSR_RI andi. r0,r3,MSR_RI
beq- unrecov_restore beq- unrecov_restore
/* extract EE bit and use it to restore paca->hard_enabled */
rldicl r4,r3,49,63 /* r0 = (r3 >> 15) & 1 */
stb r4,PACAHARDIRQEN(r13)
andi. r0,r3,MSR_PR andi. r0,r3,MSR_PR
/* /*
......
...@@ -961,10 +961,18 @@ bad_stack: ...@@ -961,10 +961,18 @@ bad_stack:
* any task or sent any task a signal, you should use * any task or sent any task a signal, you should use
* ret_from_except or ret_from_except_lite instead of this. * ret_from_except or ret_from_except_lite instead of this.
*/ */
fast_exc_return_irq: /* restores irq state too */
ld r3,SOFTE(r1)
ld r12,_MSR(r1)
stb r3,PACASOFTIRQEN(r13) /* restore paca->soft_enabled */
rldicl r4,r12,49,63 /* get MSR_EE to LSB */
stb r4,PACAHARDIRQEN(r13) /* restore paca->hard_enabled */
b 1f
.globl fast_exception_return .globl fast_exception_return
fast_exception_return: fast_exception_return:
ld r12,_MSR(r1) ld r12,_MSR(r1)
ld r11,_NIP(r1) 1: ld r11,_NIP(r1)
andi. r3,r12,MSR_RI /* check if RI is set */ andi. r3,r12,MSR_RI /* check if RI is set */
beq- unrecov_fer beq- unrecov_fer
...@@ -1361,6 +1369,16 @@ BEGIN_FW_FTR_SECTION ...@@ -1361,6 +1369,16 @@ BEGIN_FW_FTR_SECTION
* interrupts if necessary. * interrupts if necessary.
*/ */
beq .ret_from_except_lite beq .ret_from_except_lite
END_FW_FTR_SECTION_IFSET(FW_FEATURE_ISERIES)
#endif
BEGIN_FW_FTR_SECTION
/*
* Here we have interrupts hard-disabled, so it is sufficient
* to restore paca->{soft,hard}_enable and get out.
*/
beq fast_exc_return_irq /* Return from exception on success */
END_FW_FTR_SECTION_IFCLR(FW_FEATURE_ISERIES)
/* For a hash failure, we don't bother re-enabling interrupts */ /* For a hash failure, we don't bother re-enabling interrupts */
ble- 12f ble- 12f
...@@ -1372,14 +1390,6 @@ BEGIN_FW_FTR_SECTION ...@@ -1372,14 +1390,6 @@ BEGIN_FW_FTR_SECTION
ld r3,SOFTE(r1) ld r3,SOFTE(r1)
bl .local_irq_restore bl .local_irq_restore
b 11f b 11f
END_FW_FTR_SECTION_IFSET(FW_FEATURE_ISERIES)
#endif
BEGIN_FW_FTR_SECTION
beq fast_exception_return /* Return from exception on success */
ble- 12f /* Failure return from hash_page */
/* fall through */
END_FW_FTR_SECTION_IFCLR(FW_FEATURE_ISERIES)
/* Here we have a page fault that hash_page can't handle. */ /* Here we have a page fault that hash_page can't handle. */
_GLOBAL(handle_page_fault) _GLOBAL(handle_page_fault)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment