summary refs log tree commit diff
path: root/drivers/pci
diff options
context:
space:
mode:
authorBjorn Helgaas <bhelgaas@google.com>2019-07-12 17:08:29 -0500
committerBjorn Helgaas <bhelgaas@google.com>2019-07-12 17:08:29 -0500
commit55ab3ecb81d5c071287a17567f7573f16934a9e9 (patch)
treeaac0a34ad9546b82137e533eca94e24cb76f299d /drivers/pci
parent8c6af6f04252110b3e4c2ff1614a4518d5208383 (diff)
parent06013b647c708e4f3179b7b0cf3adf28cb8cbfcf (diff)
downloadlinux-55ab3ecb81d5c071287a17567f7573f16934a9e9.tar.gz
Merge branch 'pci/virtualization'
  - Fix problem with caching VF config space size (Alex Williamson)

* pci/virtualization:
  PCI/IOV: Assume SR-IOV VFs support extended config space.
  Revert "PCI/IOV: Use VF0 cached config space size for other VFs"
Diffstat (limited to 'drivers/pci')
-rw-r--r--drivers/pci/iov.c2
-rw-r--r--drivers/pci/pci.h1
-rw-r--r--drivers/pci/probe.c26
3 files changed, 12 insertions, 17 deletions
diff --git a/drivers/pci/iov.c b/drivers/pci/iov.c
index 3aa115ed3a65..525fd3f272b3 100644
--- a/drivers/pci/iov.c
+++ b/drivers/pci/iov.c
@@ -132,8 +132,6 @@ static void pci_read_vf_config_common(struct pci_dev *virtfn)
 			     &physfn->sriov->subsystem_vendor);
 	pci_read_config_word(virtfn, PCI_SUBSYSTEM_ID,
 			     &physfn->sriov->subsystem_device);
-
-	physfn->sriov->cfg_size = pci_cfg_space_size(virtfn);
 }
 
 int pci_iov_add_virtfn(struct pci_dev *dev, int id)
diff --git a/drivers/pci/pci.h b/drivers/pci/pci.h
index 9cb99380c61e..3fc227ef0815 100644
--- a/drivers/pci/pci.h
+++ b/drivers/pci/pci.h
@@ -293,7 +293,6 @@ struct pci_sriov {
 	u16		driver_max_VFs;	/* Max num VFs driver supports */
 	struct pci_dev	*dev;		/* Lowest numbered PF */
 	struct pci_dev	*self;		/* This PF */
-	u32		cfg_size;	/* VF config space size */
 	u32		class;		/* VF device */
 	u8		hdr_type;	/* VF header type */
 	u16		subsystem_vendor; /* VF subsystem vendor */
diff --git a/drivers/pci/probe.c b/drivers/pci/probe.c
index c5f27c8cd140..5a0b07428425 100644
--- a/drivers/pci/probe.c
+++ b/drivers/pci/probe.c
@@ -1555,17 +1555,6 @@ static int pci_cfg_space_size_ext(struct pci_dev *dev)
 	return PCI_CFG_SPACE_EXP_SIZE;
 }
 
-#ifdef CONFIG_PCI_IOV
-static bool is_vf0(struct pci_dev *dev)
-{
-	if (pci_iov_virtfn_devfn(dev->physfn, 0) == dev->devfn &&
-	    pci_iov_virtfn_bus(dev->physfn, 0) == dev->bus->number)
-		return true;
-
-	return false;
-}
-#endif
-
 int pci_cfg_space_size(struct pci_dev *dev)
 {
 	int pos;
@@ -1573,9 +1562,18 @@ int pci_cfg_space_size(struct pci_dev *dev)
 	u16 class;
 
 #ifdef CONFIG_PCI_IOV
-	/* Read cached value for all VFs except for VF0 */
-	if (dev->is_virtfn && !is_vf0(dev))
-		return dev->physfn->sriov->cfg_size;
+	/*
+	 * Per the SR-IOV specification (rev 1.1, sec 3.5), VFs are required to
+	 * implement a PCIe capability and therefore must implement extended
+	 * config space.  We can skip the NO_EXTCFG test below and the
+	 * reachability/aliasing test in pci_cfg_space_size_ext() by virtue of
+	 * the fact that the SR-IOV capability on the PF resides in extended
+	 * config space and must be accessible and non-aliased to have enabled
+	 * support for this VF.  This is a micro performance optimization for
+	 * systems supporting many VFs.
+	 */
+	if (dev->is_virtfn)
+		return PCI_CFG_SPACE_EXP_SIZE;
 #endif
 
 	if (dev->bus->bus_flags & PCI_BUS_FLAGS_NO_EXTCFG)