diff options
author | Alex Williamson <alex.williamson@redhat.com> | 2018-06-05 08:23:17 -0600 |
---|---|---|
committer | Alex Williamson <alex.williamson@redhat.com> | 2018-06-05 08:23:17 -0600 |
commit | c958c51d2e9923d0eb14dfec46920f69bd793cb4 (patch) | |
tree | aea08ad5bd1f914b7f4546fb52d8e8220908b169 /hw/vfio/pci.h | |
parent | 469d02de993817dcf4430d08fdff92aef8352d8f (diff) |
vfio/quirks: ioeventfd quirk acceleration
The NVIDIA BAR0 quirks virtualize the PCI config space mirrors found
in device MMIO space. Normally PCI config space is considered a slow
path and further optimization is unnecessary, however NVIDIA uses a
register here to enable the MSI interrupt to re-trigger. Exiting to
QEMU for this MSI-ACK handling can therefore rate limit our interrupt
handling. Fortunately the MSI-ACK write is easily detected since the
quirk MemoryRegion otherwise has very few accesses, so simply looking
for consecutive writes with the same data is sufficient, in this case
10 consecutive writes with the same data and size is arbitrarily
chosen. We configure the KVM ioeventfd with data match, so there's
no risk of triggering for the wrong data or size, but we do risk that
pathological driver behavior might consume all of QEMU's file
descriptors, so we cap ourselves to 10 ioeventfds for this purpose.
In support of the above, generic ioeventfd infrastructure is added
for vfio quirks. This automatically initializes an ioeventfd list
per quirk, disables and frees ioeventfds on exit, and allows
ioeventfds marked as dynamic to be dropped on device reset. The
rationale for this latter feature is that useful ioeventfds may
depend on specific driver behavior and since we necessarily place a
cap on our use of ioeventfds, a machine reset is a reasonable point
at which to assume a new driver and re-profile.
Reviewed-by: Peter Xu <peterx@redhat.com>
Reviewed-by: Eric Auger <eric.auger@redhat.com>
Signed-off-by: Alex Williamson <alex.williamson@redhat.com>
Diffstat (limited to 'hw/vfio/pci.h')
-rw-r--r-- | hw/vfio/pci.h | 14 |
1 files changed, 14 insertions, 0 deletions
diff --git a/hw/vfio/pci.h b/hw/vfio/pci.h index 594a5bd005..a4ac583fbd 100644 --- a/hw/vfio/pci.h +++ b/hw/vfio/pci.h @@ -24,9 +24,22 @@ struct VFIOPCIDevice; +typedef struct VFIOIOEventFD { + QLIST_ENTRY(VFIOIOEventFD) next; + MemoryRegion *mr; + hwaddr addr; + unsigned size; + uint64_t data; + EventNotifier e; + VFIORegion *region; + hwaddr region_addr; + bool dynamic; /* Added runtime, removed on device reset */ +} VFIOIOEventFD; + typedef struct VFIOQuirk { QLIST_ENTRY(VFIOQuirk) next; void *data; + QLIST_HEAD(, VFIOIOEventFD) ioeventfds; int nr_mem; MemoryRegion *mem; void (*reset)(struct VFIOPCIDevice *vdev, struct VFIOQuirk *quirk); @@ -149,6 +162,7 @@ typedef struct VFIOPCIDevice { bool no_kvm_msi; bool no_kvm_msix; bool no_geforce_quirks; + bool no_kvm_ioeventfd; VFIODisplay *dpy; } VFIOPCIDevice; |