summaryrefslogtreecommitdiff
path: root/drivers/pci/fsl_pci_init.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/pci/fsl_pci_init.c')
-rw-r--r--drivers/pci/fsl_pci_init.c39
1 files changed, 34 insertions, 5 deletions
diff --git a/drivers/pci/fsl_pci_init.c b/drivers/pci/fsl_pci_init.c
index 1db42fd8d..20b2dcc76 100644
--- a/drivers/pci/fsl_pci_init.c
+++ b/drivers/pci/fsl_pci_init.c
@@ -37,6 +37,11 @@ DECLARE_GLOBAL_DATA_PTR;
#include <pci.h>
#include <asm/immap_fsl_pci.h>
+/* Freescale-specific PCI config registers */
+#define FSL_PCI_PBFR 0x44
+#define FSL_PCIE_CAP_ID 0x4c
+#define FSL_PCIE_CFG_RDY 0x4b0
+
void pciauto_prescan_setup_bridge(struct pci_controller *hose,
pci_dev_t dev, int sub_bus);
void pciauto_postscan_setup_bridge(struct pci_controller *hose,
@@ -67,7 +72,7 @@ int fsl_pci_setup_inbound_windows(struct pci_region *r)
debug ("R0 bus_start: %llx phys_start: %llx size: %llx\n",
(u64)bus_start, (u64)phys_start, (u64)pci_sz);
pci_set_region(r++, bus_start, phys_start, pci_sz,
- PCI_REGION_MEM | PCI_REGION_MEMORY |
+ PCI_REGION_MEM | PCI_REGION_SYS_MEMORY |
PCI_REGION_PREFETCH);
sz -= pci_sz;
@@ -79,7 +84,7 @@ int fsl_pci_setup_inbound_windows(struct pci_region *r)
debug ("R1 bus_start: %llx phys_start: %llx size: %llx\n",
(u64)bus_start, (u64)phys_start, (u64)pci_sz);
pci_set_region(r++, bus_start, phys_start, pci_sz,
- PCI_REGION_MEM | PCI_REGION_MEMORY |
+ PCI_REGION_MEM | PCI_REGION_SYS_MEMORY |
PCI_REGION_PREFETCH);
sz -= pci_sz;
bus_start += pci_sz;
@@ -103,7 +108,7 @@ int fsl_pci_setup_inbound_windows(struct pci_region *r)
CONFIG_SYS_PCI64_MEMORY_BUS,
CONFIG_SYS_PCI_MEMORY_PHYS,
pci_sz,
- PCI_REGION_MEM | PCI_REGION_MEMORY |
+ PCI_REGION_MEM | PCI_REGION_SYS_MEMORY |
PCI_REGION_PREFETCH);
#else
pci_sz = 1ull << __ilog2_u64(sz);
@@ -111,7 +116,7 @@ int fsl_pci_setup_inbound_windows(struct pci_region *r)
debug ("R2 bus_start: %llx phys_start: %llx size: %llx\n",
(u64)bus_start, (u64)phys_start, (u64)pci_sz);
pci_set_region(r++, bus_start, phys_start, pci_sz,
- PCI_REGION_MEM | PCI_REGION_MEMORY |
+ PCI_REGION_MEM | PCI_REGION_SYS_MEMORY |
PCI_REGION_PREFETCH);
sz -= pci_sz;
bus_start += pci_sz;
@@ -152,7 +157,7 @@ void fsl_pci_init(struct pci_controller *hose)
for (r=0; r<hose->region_count; r++) {
u32 sz = (__ilog2_u64((u64)hose->regions[r].size) - 1);
- if (hose->regions[r].flags & PCI_REGION_MEMORY) { /* inbound */
+ if (hose->regions[r].flags & PCI_REGION_SYS_MEMORY) { /* inbound */
u32 flag = PIWAR_EN | PIWAR_LOCAL |
PIWAR_READ_SNOOP | PIWAR_WRITE_SNOOP;
pi->pitar = (hose->regions[r].phys_start >> 12);
@@ -306,6 +311,30 @@ void fsl_pci_init(struct pci_controller *hose)
}
}
+/* Enable inbound PCI config cycles for agent/endpoint interface */
+void fsl_pci_config_unlock(struct pci_controller *hose)
+{
+ pci_dev_t dev = PCI_BDF(hose->first_busno,0,0);
+ u8 agent;
+ u8 pcie_cap;
+ u16 pbfr;
+
+ pci_hose_read_config_byte(hose, dev, PCI_CLASS_PROG, &agent);
+ if (!agent)
+ return;
+
+ pci_hose_read_config_byte(hose, dev, FSL_PCIE_CAP_ID, &pcie_cap);
+ if (pcie_cap != 0x0) {
+ /* PCIe - set CFG_READY bit of Configuration Ready Register */
+ pci_hose_write_config_byte(hose, dev, FSL_PCIE_CFG_RDY, 0x1);
+ } else {
+ /* PCI - clear ACL bit of PBFR */
+ pci_hose_read_config_word(hose, dev, FSL_PCI_PBFR, &pbfr);
+ pbfr &= ~0x20;
+ pci_hose_write_config_word(hose, dev, FSL_PCI_PBFR, pbfr);
+ }
+}
+
#ifdef CONFIG_OF_BOARD_SETUP
#include <libfdt.h>
#include <fdt_support.h>