[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-devel] [PATCH v4 3/5] vpci/msix: carve p2m hole for MSIX MMIO regions
Make sure the MSIX MMIO regions don't have p2m entries setup, so that accesses to them trap into the hypervisor and can be handled by vpci. Commit 042678762 ("x86/iommu: add map-reserved dom0-iommu option to map reserved memory ranges") added mappings for all the reserved regions into the PVH Dom0 p2m, and some of those reserved regions might contain MSIX MMIO regions, hence the need to make sure there are no mappings established. Signed-off-by: Roger Pau Monné <roger.pau@xxxxxxxxxx> --- Cc: Andrew Cooper <andrew.cooper3@xxxxxxxxxx> Cc: George Dunlap <George.Dunlap@xxxxxxxxxxxxx> Cc: Ian Jackson <ian.jackson@xxxxxxxxxxxxx> Cc: Jan Beulich <jbeulich@xxxxxxxx> Cc: Julien Grall <julien.grall@xxxxxxx> Cc: Konrad Rzeszutek Wilk <konrad.wilk@xxxxxxxxxx> Cc: Stefano Stabellini <sstabellini@xxxxxxxxxx> Cc: Tim Deegan <tim@xxxxxxx> Cc: Wei Liu <wei.liu2@xxxxxxxxxx> --- Changes since v3: - Allow p2m_invalid for unmapped regions. - Add a DomU FIXME comment. - Reword commit message. --- xen/drivers/vpci/header.c | 11 +++++++++ xen/drivers/vpci/msix.c | 49 +++++++++++++++++++++++++++++++++++++++ xen/include/xen/vpci.h | 3 +++ 3 files changed, 63 insertions(+) diff --git a/xen/drivers/vpci/header.c b/xen/drivers/vpci/header.c index 720dec07fa..f761804beb 100644 --- a/xen/drivers/vpci/header.c +++ b/xen/drivers/vpci/header.c @@ -89,6 +89,17 @@ static void modify_decoding(const struct pci_dev *pdev, uint16_t cmd, bool map = cmd & PCI_COMMAND_MEMORY; unsigned int i; + /* + * Make sure there are no mappings in the MSIX MMIO areas, so that accesses + * can be trapped (and emulated) by Xen when the memory decoding bit is + * enabled. + * + * FIXME: punching holes after the p2m has been set up might be racy for + * DomU usage, needs to be revisited. + */ + if ( map && !rom_only && vpci_make_msix_hole(pdev) ) + return; + for ( i = 0; i < ARRAY_SIZE(header->bars); i++ ) { if ( !MAPPABLE_BAR(&header->bars[i]) ) diff --git a/xen/drivers/vpci/msix.c b/xen/drivers/vpci/msix.c index 1960dae123..af3ffa087d 100644 --- a/xen/drivers/vpci/msix.c +++ b/xen/drivers/vpci/msix.c @@ -21,6 +21,7 @@ #include <xen/vpci.h> #include <asm/msi.h> +#include <asm/p2m.h> #define VMSIX_SIZE(num) offsetof(struct vpci_msix, entries[num]) @@ -395,6 +396,54 @@ static const struct hvm_mmio_ops vpci_msix_table_ops = { .write = msix_write, }; +int vpci_make_msix_hole(const struct pci_dev *pdev) +{ + struct domain *d = pdev->domain; + unsigned int i; + + if ( !pdev->vpci->msix ) + return 0; + + /* Make sure there's a hole for the MSIX table/PBA in the p2m. */ + for ( i = 0; i < ARRAY_SIZE(pdev->vpci->msix->tables); i++ ) + { + unsigned long start = PFN_DOWN(vmsix_table_addr(pdev->vpci, i)); + unsigned long end = PFN_DOWN(vmsix_table_addr(pdev->vpci, i) + + vmsix_table_size(pdev->vpci, i) - 1); + + for ( ; start <= end; start++ ) + { + p2m_type_t t; + mfn_t mfn = get_gfn_query(d, start, &t); + + switch ( t ) + { + case p2m_mmio_dm: + case p2m_invalid: + break; + case p2m_mmio_direct: + if ( mfn_x(mfn) == start ) + { + clear_identity_p2m_entry(d, start); + break; + } + /* fallthrough. */ + default: + put_gfn(d, start); + gprintk(XENLOG_WARNING, + "%04x:%02x:%02x.%u: existing mapping (mfn: %" PRI_mfn + "type: %d) at %#lx clobbers MSIX MMIO area\n", + pdev->seg, pdev->bus, PCI_SLOT(pdev->devfn), + PCI_FUNC(pdev->devfn), mfn_x(mfn), t, start); + return -EEXIST; + } + put_gfn(d, start); + } + } + + return 0; +} + static int init_msix(struct pci_dev *pdev) { struct domain *d = pdev->domain; diff --git a/xen/include/xen/vpci.h b/xen/include/xen/vpci.h index 44104b75b6..4cf233c779 100644 --- a/xen/include/xen/vpci.h +++ b/xen/include/xen/vpci.h @@ -152,6 +152,9 @@ struct vpci_vcpu { #ifdef __XEN__ void vpci_dump_msi(void); +/* Make sure there's a hole in the p2m for the MSIX mmio areas. */ +int vpci_make_msix_hole(const struct pci_dev *pdev); + /* Arch-specific vPCI MSI helpers. */ void vpci_msi_arch_mask(struct vpci_msi *msi, const struct pci_dev *pdev, unsigned int entry, bool mask); -- 2.19.1 _______________________________________________ Xen-devel mailing list Xen-devel@xxxxxxxxxxxxxxxxxxxx https://lists.xenproject.org/mailman/listinfo/xen-devel
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |