Skip to content

Commit b3a37bf

Browse files
sagishahsean-jc
authored andcommitted
KVM: TDX: Reject fully in-kernel irqchip if EOIs are protected, i.e. for TDX VMs
Reject KVM_CREATE_IRQCHIP if the VM type has protected EOIs, i.e. if KVM can't intercept EOI and thus can't faithfully emulate level-triggered interrupts that are routed through the I/O APIC. For TDX VMs, the TDX-Module owns the VMX EOI-bitmap and configures all IRQ vectors to have the CPU accelerate EOIs, i.e. doesn't allow KVM to intercept any EOIs. KVM already requires a split irqchip[1], but does so during vCPU creation, which is both too late to allow userspace to fallback to a split irqchip and a less-than-stellar experience for userspace since an -EINVAL on KVM_VCPU_CREATE is far harder to debug/triage than failure exactly on KVM_CREATE_IRQCHIP. And of course, allowing an action that ultimately fails is arguably a bug regardless of the impact on userspace. Link: https://lore.kernel.org/lkml/20250222014757.897978-11-binbin.wu@linux.intel.com [1] Link: https://lore.kernel.org/lkml/aK3vZ5HuKKeFuuM4@google.com Suggested-by: Sean Christopherson <seanjc@google.com> Signed-off-by: Sagi Shahar <sagis@google.com> Reviewed-by: Xiaoyao Li <xiaoyao.li@intel.com> Reviewed-by: Binbin Wu <binbin.wu@linux.intel.com> Acked-by: Kai Huang <kai.huang@intel.com> Link: https://lore.kernel.org/r/20250827011726.2451115-1-sagis@google.com [sean: massage shortlog+changelog, relocate setting has_protected_eoi] Signed-off-by: Sean Christopherson <seanjc@google.com>
1 parent aac057d commit b3a37bf

3 files changed

Lines changed: 15 additions & 0 deletions

File tree

arch/x86/include/asm/kvm_host.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1362,6 +1362,7 @@ struct kvm_arch {
13621362
u8 vm_type;
13631363
bool has_private_mem;
13641364
bool has_protected_state;
1365+
bool has_protected_eoi;
13651366
bool pre_fault_allowed;
13661367
struct hlist_head *mmu_page_hash;
13671368
struct list_head active_mmu_pages;

arch/x86/kvm/vmx/tdx.c

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -629,6 +629,11 @@ int tdx_vm_init(struct kvm *kvm)
629629
struct kvm_tdx *kvm_tdx = to_kvm_tdx(kvm);
630630

631631
kvm->arch.has_protected_state = true;
632+
/*
633+
* TDX Module doesn't allow the hypervisor to modify the EOI-bitmap,
634+
* i.e. all EOIs are accelerated and never trigger exits.
635+
*/
636+
kvm->arch.has_protected_eoi = true;
632637
kvm->arch.has_private_mem = true;
633638
kvm->arch.disabled_quirks |= KVM_X86_QUIRK_IGNORE_GUEST_PAT;
634639

arch/x86/kvm/x86.c

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6989,6 +6989,15 @@ int kvm_arch_vm_ioctl(struct file *filp, unsigned int ioctl, unsigned long arg)
69896989
if (irqchip_in_kernel(kvm))
69906990
goto create_irqchip_unlock;
69916991

6992+
/*
6993+
* Disallow an in-kernel I/O APIC if the VM has protected EOIs,
6994+
* i.e. if KVM can't intercept EOIs and thus can't properly
6995+
* emulate level-triggered interrupts.
6996+
*/
6997+
r = -ENOTTY;
6998+
if (kvm->arch.has_protected_eoi)
6999+
goto create_irqchip_unlock;
7000+
69927001
r = -EINVAL;
69937002
if (kvm->created_vcpus)
69947003
goto create_irqchip_unlock;

0 commit comments

Comments
 (0)