changeset 3743:bfe4e988bf7e

6521915 EFCode interpreter can not access extended config space on PCIe devices
author aa72041
date Thu, 01 Mar 2007 08:15:27 -0800
parents 304a05354bf8
children fb3f21cb6650
files usr/src/uts/common/sys/pci.h usr/src/uts/sun4/io/efcode/fcpci.c
diffstat 2 files changed, 19 insertions(+), 12 deletions(-) [+]
line wrap: on
line diff
--- a/usr/src/uts/common/sys/pci.h	Thu Mar 01 06:49:29 2007 -0800
+++ b/usr/src/uts/common/sys/pci.h	Thu Mar 01 08:15:27 2007 -0800
@@ -970,11 +970,13 @@
 #define	PCI_REG_PF_M		0x40000000	/* prefetch bit mask */
 #define	PCI_REG_REL_M		0x80000000	/* relocation bit mask */
 #define	PCI_REG_BDFR_M		0xffffff	/* bus, dev, func, reg mask */
+#define	PCI_REG_EXTREG_M	0xF0000000	/* extended config bits mask */
 
 #define	PCI_REG_FUNC_SHIFT	8		/* Offset of function bits */
 #define	PCI_REG_DEV_SHIFT	11		/* Offset of device bits */
 #define	PCI_REG_BUS_SHIFT	16		/* Offset of bus bits */
 #define	PCI_REG_ADDR_SHIFT	24		/* Offset of address bits */
+#define	PCI_REG_EXTREG_SHIFT	28		/* Offset of ext. config bits */
 
 #define	PCI_REG_REG_G(x)	((x) & PCI_REG_REG_M)
 #define	PCI_REG_FUNC_G(x)	(((x) & PCI_REG_FUNC_M) >> PCI_REG_FUNC_SHIFT)
--- a/usr/src/uts/sun4/io/efcode/fcpci.c	Thu Mar 01 06:49:29 2007 -0800
+++ b/usr/src/uts/sun4/io/efcode/fcpci.c	Thu Mar 01 08:15:27 2007 -0800
@@ -20,7 +20,7 @@
  */
 
 /*
- * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2007 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
@@ -45,7 +45,9 @@
 #include <sys/promimpl.h>
 #include <sys/ddi_implfuncs.h>
 
-#define	PCI_NPT_bits	(PCI_RELOCAT_B | PCI_PREFETCH_B | PCI_ALIAS_B)
+#define	PCI_NPT_bits		(PCI_RELOCAT_B | PCI_PREFETCH_B | PCI_ALIAS_B)
+#define	PCI_BDF_bits		(PCI_REG_BDFR_M & ~PCI_REG_REG_M)
+
 #define	PCICFG_CONF_INDIRECT_MAP	1
 
 static int pfc_map_in(dev_info_t *, fco_handle_t, fc_ci_t *);
@@ -856,10 +858,9 @@
 
 	/*
 	 * Verify that the address is a configuration space address
-	 * ss must be zero, n,p,t must be zero.
+	 * ss must be zero.
 	 */
-	if (((p.pci_phys_hi & PCI_ADDR_MASK) != PCI_ADDR_CONFIG) ||
-	    ((p.pci_phys_hi & PCI_NPT_bits) != 0)) {
+	if ((p.pci_phys_hi & PCI_ADDR_MASK) != PCI_ADDR_CONFIG) {
 		cmn_err(CE_CONT, "pfc_config_fetch: "
 		    "invalid config addr: %x\n", p.pci_phys_hi);
 		return (fc_priv_error(cp, "non-config addr"));
@@ -869,8 +870,11 @@
 	 * Extract the register number from the config address and
 	 * remove the register number from the physical address.
 	 */
-	reg = p.pci_phys_hi & PCI_REG_REG_M;
-	p.pci_phys_hi &= ~PCI_REG_REG_M;
+
+	reg = (p.pci_phys_hi & PCI_REG_REG_M) |
+	    (((p.pci_phys_hi & PCI_REG_EXTREG_M) >> PCI_REG_EXTREG_SHIFT) << 8);
+
+	p.pci_phys_hi &= PCI_BDF_bits;
 
 	/*
 	 * Determine the access width .. we can switch on the 9th
@@ -986,10 +990,9 @@
 
 	/*
 	 * Verify that the address is a configuration space address
-	 * ss must be zero, n,p,t must be zero.
+	 * ss must be zero.
 	 */
-	if (((p.pci_phys_hi & PCI_ADDR_MASK) != PCI_ADDR_CONFIG) ||
-	    ((p.pci_phys_hi & PCI_NPT_bits) != 0)) {
+	if ((p.pci_phys_hi & PCI_ADDR_MASK) != PCI_ADDR_CONFIG) {
 		cmn_err(CE_CONT, "pfc_config_store: "
 		    "invalid config addr: %x\n", p.pci_phys_hi);
 		return (fc_priv_error(cp, "non-config addr"));
@@ -999,8 +1002,10 @@
 	 * Extract the register number from the config address and
 	 * remove the register number from the physical address.
 	 */
-	reg = p.pci_phys_hi & PCI_REG_REG_M;
-	p.pci_phys_hi &= ~PCI_REG_REG_M;
+	reg = (p.pci_phys_hi & PCI_REG_REG_M) |
+	    (((p.pci_phys_hi & PCI_REG_EXTREG_M) >> PCI_REG_EXTREG_SHIFT) << 8);
+
+	p.pci_phys_hi &= PCI_BDF_bits;
 
 	/*
 	 * Determine the access width .. we can switch on the 8th