In hv_common_cpu_init(), the per-CPU hypercall input/output pages need
to be marked as decrypted (shared) for confidential VM isolation types.
This is already done for SNP and TDX isolation; extend the same handling
to Arm CCA Realm guests so that the host hypervisor can access the
shared hypercall buffers.

is_realm_world() is only declared in arch/arm64/include/asm/rsi.h, so
using it directly in the arch-neutral drivers/hv/hv_common.c would
break the x86 build. Introduce a Hyper-V-specific helper following the
established hv_isolation_type_snp() / hv_isolation_type_tdx() pattern.

On architectures other than arm64 the weak default keeps the existing
behaviour.

Signed-off-by: Kameron Carr <[email protected]>
---
 arch/arm64/hyperv/mshyperv.c   |  5 +++++
 drivers/hv/hv_common.c         | 17 +++++++++++++----
 include/asm-generic/mshyperv.h |  1 +
 3 files changed, 19 insertions(+), 4 deletions(-)

diff --git a/arch/arm64/hyperv/mshyperv.c b/arch/arm64/hyperv/mshyperv.c
index d9010e64ddd7c..8519f694f2897 100644
--- a/arch/arm64/hyperv/mshyperv.c
+++ b/arch/arm64/hyperv/mshyperv.c
@@ -158,3 +158,8 @@ bool hv_is_hyperv_initialized(void)
        return hyperv_initialized;
 }
 EXPORT_SYMBOL_GPL(hv_is_hyperv_initialized);
+
+bool hv_isolation_type_cca(void)
+{
+       return is_realm_world();
+}
diff --git a/drivers/hv/hv_common.c b/drivers/hv/hv_common.c
index 6b67ac6167891..0f9412fcb9571 100644
--- a/drivers/hv/hv_common.c
+++ b/drivers/hv/hv_common.c
@@ -476,6 +476,7 @@ int hv_common_cpu_init(unsigned int cpu)
        u64 msr_vp_index;
        gfp_t flags;
        const int pgcount = hv_output_page_exists() ? 2 : 1;
+       const size_t alloc_size = ALIGN((size_t)pgcount * HV_HYP_PAGE_SIZE, 
PAGE_SIZE);
        void *mem;
        int ret = 0;
 
@@ -489,7 +490,7 @@ int hv_common_cpu_init(unsigned int cpu)
         * online and then taken offline
         */
        if (!*inputarg) {
-               mem = kmalloc_array(pgcount, HV_HYP_PAGE_SIZE, flags);
+               mem = kmalloc(alloc_size, flags);
                if (!mem)
                        return -ENOMEM;
 
@@ -499,14 +500,16 @@ int hv_common_cpu_init(unsigned int cpu)
                }
 
                if (!ms_hyperv.paravisor_present &&
-                   (hv_isolation_type_snp() || hv_isolation_type_tdx())) {
-                       ret = set_memory_decrypted((unsigned long)mem, pgcount);
+                   (hv_isolation_type_snp() || hv_isolation_type_tdx() ||
+                    hv_isolation_type_cca())) {
+                       ret = set_memory_decrypted((unsigned long)mem,
+                                                  alloc_size >> PAGE_SHIFT);
                        if (ret) {
                                /* It may be unsafe to free 'mem' */
                                return ret;
                        }
 
-                       memset(mem, 0x00, pgcount * HV_HYP_PAGE_SIZE);
+                       memset(mem, 0x00, alloc_size);
                }
 
                /*
@@ -666,6 +669,12 @@ bool __weak hv_isolation_type_tdx(void)
 }
 EXPORT_SYMBOL_GPL(hv_isolation_type_tdx);
 
+bool __weak hv_isolation_type_cca(void)
+{
+       return false;
+}
+EXPORT_SYMBOL_GPL(hv_isolation_type_cca);
+
 void __weak hv_setup_vmbus_handler(void (*handler)(void))
 {
 }
diff --git a/include/asm-generic/mshyperv.h b/include/asm-generic/mshyperv.h
index bf601d67cecb9..1fa79abce743c 100644
--- a/include/asm-generic/mshyperv.h
+++ b/include/asm-generic/mshyperv.h
@@ -79,6 +79,7 @@ u64 hv_do_fast_hypercall16(u16 control, u64 input1, u64 
input2);
 
 bool hv_isolation_type_snp(void);
 bool hv_isolation_type_tdx(void);
+bool hv_isolation_type_cca(void);
 
 /*
  * On architectures where Hyper-V doesn't support AEOI (e.g., ARM64),
-- 
2.45.4


Reply via email to