mirror of
https://github.com/ARM-software/arm-trusted-firmware.git
synced 2025-04-07 21:33:54 +00:00
Merge "refactor(sdei): use common create_spsr() in SDEI library" into integration
This commit is contained in:
commit
e3ecd73116
3 changed files with 6 additions and 55 deletions
|
@ -97,7 +97,7 @@ static u_register_t get_elr_el3(u_register_t spsr_el3, u_register_t vbar, unsign
|
|||
* NOTE: This piece of code must be reviewed every release to ensure that
|
||||
* we keep up with new ARCH features which introduces a new SPSR bit.
|
||||
*/
|
||||
static u_register_t create_spsr(u_register_t old_spsr, unsigned int target_el)
|
||||
u_register_t create_spsr(u_register_t old_spsr, unsigned int target_el)
|
||||
{
|
||||
u_register_t new_spsr = 0;
|
||||
u_register_t sctlr;
|
||||
|
|
|
@ -58,6 +58,8 @@ int handle_sysreg_trap(uint64_t esr_el3, cpu_context_t *ctx);
|
|||
/* Handler for injecting UNDEF exception to lower EL */
|
||||
void inject_undef64(cpu_context_t *ctx);
|
||||
|
||||
u_register_t create_spsr(u_register_t old_spsr, unsigned int target_el);
|
||||
|
||||
/* Prototypes for system register emulation handlers provided by platforms. */
|
||||
int plat_handle_impdef_trap(uint64_t esr_el3, cpu_context_t *ctx);
|
||||
int plat_handle_rng_trap(uint64_t esr_el3, cpu_context_t *ctx);
|
||||
|
|
|
@ -13,6 +13,7 @@
|
|||
#include <arch_features.h>
|
||||
#include <bl31/ehf.h>
|
||||
#include <bl31/interrupt_mgmt.h>
|
||||
#include <bl31/sync_handle.h>
|
||||
#include <common/bl_common.h>
|
||||
#include <common/debug.h>
|
||||
#include <common/runtime_svc.h>
|
||||
|
@ -237,9 +238,7 @@ static cpu_context_t *restore_and_resume_ns_context(void)
|
|||
/*
|
||||
* Prepare for ERET:
|
||||
* - Set the ELR to the registered handler address
|
||||
* - Set the SPSR register as described in the SDEI documentation and
|
||||
* the AArch64.TakeException() pseudocode function in
|
||||
* ARM DDI 0487F.c page J1-7635
|
||||
* - Set the SPSR register by calling the common create_spsr() function
|
||||
*/
|
||||
|
||||
static void sdei_set_elr_spsr(sdei_entry_t *se, sdei_dispatch_context_t *disp_ctx)
|
||||
|
@ -250,57 +249,7 @@ static void sdei_set_elr_spsr(sdei_entry_t *se, sdei_dispatch_context_t *disp_ct
|
|||
|
||||
u_register_t interrupted_pstate = disp_ctx->spsr_el3;
|
||||
|
||||
/* Check the SPAN bit in the client el SCTLR */
|
||||
u_register_t client_el_sctlr;
|
||||
|
||||
if (client_el == MODE_EL2) {
|
||||
client_el_sctlr = read_sctlr_el2();
|
||||
} else {
|
||||
client_el_sctlr = read_sctlr_el1();
|
||||
}
|
||||
|
||||
/*
|
||||
* Check whether to force the PAN bit or use the value in the
|
||||
* interrupted EL according to the check described in
|
||||
* TakeException. Since the client can only be Non-Secure
|
||||
* EL2 or El1 some of the conditions in ElIsInHost() we know
|
||||
* will always be True.
|
||||
* When the client_el is EL2 we know that there will be a SPAN
|
||||
* bit in SCTLR_EL2 as we have already checked for the condition
|
||||
* HCR_EL2.E2H = 1 and HCR_EL2.TGE = 1
|
||||
*/
|
||||
u_register_t hcr_el2 = read_hcr();
|
||||
bool el_is_in_host = (read_feat_vhe_id_field() != 0U) &&
|
||||
(hcr_el2 & HCR_TGE_BIT) &&
|
||||
(hcr_el2 & HCR_E2H_BIT);
|
||||
|
||||
if (is_feat_pan_supported() &&
|
||||
((client_el == MODE_EL1) ||
|
||||
(client_el == MODE_EL2 && el_is_in_host)) &&
|
||||
((client_el_sctlr & SCTLR_SPAN_BIT) == 0U)) {
|
||||
sdei_spsr |= SPSR_PAN_BIT;
|
||||
} else {
|
||||
sdei_spsr |= (interrupted_pstate & SPSR_PAN_BIT);
|
||||
}
|
||||
|
||||
/* If SSBS is implemented, take the value from the client el SCTLR */
|
||||
u_register_t ssbs_enabled = (read_id_aa64pfr1_el1()
|
||||
>> ID_AA64PFR1_EL1_SSBS_SHIFT)
|
||||
& ID_AA64PFR1_EL1_SSBS_MASK;
|
||||
if (ssbs_enabled != SSBS_UNAVAILABLE) {
|
||||
u_register_t ssbs_bit = ((client_el_sctlr & SCTLR_DSSBS_BIT)
|
||||
>> SCTLR_DSSBS_SHIFT)
|
||||
<< SPSR_SSBS_SHIFT_AARCH64;
|
||||
sdei_spsr |= ssbs_bit;
|
||||
}
|
||||
|
||||
/* If MTE is implemented in the client el set the TCO bit */
|
||||
if (is_feat_mte_supported()) {
|
||||
sdei_spsr |= SPSR_TCO_BIT_AARCH64;
|
||||
}
|
||||
|
||||
/* Take the DIT field from the pstate of the interrupted el */
|
||||
sdei_spsr |= (interrupted_pstate & SPSR_DIT_BIT);
|
||||
sdei_spsr = create_spsr(interrupted_pstate, client_el);
|
||||
|
||||
cm_set_elr_spsr_el3(NON_SECURE, (uintptr_t) se->ep, sdei_spsr);
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue