Skip to content

Commit 5c91941

Browse files
Andrey Smetaninbonzini
Andrey Smetanin
authored andcommitted
kvm/x86: Hyper-V synthetic interrupt controller
SynIC (synthetic interrupt controller) is a lapic extension, which is controlled via MSRs and maintains for each vCPU - 16 synthetic interrupt "lines" (SINT's); each can be configured to trigger a specific interrupt vector optionally with auto-EOI semantics - a message page in the guest memory with 16 256-byte per-SINT message slots - an event flag page in the guest memory with 16 2048-bit per-SINT event flag areas The host triggers a SINT whenever it delivers a new message to the corresponding slot or flips an event flag bit in the corresponding area. The guest informs the host that it can try delivering a message by explicitly asserting EOI in lapic or writing to End-Of-Message (EOM) MSR. The userspace (qemu) triggers interrupts and receives EOM notifications via irqfd with resampler; for that, a GSI is allocated for each configured SINT, and irq_routing api is extended to support GSI-SINT mapping. Changes v4: * added activation of SynIC by vcpu KVM_ENABLE_CAP * added per SynIC active flag * added deactivation of APICv upon SynIC activation Changes v3: * added KVM_CAP_HYPERV_SYNIC and KVM_IRQ_ROUTING_HV_SINT notes into docs Changes v2: * do not use posted interrupts for Hyper-V SynIC AutoEOI vectors * add Hyper-V SynIC vectors into EOI exit bitmap * Hyper-V SyniIC SINT msr write logic simplified Signed-off-by: Andrey Smetanin <[email protected]> Reviewed-by: Roman Kagan <[email protected]> Signed-off-by: Denis V. Lunev <[email protected]> CC: Gleb Natapov <[email protected]> CC: Paolo Bonzini <[email protected]> CC: Roman Kagan <[email protected]> CC: Denis V. Lunev <[email protected]> CC: [email protected] Signed-off-by: Paolo Bonzini <[email protected]>
1 parent d62caab commit 5c91941

File tree

10 files changed

+467
-7
lines changed

10 files changed

+467
-7
lines changed

Documentation/virtual/kvm/api.txt

+19
Original file line numberDiff line numberDiff line change
@@ -1451,6 +1451,7 @@ struct kvm_irq_routing_entry {
14511451
struct kvm_irq_routing_irqchip irqchip;
14521452
struct kvm_irq_routing_msi msi;
14531453
struct kvm_irq_routing_s390_adapter adapter;
1454+
struct kvm_irq_routing_hv_sint hv_sint;
14541455
__u32 pad[8];
14551456
} u;
14561457
};
@@ -1459,6 +1460,7 @@ struct kvm_irq_routing_entry {
14591460
#define KVM_IRQ_ROUTING_IRQCHIP 1
14601461
#define KVM_IRQ_ROUTING_MSI 2
14611462
#define KVM_IRQ_ROUTING_S390_ADAPTER 3
1463+
#define KVM_IRQ_ROUTING_HV_SINT 4
14621464

14631465
No flags are specified so far, the corresponding field must be set to zero.
14641466

@@ -1482,6 +1484,10 @@ struct kvm_irq_routing_s390_adapter {
14821484
__u32 adapter_id;
14831485
};
14841486

1487+
struct kvm_irq_routing_hv_sint {
1488+
__u32 vcpu;
1489+
__u32 sint;
1490+
};
14851491

14861492
4.53 KVM_ASSIGN_SET_MSIX_NR (deprecated)
14871493

@@ -3685,3 +3691,16 @@ available, means that that the kernel has an implementation of the
36853691
H_RANDOM hypercall backed by a hardware random-number generator.
36863692
If present, the kernel H_RANDOM handler can be enabled for guest use
36873693
with the KVM_CAP_PPC_ENABLE_HCALL capability.
3694+
3695+
8.2 KVM_CAP_HYPERV_SYNIC
3696+
3697+
Architectures: x86
3698+
This capability, if KVM_CHECK_EXTENSION indicates that it is
3699+
available, means that that the kernel has an implementation of the
3700+
Hyper-V Synthetic interrupt controller(SynIC). Hyper-V SynIC is
3701+
used to support Windows Hyper-V based guest paravirt drivers(VMBus).
3702+
3703+
In order to use SynIC, it has to be activated by setting this
3704+
capability via KVM_ENABLE_CAP ioctl on the vcpu fd. Note that this
3705+
will disable the use of APIC hardware virtualization even if supported
3706+
by the CPU, as it's incompatible with SynIC auto-EOI behavior.

arch/x86/include/asm/kvm_host.h

+15
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
#include <linux/pvclock_gtod.h>
2626
#include <linux/clocksource.h>
2727
#include <linux/irqbypass.h>
28+
#include <linux/hyperv.h>
2829

2930
#include <asm/pvclock-abi.h>
3031
#include <asm/desc.h>
@@ -374,10 +375,24 @@ struct kvm_mtrr {
374375
struct list_head head;
375376
};
376377

378+
/* Hyper-V synthetic interrupt controller (SynIC)*/
379+
struct kvm_vcpu_hv_synic {
380+
u64 version;
381+
u64 control;
382+
u64 msg_page;
383+
u64 evt_page;
384+
atomic64_t sint[HV_SYNIC_SINT_COUNT];
385+
atomic_t sint_to_gsi[HV_SYNIC_SINT_COUNT];
386+
DECLARE_BITMAP(auto_eoi_bitmap, 256);
387+
DECLARE_BITMAP(vec_bitmap, 256);
388+
bool active;
389+
};
390+
377391
/* Hyper-V per vcpu emulation context */
378392
struct kvm_vcpu_hv {
379393
u64 hv_vapic;
380394
s64 runtime_offset;
395+
struct kvm_vcpu_hv_synic synic;
381396
};
382397

383398
struct kvm_vcpu_arch {

0 commit comments

Comments
 (0)