arch: arm: update arch.mode in user thread system calls

This commit updates the thread.mode variable, in system
calls, whenever we modify the execution privilege level.
We need to do this, in order to be able to properly handle
context-switching triggered by ISRs, while doing the system
calls. The commit ensures that a context-switch, triggered
by an ISR during or after,a system call will preserve the
right privilege level.

Signed-off-by: Ioannis Glaropoulos <Ioannis.Glaropoulos@nordicsemi.no>
This commit is contained in:
Ioannis Glaropoulos 2019-04-01 12:40:23 +02:00 committed by Anas Nashif
commit 4a58fa1186
2 changed files with 18 additions and 0 deletions

View file

@ -418,6 +418,14 @@ _do_syscall:
ldr r6, =K_SYSCALL_BAD
valid_syscall_id:
push {r0, r1}
ldr r0, =_kernel
ldr r0, [r0, #_kernel_offset_to_current]
ldr r1, [r0, #_thread_offset_to_mode]
bic r1, #1
/* Store (privileged) mode in thread's mode state variable */
str r1, [r0, #_thread_offset_to_mode]
dsb
/* set mode to privileged, r2 still contains value from CONTROL */
bic r2, #1
msr CONTROL, r2
@ -427,6 +435,7 @@ valid_syscall_id:
* instructions with the previous privilege.
*/
isb
pop {r0, r1}
/* return from SVC to the modified LR - _arm_do_syscall */
bx lr

View file

@ -242,6 +242,14 @@ dispatch_syscall:
ldr ip, [sp,#8]
msr PSP, ip
push {r0, r1}
ldr r0, =_kernel
ldr r0, [r0, #_kernel_offset_to_current]
ldr r1, [r0, #_thread_offset_to_mode]
orrs r1, r1, #1
/* Store (unprivileged) mode in thread's mode state variable */
str r1, [r0, #_thread_offset_to_mode]
dsb
/* drop privileges by setting bit 0 in CONTROL */
mrs ip, CONTROL
orrs ip, ip, #1
@ -252,6 +260,7 @@ dispatch_syscall:
* instructions with the previous privilege.
*/
isb
pop {r0, r1}
/* Zero out volatile (caller-saved) registers so as to not leak state from
* kernel mode. The C calling convention for the syscall handler will