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

