]> www.infradead.org Git - users/hch/misc.git/commitdiff
KVM: arm64: Account for 52bit when computing maximum OA
authorMarc Zyngier <maz@kernel.org>
Sat, 26 Jul 2025 10:52:34 +0000 (11:52 +0100)
committerMarc Zyngier <maz@kernel.org>
Sat, 20 Sep 2025 10:05:12 +0000 (11:05 +0100)
Adjust the computation of the max OA to account for 52bit PAs.

Reviewed-by: Oliver Upton <oliver.upton@linux.dev>
Signed-off-by: Marc Zyngier <maz@kernel.org>
arch/arm64/include/asm/kvm_nested.h
arch/arm64/kvm/at.c
arch/arm64/kvm/nested.c

index 038e35430bb2cb84b6f8b3143422ff342244b9fe..1a03095b03c5b82876758f3d3a7dfc0ab95770b8 100644 (file)
@@ -265,7 +265,7 @@ static inline u64 decode_range_tlbi(u64 val, u64 *range, u16 *asid)
        return base;
 }
 
-static inline unsigned int ps_to_output_size(unsigned int ps)
+static inline unsigned int ps_to_output_size(unsigned int ps, bool pa52bit)
 {
        switch (ps) {
        case 0: return 32;
@@ -273,7 +273,10 @@ static inline unsigned int ps_to_output_size(unsigned int ps)
        case 2: return 40;
        case 3: return 42;
        case 4: return 44;
-       case 5:
+       case 5: return 48;
+       case 6: if (pa52bit)
+                       return 52;
+               fallthrough;
        default:
                return 48;
        }
index 8e275ea68cfa8ba924bcc0bcc2010db1c58ae99e..96452fdc90e2bbfcd7bde30eedad6e0747a621d4 100644 (file)
@@ -295,7 +295,7 @@ static int setup_s1_walk(struct kvm_vcpu *vcpu, struct s1_walk_info *wi,
        ps = (wi->regime == TR_EL2 ?
              FIELD_GET(TCR_EL2_PS_MASK, tcr) : FIELD_GET(TCR_IPS_MASK, tcr));
 
-       wi->max_oa_bits = min(get_kvm_ipa_limit(), ps_to_output_size(ps));
+       wi->max_oa_bits = min(get_kvm_ipa_limit(), ps_to_output_size(ps, wi->pa52bit));
 
        /* Compute minimal alignment */
        x = 3 + ia_bits - ((3 - wi->sl) * stride + wi->pgshift);
index 77db81bae86f9b1b4f34d63069a3bdebf03190ef..cb36974e010afcf7f798815c724a9b1bd1337449 100644 (file)
@@ -349,7 +349,7 @@ static void vtcr_to_walk_info(u64 vtcr, struct s2_walk_info *wi)
        wi->sl = FIELD_GET(VTCR_EL2_SL0_MASK, vtcr);
        /* Global limit for now, should eventually be per-VM */
        wi->max_oa_bits = min(get_kvm_ipa_limit(),
-                             ps_to_output_size(FIELD_GET(VTCR_EL2_PS_MASK, vtcr)));
+                             ps_to_output_size(FIELD_GET(VTCR_EL2_PS_MASK, vtcr), false));
 }
 
 int kvm_walk_nested_s2(struct kvm_vcpu *vcpu, phys_addr_t gipa,