diff options
author | cinap_lenrek <cinap_lenrek@felloff.net> | 2015-01-23 14:01:56 +0100 |
---|---|---|
committer | cinap_lenrek <cinap_lenrek@felloff.net> | 2015-01-23 14:01:56 +0100 |
commit | 3d4d5940498dabb2c7abca2acd23a7e8be83e565 (patch) | |
tree | d9585f78310ff2867676f45bbd4cf9622b43b7b9 /sys/src | |
parent | 8b95dad2080bef9958a91501a863dd29cc46345c (diff) |
pc: dont handle pending floating point exception in fpsave thru FPOFF
the FPOFF macro that follows the FXSAVE/FSAVE instructions in l.s
used to execute WAIT instruction when the TS flag was not set. this
is wrong and causes pending exceptions to be raised from fpsave which
is called from provsave() which holds up->rlock making it deadlock
when matherror() tries to postnote() to itself.
so making FPOFF non-waiting (just set TS flag).
we handle pending exception when restoring the context.
Diffstat (limited to 'sys/src')
-rw-r--r-- | sys/src/9/pc/l.s | 21 |
1 files changed, 7 insertions, 14 deletions
diff --git a/sys/src/9/pc/l.s b/sys/src/9/pc/l.s index 661e66422..44071a634 100644 --- a/sys/src/9/pc/l.s +++ b/sys/src/9/pc/l.s @@ -570,15 +570,8 @@ _aamloop: * FNxxx variations) so WAIT instructions must be explicitly placed in the * code as necessary. */ -#define FPOFF(l) ;\ - MOVL CR0, AX ;\ - ANDL $0xC, AX /* EM, TS */ ;\ - CMPL AX, $0x8 ;\ - JEQ l ;\ - WAIT ;\ -l: ;\ +#define FPOFF ;\ MOVL CR0, AX ;\ - ANDL $~0x4, AX /* EM=0 */ ;\ ORL $0x28, AX /* NE=1, TS=1 */ ;\ MOVL AX, CR0 @@ -586,9 +579,9 @@ l: ;\ MOVL CR0, AX ;\ ANDL $~0xC, AX /* EM=0, TS=0 */ ;\ MOVL AX, CR0 - + TEXT fpoff(SB), $0 /* disable */ - FPOFF(l1) + FPOFF RET TEXT fpinit(SB), $0 /* enable and init */ @@ -606,10 +599,10 @@ TEXT fpinit(SB), $0 /* enable and init */ TEXT fpx87save0(SB), $0 /* save state and disable */ MOVL p+0(FP), AX FSAVE 0(AX) /* no WAIT */ - FPOFF(l2) + FPOFF RET -TEXT fpx87restore0(SB), $0 /* enable and restore state */ +TEXT fpx87restore0(SB), $0 /* enable and restore state */ FPON MOVL p+0(FP), AX FRSTOR 0(AX) @@ -628,13 +621,13 @@ TEXT fpenv(SB), $0 /* save state without waiting */ TEXT fpclear(SB), $0 /* clear pending exceptions */ FPON FCLEX /* no WAIT */ - FPOFF(l3) + FPOFF RET TEXT fpssesave0(SB), $0 /* save state and disable */ MOVL p+0(FP), AX FXSAVE 0(AX) /* no WAIT */ - FPOFF(l4) + FPOFF RET TEXT fpsserestore0(SB), $0 /* enable and restore state */ |