From 37fa6f2f1ebea0c601944567c9e862650b62ba1a Mon Sep 17 00:00:00 2001 From: isiora Date: Wed, 24 Jan 2018 20:52:54 +0000 Subject: Fixed the saving of lr_mon and spsr_mon in smc exception entry. git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@11406 35acf78f-673a-0410-8e92-d51de3d6d3f4 --- os/common/ports/ARMCAx-TZ/chsmc.c | 3 +-- os/common/ports/ARMCAx-TZ/compilers/GCC/monitor.S | 30 ++++++++++++++--------- 2 files changed, 20 insertions(+), 13 deletions(-) (limited to 'os/common/ports') diff --git a/os/common/ports/ARMCAx-TZ/chsmc.c b/os/common/ports/ARMCAx-TZ/chsmc.c index e03d9bda6..a64be1d74 100644 --- a/os/common/ports/ARMCAx-TZ/chsmc.c +++ b/os/common/ports/ARMCAx-TZ/chsmc.c @@ -37,8 +37,7 @@ /* Module exported variables. */ /*===========================================================================*/ thread_reference_t _ns_thread = NULL; -uint32_t sm_secctx[128]; -uint32_t sm_nsecctx[128]; + /*===========================================================================*/ /* Module local types. */ /*===========================================================================*/ diff --git a/os/common/ports/ARMCAx-TZ/compilers/GCC/monitor.S b/os/common/ports/ARMCAx-TZ/compilers/GCC/monitor.S index 33ad2ca0a..d1b10f636 100644 --- a/os/common/ports/ARMCAx-TZ/compilers/GCC/monitor.S +++ b/os/common/ports/ARMCAx-TZ/compilers/GCC/monitor.S @@ -73,10 +73,9 @@ .set MSG_TIMEOUT, -1 .set MSG_RESET, -2 -// .comm sm_secctx, 32*4, 4 -// .comm sm_nsecctx, 32*4, 4 - .global sm_secctx - .global sm_nsecctx + .comm sm_secctx, 32*4, 4 + .comm sm_nsecctx, 32*4, 4 + .global _ns_thread .section .text .code 32 @@ -85,7 +84,7 @@ * Helper macros */ /* - * Store out of context registers in a world area pointed by r0 + * Store out of context registers in a world area pointed by rm */ .macro sm_store_ooctx_regs rm // cpsxx #MODE_SYS // Assume mode SYS @@ -107,7 +106,7 @@ stm \rm!, {r12, sp, lr} .endm /* - * Retrieve out of context registers from a world area pointed by r0 + * Retrieve out of context registers from a world area pointed by rm */ .macro sm_load_ooctx_regs rm // cpsxx #MODE_SYS // Assume mode SYS @@ -145,7 +144,7 @@ _monitor_vectors: * SMC entry */ sm_call: - stmfd sp!, {r3, r12} + stmfd sp!, {r3} ldr r12, =MON_S_SCR // enter in the secure world mcr p15, 0, r12, c1, c1, 0 ands r0, r0 // OS special service, @@ -153,6 +152,10 @@ sm_call: // r1 contains the address where it jumps beq 1f + mrs r3, SPSR + mov r12, lr + stmfd sp!, {r3, r12} // push r3=spsr_mon, r12=lr_mon. + cpsid if, #MODE_SYS // ints disabled ldr r3, =sm_nsecctx sm_store_ooctx_regs r3 @@ -173,16 +176,21 @@ sm_call: sm_load_ooctx_regs r3 msr CPSR_c, #MODE_MON | I_BIT | F_BIT // switch to monitor mode + + ldmfd sp!, {r3, r12} // pop r3=spsr_mon, r12=lr_mon. + msr SPSR_fsxc, r3 + mov lr, r12 + ldr r12, =MON_NS_SCR // enter in the non-secure world mcr p15, 0, r12, c1, c1, 0 - ldmfd sp!, {r3, r12} + ldmfd sp!, {r3} subs pc, lr, #0 // return from smc 1: mov lr, r1 // use the address in r1 as return address // in the non secure world ldr r12, =MON_NS_SCR // enter in the non-secure world mcr p15, 0, r12, c1, c1, 0 - ldmfd sp!, {r3, r12} + ldmfd sp!, {r3} subs pc, lr, #0 // return from smc /* @@ -198,7 +206,7 @@ sm_call: */ sm_fiq: // check point: SCR.NS == 1 - stmfd sp!, {r0, r12} + stmfd sp!, {r0} ldr r0, =MON_S_SCR // enter in the secure world mcr p15, 0, r0, c1, c1, 0 @@ -223,7 +231,7 @@ sm_fiq: msr CPSR_c, #MODE_MON | I_BIT | F_BIT // switch to monitor mode ldr r0, =MON_NS_SCR // set non-secure SCR before return mcr p15, 0, r0, c1, c1, 0 - ldmfd sp!, {r0, r12} + ldmfd sp!, {r0} subs pc, lr, #4 // return into non-secure world /* * IRQ entry -- cgit v1.2.3