diff --git a/include/lib/el3_runtime/aarch64/context.h b/include/lib/el3_runtime/aarch64/context.h index 47d91de0d..235b2cf41 100644 --- a/include/lib/el3_runtime/aarch64/context.h +++ b/include/lib/el3_runtime/aarch64/context.h @@ -341,9 +341,9 @@ /******************************************************************************* * Registers initialised in a per-world context. ******************************************************************************/ -#define CTX_CPTR_EL3 U(0x0) -#define CTX_ZCR_EL3 U(0x8) -#define CTX_GLOBAL_EL3STATE_END U(0x10) +#define CTX_CPTR_EL3 U(0x0) +#define CTX_ZCR_EL3 U(0x8) +#define CTX_PERWORLD_EL3STATE_END U(0x10) #ifndef __ASSEMBLER__ diff --git a/include/lib/el3_runtime/context_mgmt.h b/include/lib/el3_runtime/context_mgmt.h index b2bdaf5a2..f631125f0 100644 --- a/include/lib/el3_runtime/context_mgmt.h +++ b/include/lib/el3_runtime/context_mgmt.h @@ -40,7 +40,9 @@ void cm_prepare_el3_exit_ns(void); #if IMAGE_BL31 void cm_manage_extensions_el3(void); void manage_extensions_nonsecure_per_world(void); +void cm_el3_arch_init_per_world(per_world_context_t *per_world_ctx); #endif + #if CTX_INCLUDE_EL2_REGS void cm_el2_sysregs_context_save(uint32_t security_state); void cm_el2_sysregs_context_restore(uint32_t security_state); diff --git a/lib/el3_runtime/aarch64/context.S b/lib/el3_runtime/aarch64/context.S index 631094f73..18bdca82e 100644 --- a/lib/el3_runtime/aarch64/context.S +++ b/lib/el3_runtime/aarch64/context.S @@ -581,7 +581,7 @@ endfunc save_and_update_ptw_el1_sys_regs .macro get_per_world_context _reg:req ldr x10, [sp, #CTX_EL3STATE_OFFSET + CTX_SCR_EL3] get_security_state x9, x10 - mov_imm x10, (CTX_GLOBAL_EL3STATE_END - CTX_CPTR_EL3) + mov_imm x10, (CTX_PERWORLD_EL3STATE_END - CTX_CPTR_EL3) mul x9, x9, x10 adrp x10, per_world_context add x10, x10, :lo12:per_world_context diff --git a/lib/el3_runtime/aarch64/context_mgmt.c b/lib/el3_runtime/aarch64/context_mgmt.c index fdd1388cb..a0212c6b6 100644 --- a/lib/el3_runtime/aarch64/context_mgmt.c +++ b/lib/el3_runtime/aarch64/context_mgmt.c @@ -600,6 +600,28 @@ void cm_manage_extensions_el3(void) } #endif /* IMAGE_BL31 */ +/****************************************************************************** + * Function to initialise the registers with the RESET values in the context + * memory, which are maintained per world. + ******************************************************************************/ +#if IMAGE_BL31 +void cm_el3_arch_init_per_world(per_world_context_t *per_world_ctx) +{ + /* + * Initialise CPTR_EL3, setting all fields rather than relying on hw. + * + * CPTR_EL3.TFP: Set to zero so that accesses to the V- or Z- registers + * by Advanced SIMD, floating-point or SVE instructions (if + * implemented) do not trap to EL3. + * + * CPTR_EL3.TCPAC: Set to zero so that accesses to CPACR_EL1, + * CPTR_EL2,CPACR, or HCPTR do not trap to EL3. + */ + uint64_t cptr_el3 = CPTR_EL3_RESET_VAL & ~(TCPAC_BIT | TFP_BIT); + per_world_ctx->ctx_cptr_el3 = cptr_el3; +} +#endif /* IMAGE_BL31 */ + /******************************************************************************* * Initialise per_world_context for Non-Secure world. * This function enables the architecture extensions, which have same value @@ -608,6 +630,8 @@ void cm_manage_extensions_el3(void) #if IMAGE_BL31 void manage_extensions_nonsecure_per_world(void) { + cm_el3_arch_init_per_world(&per_world_context[CPU_CONTEXT_NS]); + if (is_feat_sme_supported()) { sme_enable_per_world(&per_world_context[CPU_CONTEXT_NS]); } @@ -631,10 +655,11 @@ void manage_extensions_nonsecure_per_world(void) * This function enables the architecture extensions, which have same value * across the cores for the secure world. ******************************************************************************/ - static void manage_extensions_secure_per_world(void) { #if IMAGE_BL31 + cm_el3_arch_init_per_world(&per_world_context[CPU_CONTEXT_SECURE]); + if (is_feat_sme_supported()) { if (ENABLE_SME_FOR_SWD) { diff --git a/services/std_svc/rmmd/rmmd_main.c b/services/std_svc/rmmd/rmmd_main.c index 8b78b1357..4ea074fd6 100644 --- a/services/std_svc/rmmd/rmmd_main.c +++ b/services/std_svc/rmmd/rmmd_main.c @@ -134,6 +134,8 @@ static void manage_extensions_realm(cpu_context_t *ctx) static void manage_extensions_realm_per_world(void) { + cm_el3_arch_init_per_world(&per_world_context[CPU_CONTEXT_REALM]); + if (is_feat_sve_supported()) { /* * Enable SVE and FPU in realm context when it is enabled for NS.