Commit bd2e9513 authored by Oliver Upton's avatar Oliver Upton

Merge branch kvm-arm64/misc into kvmarm/next

* kvm-arm64/misc:
  : Miscellaneous updates
  :
  :  - Provide a command-line parameter to statically control the WFx trap
  :    selection in KVM
  :
  :  - Make sysreg masks allocation accounted
  Revert "KVM: arm64: nv: Fix RESx behaviour of disabled FGTs with negative polarity"
  KVM: arm64: nv: Use GFP_KERNEL_ACCOUNT for sysreg_masks allocation
  KVM: arm64: nv: Fix RESx behaviour of disabled FGTs with negative polarity
  KVM: arm64: Add early_param to control WFx trapping
Signed-off-by: default avatarOliver Upton <oliver.upton@linux.dev>
parents 83a7eefe cb52b5c8
...@@ -2745,6 +2745,24 @@ ...@@ -2745,6 +2745,24 @@
[KVM,ARM,EARLY] Allow use of GICv4 for direct [KVM,ARM,EARLY] Allow use of GICv4 for direct
injection of LPIs. injection of LPIs.
kvm-arm.wfe_trap_policy=
[KVM,ARM] Control when to set WFE instruction trap for
KVM VMs. Traps are allowed but not guaranteed by the
CPU architecture.
trap: set WFE instruction trap
notrap: clear WFE instruction trap
kvm-arm.wfi_trap_policy=
[KVM,ARM] Control when to set WFI instruction trap for
KVM VMs. Traps are allowed but not guaranteed by the
CPU architecture.
trap: set WFI instruction trap
notrap: clear WFI instruction trap
kvm_cma_resv_ratio=n [PPC,EARLY] kvm_cma_resv_ratio=n [PPC,EARLY]
Reserves given percentage from system memory area for Reserves given percentage from system memory area for
contiguous memory allocation for KVM hash pagetable contiguous memory allocation for KVM hash pagetable
......
...@@ -48,6 +48,15 @@ ...@@ -48,6 +48,15 @@
static enum kvm_mode kvm_mode = KVM_MODE_DEFAULT; static enum kvm_mode kvm_mode = KVM_MODE_DEFAULT;
enum kvm_wfx_trap_policy {
KVM_WFX_NOTRAP_SINGLE_TASK, /* Default option */
KVM_WFX_NOTRAP,
KVM_WFX_TRAP,
};
static enum kvm_wfx_trap_policy kvm_wfi_trap_policy __read_mostly = KVM_WFX_NOTRAP_SINGLE_TASK;
static enum kvm_wfx_trap_policy kvm_wfe_trap_policy __read_mostly = KVM_WFX_NOTRAP_SINGLE_TASK;
DECLARE_KVM_HYP_PER_CPU(unsigned long, kvm_hyp_vector); DECLARE_KVM_HYP_PER_CPU(unsigned long, kvm_hyp_vector);
DEFINE_PER_CPU(unsigned long, kvm_arm_hyp_stack_page); DEFINE_PER_CPU(unsigned long, kvm_arm_hyp_stack_page);
...@@ -546,6 +555,24 @@ static void vcpu_set_pauth_traps(struct kvm_vcpu *vcpu) ...@@ -546,6 +555,24 @@ static void vcpu_set_pauth_traps(struct kvm_vcpu *vcpu)
} }
} }
static bool kvm_vcpu_should_clear_twi(struct kvm_vcpu *vcpu)
{
if (unlikely(kvm_wfi_trap_policy != KVM_WFX_NOTRAP_SINGLE_TASK))
return kvm_wfi_trap_policy == KVM_WFX_NOTRAP;
return single_task_running() &&
(atomic_read(&vcpu->arch.vgic_cpu.vgic_v3.its_vpe.vlpi_count) ||
vcpu->kvm->arch.vgic.nassgireq);
}
static bool kvm_vcpu_should_clear_twe(struct kvm_vcpu *vcpu)
{
if (unlikely(kvm_wfe_trap_policy != KVM_WFX_NOTRAP_SINGLE_TASK))
return kvm_wfe_trap_policy == KVM_WFX_NOTRAP;
return single_task_running();
}
void kvm_arch_vcpu_load(struct kvm_vcpu *vcpu, int cpu) void kvm_arch_vcpu_load(struct kvm_vcpu *vcpu, int cpu)
{ {
struct kvm_s2_mmu *mmu; struct kvm_s2_mmu *mmu;
...@@ -579,10 +606,15 @@ void kvm_arch_vcpu_load(struct kvm_vcpu *vcpu, int cpu) ...@@ -579,10 +606,15 @@ void kvm_arch_vcpu_load(struct kvm_vcpu *vcpu, int cpu)
if (kvm_arm_is_pvtime_enabled(&vcpu->arch)) if (kvm_arm_is_pvtime_enabled(&vcpu->arch))
kvm_make_request(KVM_REQ_RECORD_STEAL, vcpu); kvm_make_request(KVM_REQ_RECORD_STEAL, vcpu);
if (single_task_running()) if (kvm_vcpu_should_clear_twe(vcpu))
vcpu_clear_wfx_traps(vcpu); vcpu->arch.hcr_el2 &= ~HCR_TWE;
else
vcpu->arch.hcr_el2 |= HCR_TWE;
if (kvm_vcpu_should_clear_twi(vcpu))
vcpu->arch.hcr_el2 &= ~HCR_TWI;
else else
vcpu_set_wfx_traps(vcpu); vcpu->arch.hcr_el2 |= HCR_TWI;
vcpu_set_pauth_traps(vcpu); vcpu_set_pauth_traps(vcpu);
...@@ -2858,6 +2890,36 @@ static int __init early_kvm_mode_cfg(char *arg) ...@@ -2858,6 +2890,36 @@ static int __init early_kvm_mode_cfg(char *arg)
} }
early_param("kvm-arm.mode", early_kvm_mode_cfg); early_param("kvm-arm.mode", early_kvm_mode_cfg);
static int __init early_kvm_wfx_trap_policy_cfg(char *arg, enum kvm_wfx_trap_policy *p)
{
if (!arg)
return -EINVAL;
if (strcmp(arg, "trap") == 0) {
*p = KVM_WFX_TRAP;
return 0;
}
if (strcmp(arg, "notrap") == 0) {
*p = KVM_WFX_NOTRAP;
return 0;
}
return -EINVAL;
}
static int __init early_kvm_wfi_trap_policy_cfg(char *arg)
{
return early_kvm_wfx_trap_policy_cfg(arg, &kvm_wfi_trap_policy);
}
early_param("kvm-arm.wfi_trap_policy", early_kvm_wfi_trap_policy_cfg);
static int __init early_kvm_wfe_trap_policy_cfg(char *arg)
{
return early_kvm_wfx_trap_policy_cfg(arg, &kvm_wfe_trap_policy);
}
early_param("kvm-arm.wfe_trap_policy", early_kvm_wfe_trap_policy_cfg);
enum kvm_mode kvm_get_mode(void) enum kvm_mode kvm_get_mode(void)
{ {
return kvm_mode; return kvm_mode;
......
...@@ -198,7 +198,7 @@ int kvm_init_nv_sysregs(struct kvm *kvm) ...@@ -198,7 +198,7 @@ int kvm_init_nv_sysregs(struct kvm *kvm)
goto out; goto out;
kvm->arch.sysreg_masks = kzalloc(sizeof(*(kvm->arch.sysreg_masks)), kvm->arch.sysreg_masks = kzalloc(sizeof(*(kvm->arch.sysreg_masks)),
GFP_KERNEL); GFP_KERNEL_ACCOUNT);
if (!kvm->arch.sysreg_masks) { if (!kvm->arch.sysreg_masks) {
ret = -ENOMEM; ret = -ENOMEM;
goto out; goto out;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment