84 lines
		
	
	
		
			2.6 KiB
		
	
	
	
		
			Diff
		
	
	
	
	
	
			
		
		
	
	
			84 lines
		
	
	
		
			2.6 KiB
		
	
	
	
		
			Diff
		
	
	
	
	
	
From 46560388c476c8471fde7712c10f9fad8d0d1875 Mon Sep 17 00:00:00 2001
 | 
						|
From: Ray Jui <rjui@broadcom.com>
 | 
						|
Date: Wed, 27 Jan 2016 16:52:24 -0600
 | 
						|
Subject: [PATCH] PCI: iproc: Allow multiple devices except on PAXC
 | 
						|
 | 
						|
Commit 943ebae781f5 ("PCI: iproc: Add PAXC interface support") only allowed
 | 
						|
device 0, which is a regression on BCMA-based platforms.
 | 
						|
 | 
						|
All systems support only one device, a Root Port at 00:00.0, on the root
 | 
						|
bus.  PAXC-based systems support only the Root Port (00:00.0) and a single
 | 
						|
device (with multiple functions) below it, e.g., 01:00.0, 01:00.1, etc.
 | 
						|
Non-PAXC systems support arbitrary devices below the Root Port.
 | 
						|
 | 
						|
[bhelgaas: changelog, fold in removal of MAX_NUM_PAXC_PF check]
 | 
						|
Fixes: 943ebae781f5 ("PCI: iproc: Add PAXC interface support")
 | 
						|
Reported-by: Rafal Milecki <zajec5@gmail.com>
 | 
						|
Signed-off-by: Ray Jui <rjui@broadcom.com>
 | 
						|
Signed-off-by: Bjorn Helgaas <bhelgaas@google.com>
 | 
						|
---
 | 
						|
 drivers/pci/host/pcie-iproc.c | 29 +++++++++++------------------
 | 
						|
 1 file changed, 11 insertions(+), 18 deletions(-)
 | 
						|
 | 
						|
--- a/drivers/pci/host/pcie-iproc.c
 | 
						|
+++ b/drivers/pci/host/pcie-iproc.c
 | 
						|
@@ -64,7 +64,6 @@
 | 
						|
 #define OARR_SIZE_CFG                BIT(OARR_SIZE_CFG_SHIFT)
 | 
						|
 
 | 
						|
 #define MAX_NUM_OB_WINDOWS           2
 | 
						|
-#define MAX_NUM_PAXC_PF              4
 | 
						|
 
 | 
						|
 #define IPROC_PCIE_REG_INVALID 0xffff
 | 
						|
 
 | 
						|
@@ -170,20 +169,6 @@ static inline void iproc_pcie_ob_write(s
 | 
						|
 	writel(val, pcie->base + offset + (window * 8));
 | 
						|
 }
 | 
						|
 
 | 
						|
-static inline bool iproc_pcie_device_is_valid(struct iproc_pcie *pcie,
 | 
						|
-					      unsigned int slot,
 | 
						|
-					      unsigned int fn)
 | 
						|
-{
 | 
						|
-	if (slot > 0)
 | 
						|
-		return false;
 | 
						|
-
 | 
						|
-	/* PAXC can only support limited number of functions */
 | 
						|
-	if (pcie->type == IPROC_PCIE_PAXC && fn >= MAX_NUM_PAXC_PF)
 | 
						|
-		return false;
 | 
						|
-
 | 
						|
-	return true;
 | 
						|
-}
 | 
						|
-
 | 
						|
 /**
 | 
						|
  * Note access to the configuration registers are protected at the higher layer
 | 
						|
  * by 'pci_lock' in drivers/pci/access.c
 | 
						|
@@ -199,11 +184,11 @@ static void __iomem *iproc_pcie_map_cfg_
 | 
						|
 	u32 val;
 | 
						|
 	u16 offset;
 | 
						|
 
 | 
						|
-	if (!iproc_pcie_device_is_valid(pcie, slot, fn))
 | 
						|
-		return NULL;
 | 
						|
-
 | 
						|
 	/* root complex access */
 | 
						|
 	if (busno == 0) {
 | 
						|
+		if (slot > 0 || fn > 0)
 | 
						|
+			return NULL;
 | 
						|
+
 | 
						|
 		iproc_pcie_write_reg(pcie, IPROC_PCIE_CFG_IND_ADDR,
 | 
						|
 				     where & CFG_IND_ADDR_MASK);
 | 
						|
 		offset = iproc_pcie_reg_offset(pcie, IPROC_PCIE_CFG_IND_DATA);
 | 
						|
@@ -213,6 +198,14 @@ static void __iomem *iproc_pcie_map_cfg_
 | 
						|
 			return (pcie->base + offset);
 | 
						|
 	}
 | 
						|
 
 | 
						|
+	/*
 | 
						|
+	 * PAXC is connected to an internally emulated EP within the SoC.  It
 | 
						|
+	 * allows only one device.
 | 
						|
+	 */
 | 
						|
+	if (pcie->type == IPROC_PCIE_PAXC)
 | 
						|
+		if (slot > 0)
 | 
						|
+			return NULL;
 | 
						|
+
 | 
						|
 	/* EP device access */
 | 
						|
 	val = (busno << CFG_ADDR_BUS_NUM_SHIFT) |
 | 
						|
 		(slot << CFG_ADDR_DEV_NUM_SHIFT) |
 |