Merge tag 'sched-urgent-2020-10-25' of git://git.kernel.org/pub/scm/linux/kernel...
[linux-2.6-microblaze.git] / drivers / pci / controller / dwc / pcie-tegra194.c
index 7049868..f920e7e 100644 (file)
 #define EVENT_COUNTER_GROUP_SEL_SHIFT  24
 #define EVENT_COUNTER_GROUP_5          0x5
 
-#define PORT_LOGIC_ACK_F_ASPM_CTRL                     0x70C
-#define ENTER_ASPM                                     BIT(30)
-#define L0S_ENTRANCE_LAT_SHIFT                         24
-#define L0S_ENTRANCE_LAT_MASK                          GENMASK(26, 24)
-#define L1_ENTRANCE_LAT_SHIFT                          27
-#define L1_ENTRANCE_LAT_MASK                           GENMASK(29, 27)
-#define N_FTS_SHIFT                                    8
-#define N_FTS_MASK                                     GENMASK(7, 0)
 #define N_FTS_VAL                                      52
-
-#define PORT_LOGIC_GEN2_CTRL                           0x80C
-#define PORT_LOGIC_GEN2_CTRL_DIRECT_SPEED_CHANGE       BIT(17)
-#define FTS_MASK                                       GENMASK(7, 0)
 #define FTS_VAL                                                52
 
 #define PORT_LOGIC_MSI_CTRL_INT_0_EN           0x828
@@ -296,7 +284,6 @@ struct tegra_pcie_dw {
        u8 init_link_width;
        u32 msi_ctrl_int;
        u32 num_lanes;
-       u32 max_speed;
        u32 cid;
        u32 cfg_link_cap_l1sub;
        u32 pcie_cap_base;
@@ -401,9 +388,9 @@ static irqreturn_t tegra_pcie_rp_irq_handler(int irq, void *arg)
                        val |= APPL_CAR_RESET_OVRD_CYA_OVERRIDE_CORE_RST_N;
                        appl_writel(pcie, val, APPL_CAR_RESET_OVRD);
 
-                       val = dw_pcie_readl_dbi(pci, PORT_LOGIC_GEN2_CTRL);
-                       val |= PORT_LOGIC_GEN2_CTRL_DIRECT_SPEED_CHANGE;
-                       dw_pcie_writel_dbi(pci, PORT_LOGIC_GEN2_CTRL, val);
+                       val = dw_pcie_readl_dbi(pci, PCIE_LINK_WIDTH_SPEED_CONTROL);
+                       val |= PORT_LOGIC_SPEED_CHANGE;
+                       dw_pcie_writel_dbi(pci, PCIE_LINK_WIDTH_SPEED_CONTROL, val);
                }
        }
 
@@ -568,42 +555,44 @@ static irqreturn_t tegra_pcie_ep_hard_irq(int irq, void *arg)
        return IRQ_HANDLED;
 }
 
-static int tegra_pcie_dw_rd_own_conf(struct pcie_port *pp, int where, int size,
-                                    u32 *val)
+static int tegra_pcie_dw_rd_own_conf(struct pci_bus *bus, u32 devfn, int where,
+                                    int size, u32 *val)
 {
-       struct dw_pcie *pci = to_dw_pcie_from_pp(pp);
-
        /*
         * This is an endpoint mode specific register happen to appear even
         * when controller is operating in root port mode and system hangs
         * when it is accessed with link being in ASPM-L1 state.
         * So skip accessing it altogether
         */
-       if (where == PORT_LOGIC_MSIX_DOORBELL) {
+       if (!PCI_SLOT(devfn) && where == PORT_LOGIC_MSIX_DOORBELL) {
                *val = 0x00000000;
                return PCIBIOS_SUCCESSFUL;
        }
 
-       return dw_pcie_read(pci->dbi_base + where, size, val);
+       return pci_generic_config_read(bus, devfn, where, size, val);
 }
 
-static int tegra_pcie_dw_wr_own_conf(struct pcie_port *pp, int where, int size,
-                                    u32 val)
+static int tegra_pcie_dw_wr_own_conf(struct pci_bus *bus, u32 devfn, int where,
+                                    int size, u32 val)
 {
-       struct dw_pcie *pci = to_dw_pcie_from_pp(pp);
-
        /*
         * This is an endpoint mode specific register happen to appear even
         * when controller is operating in root port mode and system hangs
         * when it is accessed with link being in ASPM-L1 state.
         * So skip accessing it altogether
         */
-       if (where == PORT_LOGIC_MSIX_DOORBELL)
+       if (!PCI_SLOT(devfn) && where == PORT_LOGIC_MSIX_DOORBELL)
                return PCIBIOS_SUCCESSFUL;
 
-       return dw_pcie_write(pci->dbi_base + where, size, val);
+       return pci_generic_config_write(bus, devfn, where, size, val);
 }
 
+static struct pci_ops tegra_pci_ops = {
+       .map_bus = dw_pcie_own_conf_map_bus,
+       .read = tegra_pcie_dw_rd_own_conf,
+       .write = tegra_pcie_dw_wr_own_conf,
+};
+
 #if defined(CONFIG_PCIEASPM)
 static void disable_aspm_l11(struct tegra_pcie_dw *pcie)
 {
@@ -692,30 +681,23 @@ static void init_host_aspm(struct tegra_pcie_dw *pcie)
        dw_pcie_writel_dbi(pci, pcie->cfg_link_cap_l1sub, val);
 
        /* Program L0s and L1 entrance latencies */
-       val = dw_pcie_readl_dbi(pci, PORT_LOGIC_ACK_F_ASPM_CTRL);
-       val &= ~L0S_ENTRANCE_LAT_MASK;
-       val |= (pcie->aspm_l0s_enter_lat << L0S_ENTRANCE_LAT_SHIFT);
-       val |= ENTER_ASPM;
-       dw_pcie_writel_dbi(pci, PORT_LOGIC_ACK_F_ASPM_CTRL, val);
+       val = dw_pcie_readl_dbi(pci, PCIE_PORT_AFR);
+       val &= ~PORT_AFR_L0S_ENTRANCE_LAT_MASK;
+       val |= (pcie->aspm_l0s_enter_lat << PORT_AFR_L0S_ENTRANCE_LAT_SHIFT);
+       val |= PORT_AFR_ENTER_ASPM;
+       dw_pcie_writel_dbi(pci, PCIE_PORT_AFR, val);
 }
 
-static int init_debugfs(struct tegra_pcie_dw *pcie)
+static void init_debugfs(struct tegra_pcie_dw *pcie)
 {
-       struct dentry *d;
-
-       d = debugfs_create_devm_seqfile(pcie->dev, "aspm_state_cnt",
-                                       pcie->debugfs, aspm_state_cnt);
-       if (IS_ERR_OR_NULL(d))
-               dev_err(pcie->dev,
-                       "Failed to create debugfs file \"aspm_state_cnt\"\n");
-
-       return 0;
+       debugfs_create_devm_seqfile(pcie->dev, "aspm_state_cnt", pcie->debugfs,
+                                   aspm_state_cnt);
 }
 #else
 static inline void disable_aspm_l12(struct tegra_pcie_dw *pcie) { return; }
 static inline void disable_aspm_l11(struct tegra_pcie_dw *pcie) { return; }
 static inline void init_host_aspm(struct tegra_pcie_dw *pcie) { return; }
-static inline int init_debugfs(struct tegra_pcie_dw *pcie) { return 0; }
+static inline void init_debugfs(struct tegra_pcie_dw *pcie) { return; }
 #endif
 
 static void tegra_pcie_enable_system_interrupts(struct pcie_port *pp)
@@ -827,26 +809,24 @@ static void config_gen3_gen4_eq_presets(struct tegra_pcie_dw *pcie)
 
        /* Program init preset */
        for (i = 0; i < pcie->num_lanes; i++) {
-               dw_pcie_read(pci->dbi_base + CAP_SPCIE_CAP_OFF
-                                + (i * 2), 2, &val);
+               val = dw_pcie_readw_dbi(pci, CAP_SPCIE_CAP_OFF + (i * 2));
                val &= ~CAP_SPCIE_CAP_OFF_DSP_TX_PRESET0_MASK;
                val |= GEN3_GEN4_EQ_PRESET_INIT;
                val &= ~CAP_SPCIE_CAP_OFF_USP_TX_PRESET0_MASK;
                val |= (GEN3_GEN4_EQ_PRESET_INIT <<
                           CAP_SPCIE_CAP_OFF_USP_TX_PRESET0_SHIFT);
-               dw_pcie_write(pci->dbi_base + CAP_SPCIE_CAP_OFF
-                                + (i * 2), 2, val);
+               dw_pcie_writew_dbi(pci, CAP_SPCIE_CAP_OFF + (i * 2), val);
 
                offset = dw_pcie_find_ext_capability(pci,
                                                     PCI_EXT_CAP_ID_PL_16GT) +
                                PCI_PL_16GT_LE_CTRL;
-               dw_pcie_read(pci->dbi_base + offset + i, 1, &val);
+               val = dw_pcie_readb_dbi(pci, offset + i);
                val &= ~PCI_PL_16GT_LE_CTRL_DSP_TX_PRESET_MASK;
                val |= GEN3_GEN4_EQ_PRESET_INIT;
                val &= ~PCI_PL_16GT_LE_CTRL_USP_TX_PRESET_MASK;
                val |= (GEN3_GEN4_EQ_PRESET_INIT <<
                        PCI_PL_16GT_LE_CTRL_USP_TX_PRESET_SHIFT);
-               dw_pcie_write(pci->dbi_base + offset + i, 1, val);
+               dw_pcie_writeb_dbi(pci, offset + i, val);
        }
 
        val = dw_pcie_readl_dbi(pci, GEN3_RELATED_OFF);
@@ -892,17 +872,6 @@ static void tegra_pcie_prepare_host(struct pcie_port *pp)
 
        dw_pcie_writel_dbi(pci, PCI_BASE_ADDRESS_0, 0);
 
-       /* Configure FTS */
-       val = dw_pcie_readl_dbi(pci, PORT_LOGIC_ACK_F_ASPM_CTRL);
-       val &= ~(N_FTS_MASK << N_FTS_SHIFT);
-       val |= N_FTS_VAL << N_FTS_SHIFT;
-       dw_pcie_writel_dbi(pci, PORT_LOGIC_ACK_F_ASPM_CTRL, val);
-
-       val = dw_pcie_readl_dbi(pci, PORT_LOGIC_GEN2_CTRL);
-       val &= ~FTS_MASK;
-       val |= FTS_VAL;
-       dw_pcie_writel_dbi(pci, PORT_LOGIC_GEN2_CTRL, val);
-
        /* Enable as 0xFFFF0001 response for CRS */
        val = dw_pcie_readl_dbi(pci, PORT_LOGIC_AMBA_ERROR_RESPONSE_DEFAULT);
        val &= ~(AMBA_ERROR_RESPONSE_CRS_MASK << AMBA_ERROR_RESPONSE_CRS_SHIFT);
@@ -910,16 +879,6 @@ static void tegra_pcie_prepare_host(struct pcie_port *pp)
                AMBA_ERROR_RESPONSE_CRS_SHIFT);
        dw_pcie_writel_dbi(pci, PORT_LOGIC_AMBA_ERROR_RESPONSE_DEFAULT, val);
 
-       /* Configure Max Speed from DT */
-       if (pcie->max_speed && pcie->max_speed != -EINVAL) {
-               val = dw_pcie_readl_dbi(pci, pcie->pcie_cap_base +
-                                       PCI_EXP_LNKCAP);
-               val &= ~PCI_EXP_LNKCAP_SLS;
-               val |= pcie->max_speed;
-               dw_pcie_writel_dbi(pci, pcie->pcie_cap_base + PCI_EXP_LNKCAP,
-                                  val);
-       }
-
        /* Configure Max lane width from DT */
        val = dw_pcie_readl_dbi(pci, pcie->pcie_cap_base + PCI_EXP_LNKCAP);
        val &= ~PCI_EXP_LNKCAP_MLW;
@@ -970,6 +929,8 @@ static int tegra_pcie_dw_host_init(struct pcie_port *pp)
        struct tegra_pcie_dw *pcie = to_tegra_pcie(pci);
        u32 val, tmp, offset, speed;
 
+       pp->bridge->ops = &tegra_pci_ops;
+
        tegra_pcie_prepare_host(pp);
 
        if (dw_pcie_wait_for_link(pci)) {
@@ -1057,8 +1018,6 @@ static const struct dw_pcie_ops tegra_dw_pcie_ops = {
 };
 
 static struct dw_pcie_host_ops tegra_pcie_dw_host_ops = {
-       .rd_own_conf = tegra_pcie_dw_rd_own_conf,
-       .wr_own_conf = tegra_pcie_dw_wr_own_conf,
        .host_init = tegra_pcie_dw_host_init,
        .set_num_vectors = tegra_pcie_set_msi_vec_num,
 };
@@ -1129,8 +1088,6 @@ static int tegra_pcie_dw_parse_dt(struct tegra_pcie_dw *pcie)
                return ret;
        }
 
-       pcie->max_speed = of_pci_get_max_link_speed(np);
-
        ret = of_property_read_u32_index(np, "nvidia,bpmp", 1, &pcie->cid);
        if (ret) {
                dev_err(pcie->dev, "Failed to read Controller-ID: %d\n", ret);
@@ -1262,9 +1219,9 @@ static void tegra_pcie_downstream_dev_to_D0(struct tegra_pcie_dw *pcie)
         * 5.2 Link State Power Management (Page #428).
         */
 
-       list_for_each_entry(child, &pp->root_bus->children, node) {
+       list_for_each_entry(child, &pp->bridge->bus->children, node) {
                /* Bring downstream devices to D0 if they are not already in */
-               if (child->parent == pp->root_bus) {
+               if (child->parent == pp->bridge->bus) {
                        root_bus = child;
                        break;
                }
@@ -1641,10 +1598,7 @@ static int tegra_pcie_config_rp(struct tegra_pcie_dw *pcie)
        }
 
        pcie->debugfs = debugfs_create_dir(name, NULL);
-       if (!pcie->debugfs)
-               dev_err(dev, "Failed to create debugfs\n");
-       else
-               init_debugfs(pcie);
+       init_debugfs(pcie);
 
        return ret;
 
@@ -1817,27 +1771,6 @@ static void pex_ep_event_pex_rst_deassert(struct tegra_pcie_dw *pcie)
        val &= ~GEN3_RELATED_OFF_GEN3_ZRXDC_NONCOMPL;
        dw_pcie_writel_dbi(pci, GEN3_RELATED_OFF, val);
 
-       /* Configure N_FTS & FTS */
-       val = dw_pcie_readl_dbi(pci, PORT_LOGIC_ACK_F_ASPM_CTRL);
-       val &= ~(N_FTS_MASK << N_FTS_SHIFT);
-       val |= N_FTS_VAL << N_FTS_SHIFT;
-       dw_pcie_writel_dbi(pci, PORT_LOGIC_ACK_F_ASPM_CTRL, val);
-
-       val = dw_pcie_readl_dbi(pci, PORT_LOGIC_GEN2_CTRL);
-       val &= ~FTS_MASK;
-       val |= FTS_VAL;
-       dw_pcie_writel_dbi(pci, PORT_LOGIC_GEN2_CTRL, val);
-
-       /* Configure Max Speed from DT */
-       if (pcie->max_speed && pcie->max_speed != -EINVAL) {
-               val = dw_pcie_readl_dbi(pci, pcie->pcie_cap_base +
-                                       PCI_EXP_LNKCAP);
-               val &= ~PCI_EXP_LNKCAP_SLS;
-               val |= pcie->max_speed;
-               dw_pcie_writel_dbi(pci, pcie->pcie_cap_base + PCI_EXP_LNKCAP,
-                                  val);
-       }
-
        pcie->pcie_cap_base = dw_pcie_find_capability(&pcie->pci,
                                                      PCI_CAP_ID_EXP);
        clk_set_rate(pcie->core_clk, GEN4_CORE_CLK_FREQ);
@@ -2066,6 +1999,9 @@ static int tegra_pcie_dw_probe(struct platform_device *pdev)
        pci = &pcie->pci;
        pci->dev = &pdev->dev;
        pci->ops = &tegra_dw_pcie_ops;
+       pci->n_fts[0] = N_FTS_VAL;
+       pci->n_fts[1] = FTS_VAL;
+
        pp = &pci->pp;
        pcie->dev = &pdev->dev;
        pcie->mode = (enum dw_pcie_device_mode)data->mode;