PCI/P2PDMA: Factor out __upstream_bridge_distance()
This is a prep patch to create a second level helper. There are no functional changes. The root complex whitelist code will be moved into this function in a subsequent patch. Link: https://lore.kernel.org/r/20190730163545.4915-5-logang@deltatee.com Link: https://lore.kernel.org/r/20190812173048.9186-5-logang@deltatee.com Signed-off-by: Logan Gunthorpe <logang@deltatee.com> Signed-off-by: Bjorn Helgaas <bhelgaas@google.com> Reviewed-by: Christian König <christian.koenig@amd.com> Reviewed-by: Christoph Hellwig <hch@lst.de>
This commit is contained in:
parent
72583084e3
commit
c6bfaeb573
|
@ -296,47 +296,8 @@ static bool root_complex_whitelist(struct pci_dev *dev)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Find the distance through the nearest common upstream bridge between
|
|
||||||
* two PCI devices.
|
|
||||||
*
|
|
||||||
* If the two devices are the same device then 0 will be returned.
|
|
||||||
*
|
|
||||||
* If there are two virtual functions of the same device behind the same
|
|
||||||
* bridge port then 2 will be returned (one step down to the PCIe switch,
|
|
||||||
* then one step back to the same device).
|
|
||||||
*
|
|
||||||
* In the case where two devices are connected to the same PCIe switch, the
|
|
||||||
* value 4 will be returned. This corresponds to the following PCI tree:
|
|
||||||
*
|
|
||||||
* -+ Root Port
|
|
||||||
* \+ Switch Upstream Port
|
|
||||||
* +-+ Switch Downstream Port
|
|
||||||
* + \- Device A
|
|
||||||
* \-+ Switch Downstream Port
|
|
||||||
* \- Device B
|
|
||||||
*
|
|
||||||
* The distance is 4 because we traverse from Device A through the downstream
|
|
||||||
* port of the switch, to the common upstream port, back up to the second
|
|
||||||
* downstream port and then to Device B.
|
|
||||||
*
|
|
||||||
* Any two devices that cannot communicate using p2pdma will return
|
|
||||||
* PCI_P2PDMA_MAP_NOT_SUPPORTED.
|
|
||||||
*
|
|
||||||
* Any two devices that have a data path that goes through the host bridge
|
|
||||||
* will consult a whitelist. If the host bridges are on the whitelist,
|
|
||||||
* this function will return PCI_P2PDMA_MAP_THRU_HOST_BRIDGE.
|
|
||||||
*
|
|
||||||
* If either bridge is not on the whitelist this function returns
|
|
||||||
* PCI_P2PDMA_MAP_NOT_SUPPORTED.
|
|
||||||
*
|
|
||||||
* If a bridge which has any ACS redirection bits set is in the path,
|
|
||||||
* acs_redirects will be set to true. In this case, a list of all infringing
|
|
||||||
* bridge addresses will be populated in acs_list (assuming it's non-null)
|
|
||||||
* for printk purposes.
|
|
||||||
*/
|
|
||||||
static enum pci_p2pdma_map_type
|
static enum pci_p2pdma_map_type
|
||||||
upstream_bridge_distance(struct pci_dev *provider, struct pci_dev *client,
|
__upstream_bridge_distance(struct pci_dev *provider, struct pci_dev *client,
|
||||||
int *dist, bool *acs_redirects, struct seq_buf *acs_list)
|
int *dist, bool *acs_redirects, struct seq_buf *acs_list)
|
||||||
{
|
{
|
||||||
struct pci_dev *a = provider, *b = client, *bb;
|
struct pci_dev *a = provider, *b = client, *bb;
|
||||||
|
@ -416,6 +377,53 @@ check_b_path_acs:
|
||||||
return PCI_P2PDMA_MAP_BUS_ADDR;
|
return PCI_P2PDMA_MAP_BUS_ADDR;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Find the distance through the nearest common upstream bridge between
|
||||||
|
* two PCI devices.
|
||||||
|
*
|
||||||
|
* If the two devices are the same device then 0 will be returned.
|
||||||
|
*
|
||||||
|
* If there are two virtual functions of the same device behind the same
|
||||||
|
* bridge port then 2 will be returned (one step down to the PCIe switch,
|
||||||
|
* then one step back to the same device).
|
||||||
|
*
|
||||||
|
* In the case where two devices are connected to the same PCIe switch, the
|
||||||
|
* value 4 will be returned. This corresponds to the following PCI tree:
|
||||||
|
*
|
||||||
|
* -+ Root Port
|
||||||
|
* \+ Switch Upstream Port
|
||||||
|
* +-+ Switch Downstream Port
|
||||||
|
* + \- Device A
|
||||||
|
* \-+ Switch Downstream Port
|
||||||
|
* \- Device B
|
||||||
|
*
|
||||||
|
* The distance is 4 because we traverse from Device A through the downstream
|
||||||
|
* port of the switch, to the common upstream port, back up to the second
|
||||||
|
* downstream port and then to Device B.
|
||||||
|
*
|
||||||
|
* Any two devices that cannot communicate using p2pdma will return
|
||||||
|
* PCI_P2PDMA_MAP_NOT_SUPPORTED.
|
||||||
|
*
|
||||||
|
* Any two devices that have a data path that goes through the host bridge
|
||||||
|
* will consult a whitelist. If the host bridges are on the whitelist,
|
||||||
|
* this function will return PCI_P2PDMA_MAP_THRU_HOST_BRIDGE.
|
||||||
|
*
|
||||||
|
* If either bridge is not on the whitelist this function returns
|
||||||
|
* PCI_P2PDMA_MAP_NOT_SUPPORTED.
|
||||||
|
*
|
||||||
|
* If a bridge which has any ACS redirection bits set is in the path,
|
||||||
|
* acs_redirects will be set to true. In this case, a list of all infringing
|
||||||
|
* bridge addresses will be populated in acs_list (assuming it's non-null)
|
||||||
|
* for printk purposes.
|
||||||
|
*/
|
||||||
|
static enum pci_p2pdma_map_type
|
||||||
|
upstream_bridge_distance(struct pci_dev *provider, struct pci_dev *client,
|
||||||
|
int *dist, bool *acs_redirects, struct seq_buf *acs_list)
|
||||||
|
{
|
||||||
|
return __upstream_bridge_distance(provider, client, dist,
|
||||||
|
acs_redirects, acs_list);
|
||||||
|
}
|
||||||
|
|
||||||
static enum pci_p2pdma_map_type
|
static enum pci_p2pdma_map_type
|
||||||
upstream_bridge_distance_warn(struct pci_dev *provider, struct pci_dev *client,
|
upstream_bridge_distance_warn(struct pci_dev *provider, struct pci_dev *client,
|
||||||
int *dist)
|
int *dist)
|
||||||
|
|
Loading…
Reference in New Issue