From: Alex Bennée <[email protected]>

The computation of s1ns was simply wrong. For Stage 2 faults, it
should indicate whether the faulting IPA is in the Non-Secure IPA
space. Correct the logic to check for ARMSS_NonSecure and drop the
extraneous s2_mmu_idx test.

This is effectively a change in the intended semantics of the
ARMMMUFaultInfo::s1ns field, so that we no longer try to make it
exactly match HPFAR_EL2.NS but instead set it for any stage 2 fault
on an NS IPA, relying on users of the field to check whether the
fault is to be taken to Secure EL2 before propagating the field to
the HPFAR_EL2.NS bit.  Since the actual writing of HPFAR_EL2.NS is
already gated by arm_is_secure_below_el3(env), we only need to update
the comments to document this change of semantics.

Cc: [email protected]
Resolves: https://gitlab.com/qemu-project/qemu/-/work_items/2568
Signed-off-by: Alex Bennée <[email protected]>
Reviewed-by: Richard Henderson <[email protected]>
Message-id: [email protected]
[PMM: also update comments about the s1ns field]
Reviewed-by: Peter Maydell <[email protected]>
Signed-off-by: Peter Maydell <[email protected]>
(cherry picked from commit 566594f10873723a179057a604d890bfaa1a9f0a)
Signed-off-by: Michael Tokarev <[email protected]>

diff --git a/target/arm/internals.h b/target/arm/internals.h
index 17221c847d..e95f791ce0 100644
--- a/target/arm/internals.h
+++ b/target/arm/internals.h
@@ -717,7 +717,10 @@ typedef enum ARMGPCF {
  * @paddr_space: physical address space that caused a fault for gpc
  * @stage2: True if we faulted at stage 2
  * @s1ptw: True if we faulted at stage 2 while doing a stage 1 page-table walk
- * @s1ns: True if we faulted on a non-secure IPA while in secure state
+ * @s1ns: True if we faulted on a non-secure IPA. Note that (unlike the
+ * HPFAR_EL2.NS bit) this is set for any stage 2 fault for an NS IPA, so
+ * code must check that this is for a fault taken to Secure EL2 before
+ * propagating s1ns to HPFAR_EL2.NS.
  * @ea: True if we should set the EA (external abort type) bit in syndrome
  */
 typedef struct ARMMMUFaultInfo ARMMMUFaultInfo;
diff --git a/target/arm/ptw.c b/target/arm/ptw.c
index 4330900348..92d6bd9d40 100644
--- a/target/arm/ptw.c
+++ b/target/arm/ptw.c
@@ -550,12 +550,14 @@ static ARMSecuritySpace 
S2_security_space(ARMSecuritySpace s1_space,
 static bool fault_s1ns(ARMSecuritySpace space, ARMMMUIdx s2_mmu_idx)
 {
     /*
-     * For stage 2 faults in Secure EL22, S1NS indicates
-     * whether the faulting IPA is in the Secure or NonSecure
-     * IPA space. For all other kinds of fault, it is false.
+     * For stage 2 faults, S1NS indicates whether the faulting IPA is
+     * in the Non-Secure (true) or Secure (false) IPA space. For all
+     * other kinds of fault, it is false. Note that we do not
+     * distinguish "s2 fault on NS IPA taken to Secure EL2" from
+     * "s2 fault on NS IPA taken to NS EL2 or Realm EL2" here, but
+     * instead do that when setting HPFAR_EL2.NS.
      */
-    return space == ARMSS_Secure && regime_is_stage2(s2_mmu_idx)
-        && s2_mmu_idx == ARMMMUIdx_Stage2_S;
+    return space == ARMSS_NonSecure && regime_is_stage2(s2_mmu_idx);
 }
 
 /* Translate a S1 pagetable walk through S2 if needed.  */
-- 
2.47.3


Reply via email to