From: Alan Cox Date: Fri, 17 Jul 2015 22:27:53 +0000 (+0100) Subject: lowlevel-z80: set insys when pre-empting, fix a scribble in some modes X-Git-Url: https://git.ndcode.org/public/gitweb.cgi?a=commitdiff_plain;h=3984cf3d985f5e615c5438943b08020af14a5b17;p=FUZIX.git lowlevel-z80: set insys when pre-empting, fix a scribble in some modes We must update the udata before mapping process memory as we are not guaranteed that won't vanish the udata. Set u_insys so that the following case cannot occur once we begin loosening irq disabled areas IRQ pre-empt ei swapper() IRQ pre-empt *boom* --- diff --git a/Kernel/lowlevel-z80-banked.s b/Kernel/lowlevel-z80-banked.s index 95c72ed3..a323d344 100644 --- a/Kernel/lowlevel-z80-banked.s +++ b/Kernel/lowlevel-z80-banked.s @@ -516,6 +516,14 @@ preemption: ; intret2:call map_kernel + + ; + ; Semantically we are doing a null syscall for pre-empt. We need + ; to record ourselves as in a syscall so we can't be recursively + ; pre-empted when switchout re-enables interrupts. + ; + ld a, #1 + ld (U_DATA__U_INSYS), a ; ; Process status is offset 0 ; @@ -523,15 +531,17 @@ intret2:call map_kernel ld (hl), #P_READY call _switchout ; + ; We are no longer in an interrupt or a syscall + ; + xor a + ld (U_DATA__U_ININTERRUPT), a + ld (U_DATA__U_INSYS), a + ; ; We have been rescheduled, remap ourself and go back to user ; space via signal handling ; call map_process_always ; Get our user mapping back - ; We are no longer in an interrupt - xor a - ld (U_DATA__U_ININTERRUPT), a - ; We were pre-empted but have now been rescheduled ; User stack ld sp, (U_DATA__U_SYSCALL_SP) diff --git a/Kernel/lowlevel-z80.s b/Kernel/lowlevel-z80.s index f8499bf4..094787e4 100644 --- a/Kernel/lowlevel-z80.s +++ b/Kernel/lowlevel-z80.s @@ -508,6 +508,14 @@ preemption: ; intret2:call map_kernel + + ; + ; Semantically we are doing a null syscall for pre-empt. We need + ; to record ourselves as in a syscall so we can't be recursively + ; pre-empted when switchout re-enables interrupts. + ; + ld a, #1 + ld (U_DATA__U_INSYS), a ; ; Process status is offset 0 ; @@ -515,14 +523,17 @@ intret2:call map_kernel ld (hl), #P_READY call _switchout ; + ; We are no longer in an interrupt or a syscall + ; + xor a + ld (U_DATA__U_ININTERRUPT), a + ld (U_DATA__U_INSYS), a + ; ; We have been rescheduled, remap ourself and go back to user ; space via signal handling ; call map_process_always ; Get our user mapping back - ; We are no longer in an interrupt - xor a - ld (U_DATA__U_ININTERRUPT), a ; We were pre-empted but have now been rescheduled ; User stack