|
@@ -42,6 +42,9 @@
|
|
|
|
|
|
/* PCIe Port Logic registers (memory-mapped) */
|
|
|
#define PL_OFFSET 0x700
|
|
|
+#define PCIE_PL_PFLR (PL_OFFSET + 0x08)
|
|
|
+#define PCIE_PL_PFLR_LINK_STATE_MASK (0x3f << 16)
|
|
|
+#define PCIE_PL_PFLR_FORCE_LINK (1 << 15)
|
|
|
#define PCIE_PHY_DEBUG_R0 (PL_OFFSET + 0x28)
|
|
|
#define PCIE_PHY_DEBUG_R1 (PL_OFFSET + 0x2c)
|
|
|
#define PCIE_PHY_DEBUG_R1_LINK_UP (1 << 4)
|
|
@@ -445,6 +448,36 @@ static int imx6_pcie_assert_core_reset(void)
|
|
|
/* Power up PCIe PHY */
|
|
|
setbits_le32(&gpc_regs->cntr, PCIE_PHY_PUP_REQ);
|
|
|
#else
|
|
|
+ /*
|
|
|
+ * If the bootloader already enabled the link we need some special
|
|
|
+ * handling to get the core back into a state where it is safe to
|
|
|
+ * touch it for configuration. As there is no dedicated reset signal
|
|
|
+ * wired up for MX6QDL, we need to manually force LTSSM into "detect"
|
|
|
+ * state before completely disabling LTSSM, which is a prerequisite
|
|
|
+ * for core configuration.
|
|
|
+ *
|
|
|
+ * If both LTSSM_ENABLE and REF_SSP_ENABLE are active we have a strong
|
|
|
+ * indication that the bootloader activated the link.
|
|
|
+ */
|
|
|
+ if (is_mx6dq()) {
|
|
|
+ u32 val, gpr1, gpr12;
|
|
|
+
|
|
|
+ gpr1 = readl(&iomuxc_regs->gpr[1]);
|
|
|
+ gpr12 = readl(&iomuxc_regs->gpr[12]);
|
|
|
+ if ((gpr1 & IOMUXC_GPR1_PCIE_REF_CLK_EN) &&
|
|
|
+ (gpr12 & IOMUXC_GPR12_PCIE_CTL_2)) {
|
|
|
+ val = readl(MX6_DBI_ADDR + PCIE_PL_PFLR);
|
|
|
+ val &= ~PCIE_PL_PFLR_LINK_STATE_MASK;
|
|
|
+ val |= PCIE_PL_PFLR_FORCE_LINK;
|
|
|
+
|
|
|
+ imx_pcie_fix_dabt_handler(true);
|
|
|
+ writel(val, MX6_DBI_ADDR + PCIE_PL_PFLR);
|
|
|
+ imx_pcie_fix_dabt_handler(false);
|
|
|
+
|
|
|
+ gpr12 &= ~IOMUXC_GPR12_PCIE_CTL_2;
|
|
|
+ writel(val, &iomuxc_regs->gpr[12]);
|
|
|
+ }
|
|
|
+ }
|
|
|
setbits_le32(&iomuxc_regs->gpr[1], IOMUXC_GPR1_TEST_POWERDOWN);
|
|
|
clrbits_le32(&iomuxc_regs->gpr[1], IOMUXC_GPR1_REF_SSP_EN);
|
|
|
#endif
|
|
@@ -652,6 +685,11 @@ void imx_pcie_init(void)
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+void imx_pcie_remove(void)
|
|
|
+{
|
|
|
+ imx6_pcie_assert_core_reset();
|
|
|
+}
|
|
|
+
|
|
|
/* Probe function. */
|
|
|
void pci_init_board(void)
|
|
|
{
|