From 417ce1b32daa19f8c6c2263105e43d206708c043 Mon Sep 17 00:00:00 2001 From: Binbin Wu Date: Wed, 13 May 2020 15:02:48 +0000 Subject: [PATCH] dm: passthru: add support to allocate a bar for vmsix on msi emulation New option "vmsix_on_msi," is added to specify the passthrough device needs vMSI-X emulation based on MSI capability. If vMSI-X on MSI emulation is needed, a virtual BAR will be allocated. Also, fix a logic error on when to setup INTx. Tracked-On: #4831 Signed-off-by: Binbin Wu Acked-by: Eddie Dong --- devicemodel/hw/pci/passthrough.c | 33 +++++++++++++++++++++++++++++++- 1 file changed, 32 insertions(+), 1 deletion(-) diff --git a/devicemodel/hw/pci/passthrough.c b/devicemodel/hw/pci/passthrough.c index a5c50b6b2..41fcf7fd0 100644 --- a/devicemodel/hw/pci/passthrough.c +++ b/devicemodel/hw/pci/passthrough.c @@ -467,6 +467,22 @@ passthru_gpu_dsm_opregion(struct vmctx *ctx, struct passthru_dev *ptdev, pcidev->type = QUIRK_PTDEV; } +static int +parse_vmsix_on_msi_bar_id(char *s, int *id, int base) +{ + char *str, *cp; + int ret = 0; + + if (s == NULL) + return -EINVAL; + + str = cp = strdup(s); + ret = dm_strtoi(cp, &cp, base, id); + free(str); + + return ret; +} + /* * Passthrough device initialization function: * - initialize virtual config space @@ -488,6 +504,7 @@ passthru_init(struct vmctx *ctx, struct pci_vdev *dev, char *opts) char *opt; bool keep_gsi = false; bool need_reset = true; + int vmsix_on_msi_bar_id = -1; struct acrn_assign_pcidev pcidev = {}; uint16_t vendor = 0, device = 0; @@ -519,6 +536,13 @@ passthru_init(struct vmctx *ctx, struct pci_vdev *dev, char *opts) /* Create the dedicated "igd-lpc" on 00:1f.0 for IGD passthrough */ if (pci_parse_slot("31,igd-lpc") != 0) warnx("faild to create igd-lpc"); + } else if (!strncmp(opt, "vmsix_on_msi", 12)) { + opt = strsep(&opts, ","); + if (parse_vmsix_on_msi_bar_id(opt, &vmsix_on_msi_bar_id, 10) != 0) { + warnx("faild to parse msix emulation bar id"); + return -EINVAL; + } + } else warnx("Invalid passthru options:%s", opt); } @@ -589,6 +613,13 @@ passthru_init(struct vmctx *ctx, struct pci_vdev *dev, char *opts) if (error < 0) goto done; + if (vmsix_on_msi_bar_id != -1) { + error = pci_emul_alloc_pbar(dev, vmsix_on_msi_bar_id, 0, PCIBAR_MEM32, 4096); + if (error < 0) + goto done; + error = IRQ_MSI; + } + if (ptdev->phys_bdf == PCI_BDF_GPU) passthru_gpu_dsm_opregion(ctx, ptdev, &pcidev, device); @@ -602,7 +633,7 @@ passthru_init(struct vmctx *ctx, struct pci_vdev *dev, char *opts) * Forge Guest to use MSI/MSIX in this case to mitigate IRQ sharing * issue */ - if (error != IRQ_MSI && !keep_gsi) { + if (error != IRQ_MSI || keep_gsi) { /* Allocates the virq if ptdev only support INTx */ pci_lintr_request(dev);