Subject: Re: locore.S question about [fs]uswintr
To: port-mips@netbsd.org <port-mips@netbsd.org>
From: Ethan Solomita <ethan@geocast.com>
List: port-mips
Date: 08/07/2000 19:52:05
I've received a couple of replies which agree that what I describe
below is a bug, namely, [fs]uswintr should preserve U_PCB_ONFAULT, in
case it's in an interrupt which interrupted one of the copy routines
that relies on U_PCB_ONFAULT.
So here's the diff I'm thinking of. If there's any problems, speak up
RSN or forever hold your peace.
Thanks!
-- Ethan
***************
*** 831,841 ****
LEAF(fuswintr)
lw v1, _C_LABEL(curpcb)
la v0, _C_LABEL(fswintrberr)
blt a0, zero, _C_LABEL(fswintrberr)
sw v0, U_PCB_ONFAULT(v1)
lhu v0, 0(a0) # fetch short
j ra
! sw zero, U_PCB_ONFAULT(v1)
END(fuswintr)
/*
--- 845,856 ----
LEAF(fuswintr)
lw v1, _C_LABEL(curpcb)
la v0, _C_LABEL(fswintrberr)
+ lw a2, U_PCB_ONFAULT(v1)
blt a0, zero, _C_LABEL(fswintrberr)
sw v0, U_PCB_ONFAULT(v1)
lhu v0, 0(a0) # fetch short
j ra
! sw a2, U_PCB_ONFAULT(v1)
END(fuswintr)
/*
***************
*** 846,855 ****
LEAF(suswintr)
lw v1, _C_LABEL(curpcb)
la v0, _C_LABEL(fswintrberr)
blt a0, zero, _C_LABEL(fswintrberr)
sw v0, U_PCB_ONFAULT(v1)
sh a1, 0(a0) # store short
! sw zero, U_PCB_ONFAULT(v1)
j ra
move v0, zero
END(suswintr)
--- 861,871 ----
LEAF(suswintr)
lw v1, _C_LABEL(curpcb)
la v0, _C_LABEL(fswintrberr)
+ lw a2, U_PCB_ONFAULT(v1)
blt a0, zero, _C_LABEL(fswintrberr)
sw v0, U_PCB_ONFAULT(v1)
sh a1, 0(a0) # store short
! sw a2, U_PCB_ONFAULT(v1)
j ra
move v0, zero
END(suswintr)
***************
*** 996,1002 ****
*/
LEAF(fswintrberr)
nop
! XLEAF(fswberr)
XLEAF(baderr)
sw zero, U_PCB_ONFAULT(v1)
j ra
--- 1012,1023 ----
*/
LEAF(fswintrberr)
nop
! sw a2, U_PCB_ONFAULT(v1)
! j ra
! li v0, -1
! END(fswintrberr)
!
! LEAF(fswberr)
XLEAF(baderr)
sw zero, U_PCB_ONFAULT(v1)
j ra
Ethan Solomita wrote:
>
> In locore.S, the comments before [fs]uswintr claim that they are safe
> to be called from an interrupt context. I think that they aren't, and I
> was hoping someone could either confirm what I see, or give me the
> missing clues.
>
> If they're called from an interrupt, then it is possible that another
> of these user-data routines could have been running at the time that the
> interrupt was received. When [fs]uswintr run, they set U_PCB_ONFAULT,
> and then clear it when they're done. So when the interrupt returns, and
> we resume running something like copyout (for example), it is running
> with a 0 in U_PCB_ONFAULT. If you get a fault, the kernel panics.
>
> I know that this all sounds very theoretical, but it came up with some
> improvements to user profiling that I've been looking into. The result
> is that the profiling code can be called from interrupt (namely,
> setrunnable()), and in particular can be called at splclock. So we're
> processing a disk interrupt and doing a copyout() to the user, then a
> clock interrupt happens and the profiling code calls [fs]uswintr.
>
> So, is this a bug? I eliminated the problem by changing [fs]uswintr to
> be like kcopy, which saves the old value of U_PCB_ONFAULT.
>
> Thanks!
> -- Ethan