feat(el3-spmc): support simd context management upon world switch

This patch performs necessary simd context management operations for
context switch from NWd to SWD and vice versa.

Change-Id: Ife01fffc4e2a7f3deb9b6273424161c225fdbbfb
Signed-off-by: Madhukar Pappireddy <madhukar.pappireddy@arm.com>
This commit is contained in:
Madhukar Pappireddy 2024-04-25 23:01:00 -05:00
parent 7461025985
commit 59bdcc58c3
2 changed files with 29 additions and 0 deletions
Makefile
services/std_svc/spmd

View file

@ -457,6 +457,9 @@ ifneq (${SPD},none)
ifeq ($(SPMC_AT_EL3),1)
$(error SPM cannot be enabled in both S-EL2 and EL3.)
endif
ifeq ($(CTX_INCLUDE_SVE_REGS),1)
$(error SVE context management not needed with Hafnium SPMC.)
endif
endif
ifeq ($(findstring optee_sp,$(ARM_SPMC_MANIFEST_DTS)),optee_sp)

View file

@ -215,6 +215,14 @@ static uint64_t spmd_secure_interrupt_handler(uint32_t id,
cm_el2_sysregs_context_save(NON_SECURE);
#else
cm_el1_sysregs_context_save(NON_SECURE);
#if CTX_INCLUDE_FPREGS || CTX_INCLUDE_SVE_REGS
/*
* The hint bit denoting absence of SVE live state is effectively false
* in this scenario where execution was trapped to EL3 due to FIQ.
*/
simd_ctx_save(NON_SECURE, false);
#endif
#endif
/* Convey the event to the SPMC through the FFA_INTERRUPT interface. */
@ -230,7 +238,14 @@ static uint64_t spmd_secure_interrupt_handler(uint32_t id,
/* Mark current core as handling a secure interrupt. */
ctx->secure_interrupt_ongoing = true;
#if CTX_INCLUDE_FPREGS || CTX_INCLUDE_SVE_REGS
simd_ctx_restore(SECURE);
#endif
rc = spmd_spm_core_sync_entry(ctx);
#if CTX_INCLUDE_FPREGS || CTX_INCLUDE_SVE_REGS
simd_ctx_save(SECURE, false);
#endif
if (rc != 0ULL) {
ERROR("%s failed (%" PRId64 ") on CPU%u\n", __func__, rc, plat_my_core_pos());
}
@ -241,6 +256,10 @@ static uint64_t spmd_secure_interrupt_handler(uint32_t id,
cm_el2_sysregs_context_restore(NON_SECURE);
#else
cm_el1_sysregs_context_restore(NON_SECURE);
#if CTX_INCLUDE_FPREGS || CTX_INCLUDE_SVE_REGS
simd_ctx_restore(NON_SECURE);
#endif
#endif
cm_set_next_eret_context(NON_SECURE);
@ -678,6 +697,10 @@ uint64_t spmd_smc_switch_state(uint32_t smc_fid,
cm_el2_sysregs_context_save(secure_state_in);
#else
cm_el1_sysregs_context_save(secure_state_in);
#if CTX_INCLUDE_FPREGS || CTX_INCLUDE_SVE_REGS
/* Forward the hint bit denoting the absence of SVE live state. */
simd_ctx_save(secure_state_in, (!secure_origin && (is_sve_hint_set(flags) == true)));
#endif
#endif
/* Restore outgoing security state */
@ -685,6 +708,9 @@ uint64_t spmd_smc_switch_state(uint32_t smc_fid,
cm_el2_sysregs_context_restore(secure_state_out);
#else
cm_el1_sysregs_context_restore(secure_state_out);
#if CTX_INCLUDE_FPREGS || CTX_INCLUDE_SVE_REGS
simd_ctx_restore(secure_state_out);
#endif
#endif
cm_set_next_eret_context(secure_state_out);