Date: Mon, 27 May 2013 18:26:08 +0000 (UTC) From: Konstantin Belousov <kib@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r251033 - in head/sys: amd64/amd64 i386/i386 Message-ID: <201305271826.r4RIQ8IT004923@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: kib Date: Mon May 27 18:26:08 2013 New Revision: 251033 URL: http://svnweb.freebsd.org/changeset/base/251033 Log: When handling an exception from the attempt from loading the faulting context on return from the trap handler, re-enable the interrupts on i386 and amd64. The trap return path have to disable interrupts since the sequence of loading the machine state is not atomic. The trap() function which transfers the control to the special handler would enable the interrupt, but an iret loads the previous eflags with PSL_I clear. Then, the special handler calls trap() on its own, which now sees the original eflags with PSL_I set and does not enable interrupts. The end result is that signal delivery and process exiting code could be executed with interrupts disabled, which is generally wrong and triggers several assertions. For amd64, the interrupts are enabled conditionally based on PSL_I in the eflags of the outer frame, as it is already done for doreti_iret_fault. For i386, the interrupts are enabled unconditionally, the ast loop could have opened a window with interrupts enabled just before the iret anyway. Reported and tested by: pho Sponsored by: The FreeBSD Foundation MFC after: 1 week Modified: head/sys/amd64/amd64/exception.S head/sys/i386/i386/exception.s Modified: head/sys/amd64/amd64/exception.S ============================================================================== --- head/sys/amd64/amd64/exception.S Mon May 27 16:29:53 2013 (r251032) +++ head/sys/amd64/amd64/exception.S Mon May 27 18:26:08 2013 (r251033) @@ -818,6 +818,10 @@ doreti_iret_fault: .globl ds_load_fault ds_load_fault: movl $T_PROTFLT,TF_TRAPNO(%rsp) + testl $PSL_I,TF_RFLAGS(%rsp) + jz 1f + sti +1: movq %rsp,%rdi call trap movw $KUDSEL,TF_DS(%rsp) @@ -827,6 +831,10 @@ ds_load_fault: .globl es_load_fault es_load_fault: movl $T_PROTFLT,TF_TRAPNO(%rsp) + testl $PSL_I,TF_RFLAGS(%rsp) + jz 1f + sti +1: movq %rsp,%rdi call trap movw $KUDSEL,TF_ES(%rsp) @@ -835,6 +843,10 @@ es_load_fault: ALIGN_TEXT .globl fs_load_fault fs_load_fault: + testl $PSL_I,TF_RFLAGS(%rsp) + jz 1f + sti +1: movl $T_PROTFLT,TF_TRAPNO(%rsp) movq %rsp,%rdi call trap @@ -846,6 +858,10 @@ fs_load_fault: gs_load_fault: popfq movl $T_PROTFLT,TF_TRAPNO(%rsp) + testl $PSL_I,TF_RFLAGS(%rsp) + jz 1f + sti +1: movq %rsp,%rdi call trap movw $KUG32SEL,TF_GS(%rsp) @@ -855,6 +871,10 @@ gs_load_fault: .globl fsbase_load_fault fsbase_load_fault: movl $T_PROTFLT,TF_TRAPNO(%rsp) + testl $PSL_I,TF_RFLAGS(%rsp) + jz 1f + sti +1: movq %rsp,%rdi call trap movq PCPU(CURTHREAD),%r8 @@ -866,6 +886,10 @@ fsbase_load_fault: .globl gsbase_load_fault gsbase_load_fault: movl $T_PROTFLT,TF_TRAPNO(%rsp) + testl $PSL_I,TF_RFLAGS(%rsp) + jz 1f + sti +1: movq %rsp,%rdi call trap movq PCPU(CURTHREAD),%r8 Modified: head/sys/i386/i386/exception.s ============================================================================== --- head/sys/i386/i386/exception.s Mon May 27 16:29:53 2013 (r251032) +++ head/sys/i386/i386/exception.s Mon May 27 18:26:08 2013 (r251033) @@ -422,6 +422,7 @@ doreti_popl_es_fault: pushl %fs .globl doreti_popl_fs_fault doreti_popl_fs_fault: + sti movl $0,TF_ERR(%esp) /* XXX should be the error code */ movl $T_PROTFLT,TF_TRAPNO(%esp) jmp alltraps_with_regs_pushed
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201305271826.r4RIQ8IT004923>