mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-06 10:58:48 +09:00
ANDROID: BACKPORT: arm64: Enroll into KVM's MMIO guard if required
Should a guest desire to enroll into the MMIO guard, allow it to do so with a command-line option. Signed-off-by: Marc Zyngier <maz@kernel.org> Bug: 233587962 Change-Id: Ia9a77f693531740500739693c52b4959abacafd4 [willdeacon@: Add hypercall IDs] Signed-off-by: Will Deacon <willdeacon@google.com> Signed-off-by: Quentin Perret <qperret@google.com>
This commit is contained in:
committed by
Quentin Perret
parent
4c87d6516a
commit
f7c4ae96ad
@@ -2184,6 +2184,9 @@
|
||||
1 - Bypass the IOMMU for DMA.
|
||||
unset - Use value of CONFIG_IOMMU_DEFAULT_PASSTHROUGH.
|
||||
|
||||
ioremap_guard [ARM64] enable the KVM MMIO guard functionality
|
||||
if available.
|
||||
|
||||
io7= [HW] IO7 for Marvel-based Alpha systems
|
||||
See comment before marvel_specify_io7 in
|
||||
arch/alpha/kernel/core_marvel.c.
|
||||
|
||||
@@ -28,6 +28,7 @@ config ARM64
|
||||
select ARCH_HAS_FORTIFY_SOURCE
|
||||
select ARCH_HAS_GCOV_PROFILE_ALL
|
||||
select ARCH_HAS_GIGANTIC_PAGE
|
||||
select ARCH_HAS_IOREMAP_PHYS_HOOKS
|
||||
select ARCH_HAS_KCOV
|
||||
select ARCH_HAS_KEEPINITRD
|
||||
select ARCH_HAS_MEMBARRIER_SYNC_CORE
|
||||
|
||||
@@ -8,5 +8,6 @@ void kvm_init_hyp_services(void);
|
||||
bool kvm_arm_hyp_service_available(u32 func_id);
|
||||
void kvm_arm_init_hyp_services(void);
|
||||
void kvm_init_memshare_services(void);
|
||||
void kvm_init_ioremap_services(void);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -50,6 +50,7 @@
|
||||
#include <asm/tlbflush.h>
|
||||
#include <asm/traps.h>
|
||||
#include <asm/efi.h>
|
||||
#include <asm/hypervisor.h>
|
||||
#include <asm/xen/hypervisor.h>
|
||||
#include <asm/mmu_context.h>
|
||||
|
||||
@@ -442,5 +443,6 @@ device_initcall(register_arm64_panic_block);
|
||||
|
||||
void kvm_arm_init_hyp_services(void)
|
||||
{
|
||||
kvm_init_ioremap_services();
|
||||
kvm_init_memshare_services();
|
||||
}
|
||||
|
||||
@@ -11,6 +11,26 @@
|
||||
#include <asm/tlbflush.h>
|
||||
#include <asm/hypervisor.h>
|
||||
|
||||
#ifndef ARM_SMCCC_KVM_FUNC_MMIO_GUARD_INFO
|
||||
#define ARM_SMCCC_KVM_FUNC_MMIO_GUARD_INFO 5
|
||||
|
||||
#define ARM_SMCCC_VENDOR_HYP_KVM_MMIO_GUARD_INFO_FUNC_ID \
|
||||
ARM_SMCCC_CALL_VAL(ARM_SMCCC_FAST_CALL, \
|
||||
ARM_SMCCC_SMC_64, \
|
||||
ARM_SMCCC_OWNER_VENDOR_HYP, \
|
||||
ARM_SMCCC_KVM_FUNC_MMIO_GUARD_INFO)
|
||||
#endif /* ARM_SMCCC_KVM_FUNC_MMIO_GUARD_INFO */
|
||||
|
||||
#ifndef ARM_SMCCC_KVM_FUNC_MMIO_GUARD_ENROLL
|
||||
#define ARM_SMCCC_KVM_FUNC_MMIO_GUARD_ENROLL 6
|
||||
|
||||
#define ARM_SMCCC_VENDOR_HYP_KVM_MMIO_GUARD_ENROLL_FUNC_ID \
|
||||
ARM_SMCCC_CALL_VAL(ARM_SMCCC_FAST_CALL, \
|
||||
ARM_SMCCC_SMC_64, \
|
||||
ARM_SMCCC_OWNER_VENDOR_HYP, \
|
||||
ARM_SMCCC_KVM_FUNC_MMIO_GUARD_ENROLL)
|
||||
#endif /* ARM_SMCCC_KVM_FUNC_MMIO_GUARD_ENROLL */
|
||||
|
||||
#ifndef ARM_SMCCC_KVM_FUNC_MMIO_GUARD_MAP
|
||||
#define ARM_SMCCC_KVM_FUNC_MMIO_GUARD_MAP 7
|
||||
|
||||
@@ -39,6 +59,44 @@ static DEFINE_STATIC_KEY_FALSE(ioremap_guard_key);
|
||||
static DEFINE_XARRAY(ioremap_guard_array);
|
||||
static DEFINE_MUTEX(ioremap_guard_lock);
|
||||
|
||||
static bool ioremap_guard;
|
||||
static int __init ioremap_guard_setup(char *str)
|
||||
{
|
||||
ioremap_guard = true;
|
||||
|
||||
return 0;
|
||||
}
|
||||
early_param("ioremap_guard", ioremap_guard_setup);
|
||||
|
||||
void kvm_init_ioremap_services(void)
|
||||
{
|
||||
struct arm_smccc_res res;
|
||||
|
||||
if (!ioremap_guard)
|
||||
return;
|
||||
|
||||
/* We need all the functions to be implemented */
|
||||
if (!kvm_arm_hyp_service_available(ARM_SMCCC_KVM_FUNC_MMIO_GUARD_INFO) ||
|
||||
!kvm_arm_hyp_service_available(ARM_SMCCC_KVM_FUNC_MMIO_GUARD_ENROLL) ||
|
||||
!kvm_arm_hyp_service_available(ARM_SMCCC_KVM_FUNC_MMIO_GUARD_MAP) ||
|
||||
!kvm_arm_hyp_service_available(ARM_SMCCC_KVM_FUNC_MMIO_GUARD_UNMAP))
|
||||
return;
|
||||
|
||||
arm_smccc_1_1_invoke(ARM_SMCCC_VENDOR_HYP_KVM_MMIO_GUARD_INFO_FUNC_ID,
|
||||
0, 0, 0, &res);
|
||||
if (res.a0 != PAGE_SIZE)
|
||||
return;
|
||||
|
||||
arm_smccc_1_1_invoke(ARM_SMCCC_VENDOR_HYP_KVM_MMIO_GUARD_ENROLL_FUNC_ID,
|
||||
&res);
|
||||
if (res.a0 == SMCCC_RET_SUCCESS) {
|
||||
static_branch_enable(&ioremap_guard_key);
|
||||
pr_info("Using KVM MMIO guard for ioremap\n");
|
||||
} else {
|
||||
pr_warn("KVM MMIO guard registration failed (%ld)\n", res.a0);
|
||||
}
|
||||
}
|
||||
|
||||
void ioremap_phys_range_hook(phys_addr_t phys_addr, size_t size, pgprot_t prot)
|
||||
{
|
||||
if (!static_branch_unlikely(&ioremap_guard_key))
|
||||
|
||||
Reference in New Issue
Block a user