mirror of
https://github.com/torvalds/linux.git
synced 2025-12-07 20:06:24 +00:00
Merge tag 'pci-v6.18-fixes-3' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci
Pull pci fixes from Bjorn Helgaas: - Add DWC custom pci_ops for the root bus instead of overwriting the DBI base address, which broke drivers that rely on the DBI address for iATU programming; fixes an FU740 probe regression (Krishna Chaitanya Chundru) - Revert qcom ECAM enablement, which is rendered unnecessary by the DWC custom pci_ops (Krishna Chaitanya Chundru) - Fix longstanding MIPS Malta resource registration issues to avoid exposing them when the next commit fixes the boot failure (Maciej W. Rozycki) - Use pcibios_align_resource() on MIPS Malta to fix boot failure caused by using the generic pci_enable_resources() (Ilpo Järvinen) - Enable only ASPM L0s and L1, not L1 PM Substates, for devicetree platforms because we lack information required to configure L1 Substates; fixes regressions on powerpc and rockchip. A qcom regression (L1 Substates no longer enabled) remains and will be addressed next (Bjorn Helgaas) * tag 'pci-v6.18-fixes-3' of git://git.kernel.org/pub/scm/linux/kernel/git/pci/pci: PCI/ASPM: Enable only L0s and L1 for devicetree platforms MIPS: Malta: Use pcibios_align_resource() to block io range MIPS: Malta: Fix PCI southbridge legacy resource reservations MIPS: Malta: Fix keyboard resource preventing i8042 driver from registering Revert "PCI: qcom: Prepare for the DWC ECAM enablement" PCI: dwc: Use custom pci_ops for root bus DBI vs ECAM config access
This commit is contained in:
@@ -47,7 +47,7 @@ static struct resource standard_io_resources[] = {
|
||||
.name = "keyboard",
|
||||
.start = 0x60,
|
||||
.end = 0x6f,
|
||||
.flags = IORESOURCE_IO | IORESOURCE_BUSY
|
||||
.flags = IORESOURCE_IO
|
||||
},
|
||||
{
|
||||
.name = "dma page reg",
|
||||
@@ -213,7 +213,7 @@ void __init plat_mem_setup(void)
|
||||
|
||||
/* Request I/O space for devices used on the Malta board. */
|
||||
for (i = 0; i < ARRAY_SIZE(standard_io_resources); i++)
|
||||
request_resource(&ioport_resource, standard_io_resources+i);
|
||||
insert_resource(&ioport_resource, standard_io_resources + i);
|
||||
|
||||
/*
|
||||
* Enable DMA channel 4 (cascade channel) in the PIIX4 south bridge.
|
||||
|
||||
@@ -230,8 +230,7 @@ void __init mips_pcibios_init(void)
|
||||
}
|
||||
|
||||
/* PIIX4 ACPI starts at 0x1000 */
|
||||
if (controller->io_resource->start < 0x00001000UL)
|
||||
controller->io_resource->start = 0x00001000UL;
|
||||
PCIBIOS_MIN_IO = 0x1000;
|
||||
|
||||
iomem_resource.end &= 0xfffffffffULL; /* 64 GB */
|
||||
ioport_resource.end = controller->io_resource->end;
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
#include "pcie-designware.h"
|
||||
|
||||
static struct pci_ops dw_pcie_ops;
|
||||
static struct pci_ops dw_pcie_ecam_ops;
|
||||
static struct pci_ops dw_child_pcie_ops;
|
||||
|
||||
#define DW_PCIE_MSI_FLAGS_REQUIRED (MSI_FLAG_USE_DEF_DOM_OPS | \
|
||||
@@ -471,9 +472,6 @@ static int dw_pcie_create_ecam_window(struct dw_pcie_rp *pp, struct resource *re
|
||||
if (IS_ERR(pp->cfg))
|
||||
return PTR_ERR(pp->cfg);
|
||||
|
||||
pci->dbi_base = pp->cfg->win;
|
||||
pci->dbi_phys_addr = res->start;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@@ -529,7 +527,7 @@ static int dw_pcie_host_get_resources(struct dw_pcie_rp *pp)
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
pp->bridge->ops = (struct pci_ops *)&pci_generic_ecam_ops.pci_ops;
|
||||
pp->bridge->ops = &dw_pcie_ecam_ops;
|
||||
pp->bridge->sysdata = pp->cfg;
|
||||
pp->cfg->priv = pp;
|
||||
} else {
|
||||
@@ -842,12 +840,34 @@ void __iomem *dw_pcie_own_conf_map_bus(struct pci_bus *bus, unsigned int devfn,
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(dw_pcie_own_conf_map_bus);
|
||||
|
||||
static void __iomem *dw_pcie_ecam_conf_map_bus(struct pci_bus *bus, unsigned int devfn, int where)
|
||||
{
|
||||
struct pci_config_window *cfg = bus->sysdata;
|
||||
struct dw_pcie_rp *pp = cfg->priv;
|
||||
struct dw_pcie *pci = to_dw_pcie_from_pp(pp);
|
||||
unsigned int busn = bus->number;
|
||||
|
||||
if (busn > 0)
|
||||
return pci_ecam_map_bus(bus, devfn, where);
|
||||
|
||||
if (PCI_SLOT(devfn) > 0)
|
||||
return NULL;
|
||||
|
||||
return pci->dbi_base + where;
|
||||
}
|
||||
|
||||
static struct pci_ops dw_pcie_ops = {
|
||||
.map_bus = dw_pcie_own_conf_map_bus,
|
||||
.read = pci_generic_config_read,
|
||||
.write = pci_generic_config_write,
|
||||
};
|
||||
|
||||
static struct pci_ops dw_pcie_ecam_ops = {
|
||||
.map_bus = dw_pcie_ecam_conf_map_bus,
|
||||
.read = pci_generic_config_read,
|
||||
.write = pci_generic_config_write,
|
||||
};
|
||||
|
||||
static int dw_pcie_iatu_setup(struct dw_pcie_rp *pp)
|
||||
{
|
||||
struct dw_pcie *pci = to_dw_pcie_from_pp(pp);
|
||||
|
||||
@@ -55,7 +55,6 @@
|
||||
#define PARF_AXI_MSTR_WR_ADDR_HALT_V2 0x1a8
|
||||
#define PARF_Q2A_FLUSH 0x1ac
|
||||
#define PARF_LTSSM 0x1b0
|
||||
#define PARF_SLV_DBI_ELBI 0x1b4
|
||||
#define PARF_INT_ALL_STATUS 0x224
|
||||
#define PARF_INT_ALL_CLEAR 0x228
|
||||
#define PARF_INT_ALL_MASK 0x22c
|
||||
@@ -65,16 +64,6 @@
|
||||
#define PARF_DBI_BASE_ADDR_V2_HI 0x354
|
||||
#define PARF_SLV_ADDR_SPACE_SIZE_V2 0x358
|
||||
#define PARF_SLV_ADDR_SPACE_SIZE_V2_HI 0x35c
|
||||
#define PARF_BLOCK_SLV_AXI_WR_BASE 0x360
|
||||
#define PARF_BLOCK_SLV_AXI_WR_BASE_HI 0x364
|
||||
#define PARF_BLOCK_SLV_AXI_WR_LIMIT 0x368
|
||||
#define PARF_BLOCK_SLV_AXI_WR_LIMIT_HI 0x36c
|
||||
#define PARF_BLOCK_SLV_AXI_RD_BASE 0x370
|
||||
#define PARF_BLOCK_SLV_AXI_RD_BASE_HI 0x374
|
||||
#define PARF_BLOCK_SLV_AXI_RD_LIMIT 0x378
|
||||
#define PARF_BLOCK_SLV_AXI_RD_LIMIT_HI 0x37c
|
||||
#define PARF_ECAM_BASE 0x380
|
||||
#define PARF_ECAM_BASE_HI 0x384
|
||||
#define PARF_NO_SNOOP_OVERRIDE 0x3d4
|
||||
#define PARF_ATU_BASE_ADDR 0x634
|
||||
#define PARF_ATU_BASE_ADDR_HI 0x638
|
||||
@@ -98,7 +87,6 @@
|
||||
|
||||
/* PARF_SYS_CTRL register fields */
|
||||
#define MAC_PHY_POWERDOWN_IN_P2_D_MUX_EN BIT(29)
|
||||
#define PCIE_ECAM_BLOCKER_EN BIT(26)
|
||||
#define MST_WAKEUP_EN BIT(13)
|
||||
#define SLV_WAKEUP_EN BIT(12)
|
||||
#define MSTR_ACLK_CGC_DIS BIT(10)
|
||||
@@ -146,9 +134,6 @@
|
||||
/* PARF_LTSSM register fields */
|
||||
#define LTSSM_EN BIT(8)
|
||||
|
||||
/* PARF_SLV_DBI_ELBI */
|
||||
#define SLV_DBI_ELBI_ADDR_BASE GENMASK(11, 0)
|
||||
|
||||
/* PARF_INT_ALL_{STATUS/CLEAR/MASK} register fields */
|
||||
#define PARF_INT_ALL_LINK_UP BIT(13)
|
||||
#define PARF_INT_MSI_DEV_0_7 GENMASK(30, 23)
|
||||
@@ -326,47 +311,6 @@ static void qcom_ep_reset_deassert(struct qcom_pcie *pcie)
|
||||
qcom_perst_assert(pcie, false);
|
||||
}
|
||||
|
||||
static void qcom_pci_config_ecam(struct dw_pcie_rp *pp)
|
||||
{
|
||||
struct dw_pcie *pci = to_dw_pcie_from_pp(pp);
|
||||
struct qcom_pcie *pcie = to_qcom_pcie(pci);
|
||||
u64 addr, addr_end;
|
||||
u32 val;
|
||||
|
||||
writel_relaxed(lower_32_bits(pci->dbi_phys_addr), pcie->parf + PARF_ECAM_BASE);
|
||||
writel_relaxed(upper_32_bits(pci->dbi_phys_addr), pcie->parf + PARF_ECAM_BASE_HI);
|
||||
|
||||
/*
|
||||
* The only device on the root bus is a single Root Port. If we try to
|
||||
* access any devices other than Device/Function 00.0 on Bus 0, the TLP
|
||||
* will go outside of the controller to the PCI bus. But with CFG Shift
|
||||
* Feature (ECAM) enabled in iATU, there is no guarantee that the
|
||||
* response is going to be all F's. Hence, to make sure that the
|
||||
* requester gets all F's response for accesses other than the Root
|
||||
* Port, configure iATU to block the transactions starting from
|
||||
* function 1 of the root bus to the end of the root bus (i.e., from
|
||||
* dbi_base + 4KB to dbi_base + 1MB).
|
||||
*/
|
||||
addr = pci->dbi_phys_addr + SZ_4K;
|
||||
writel_relaxed(lower_32_bits(addr), pcie->parf + PARF_BLOCK_SLV_AXI_WR_BASE);
|
||||
writel_relaxed(upper_32_bits(addr), pcie->parf + PARF_BLOCK_SLV_AXI_WR_BASE_HI);
|
||||
|
||||
writel_relaxed(lower_32_bits(addr), pcie->parf + PARF_BLOCK_SLV_AXI_RD_BASE);
|
||||
writel_relaxed(upper_32_bits(addr), pcie->parf + PARF_BLOCK_SLV_AXI_RD_BASE_HI);
|
||||
|
||||
addr_end = pci->dbi_phys_addr + SZ_1M - 1;
|
||||
|
||||
writel_relaxed(lower_32_bits(addr_end), pcie->parf + PARF_BLOCK_SLV_AXI_WR_LIMIT);
|
||||
writel_relaxed(upper_32_bits(addr_end), pcie->parf + PARF_BLOCK_SLV_AXI_WR_LIMIT_HI);
|
||||
|
||||
writel_relaxed(lower_32_bits(addr_end), pcie->parf + PARF_BLOCK_SLV_AXI_RD_LIMIT);
|
||||
writel_relaxed(upper_32_bits(addr_end), pcie->parf + PARF_BLOCK_SLV_AXI_RD_LIMIT_HI);
|
||||
|
||||
val = readl_relaxed(pcie->parf + PARF_SYS_CTRL);
|
||||
val |= PCIE_ECAM_BLOCKER_EN;
|
||||
writel_relaxed(val, pcie->parf + PARF_SYS_CTRL);
|
||||
}
|
||||
|
||||
static int qcom_pcie_start_link(struct dw_pcie *pci)
|
||||
{
|
||||
struct qcom_pcie *pcie = to_qcom_pcie(pci);
|
||||
@@ -1320,7 +1264,6 @@ static int qcom_pcie_host_init(struct dw_pcie_rp *pp)
|
||||
{
|
||||
struct dw_pcie *pci = to_dw_pcie_from_pp(pp);
|
||||
struct qcom_pcie *pcie = to_qcom_pcie(pci);
|
||||
u16 offset;
|
||||
int ret;
|
||||
|
||||
qcom_ep_reset_assert(pcie);
|
||||
@@ -1329,17 +1272,6 @@ static int qcom_pcie_host_init(struct dw_pcie_rp *pp)
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
if (pp->ecam_enabled) {
|
||||
/*
|
||||
* Override ELBI when ECAM is enabled, as when ECAM is enabled,
|
||||
* ELBI moves under the 'config' space.
|
||||
*/
|
||||
offset = FIELD_GET(SLV_DBI_ELBI_ADDR_BASE, readl(pcie->parf + PARF_SLV_DBI_ELBI));
|
||||
pci->elbi_base = pci->dbi_base + offset;
|
||||
|
||||
qcom_pci_config_ecam(pp);
|
||||
}
|
||||
|
||||
ret = qcom_pcie_phy_power_on(pcie);
|
||||
if (ret)
|
||||
goto err_deinit;
|
||||
|
||||
@@ -243,8 +243,7 @@ struct pcie_link_state {
|
||||
/* Clock PM state */
|
||||
u32 clkpm_capable:1; /* Clock PM capable? */
|
||||
u32 clkpm_enabled:1; /* Current Clock PM state */
|
||||
u32 clkpm_default:1; /* Default Clock PM state by BIOS or
|
||||
override */
|
||||
u32 clkpm_default:1; /* Default Clock PM state by BIOS */
|
||||
u32 clkpm_disable:1; /* Clock PM disabled */
|
||||
};
|
||||
|
||||
@@ -376,18 +375,6 @@ static void pcie_set_clkpm(struct pcie_link_state *link, int enable)
|
||||
pcie_set_clkpm_nocheck(link, enable);
|
||||
}
|
||||
|
||||
static void pcie_clkpm_override_default_link_state(struct pcie_link_state *link,
|
||||
int enabled)
|
||||
{
|
||||
struct pci_dev *pdev = link->downstream;
|
||||
|
||||
/* For devicetree platforms, enable ClockPM by default */
|
||||
if (of_have_populated_dt() && !enabled) {
|
||||
link->clkpm_default = 1;
|
||||
pci_info(pdev, "ASPM: DT platform, enabling ClockPM\n");
|
||||
}
|
||||
}
|
||||
|
||||
static void pcie_clkpm_cap_init(struct pcie_link_state *link, int blacklist)
|
||||
{
|
||||
int capable = 1, enabled = 1;
|
||||
@@ -410,7 +397,6 @@ static void pcie_clkpm_cap_init(struct pcie_link_state *link, int blacklist)
|
||||
}
|
||||
link->clkpm_enabled = enabled;
|
||||
link->clkpm_default = enabled;
|
||||
pcie_clkpm_override_default_link_state(link, enabled);
|
||||
link->clkpm_capable = capable;
|
||||
link->clkpm_disable = blacklist ? 1 : 0;
|
||||
}
|
||||
@@ -811,19 +797,17 @@ static void pcie_aspm_override_default_link_state(struct pcie_link_state *link)
|
||||
struct pci_dev *pdev = link->downstream;
|
||||
u32 override;
|
||||
|
||||
/* For devicetree platforms, enable all ASPM states by default */
|
||||
/* For devicetree platforms, enable L0s and L1 by default */
|
||||
if (of_have_populated_dt()) {
|
||||
link->aspm_default = PCIE_LINK_STATE_ASPM_ALL;
|
||||
if (link->aspm_support & PCIE_LINK_STATE_L0S)
|
||||
link->aspm_default |= PCIE_LINK_STATE_L0S;
|
||||
if (link->aspm_support & PCIE_LINK_STATE_L1)
|
||||
link->aspm_default |= PCIE_LINK_STATE_L1;
|
||||
override = link->aspm_default & ~link->aspm_enabled;
|
||||
if (override)
|
||||
pci_info(pdev, "ASPM: DT platform, enabling%s%s%s%s%s%s%s\n",
|
||||
FLAG(override, L0S_UP, " L0s-up"),
|
||||
FLAG(override, L0S_DW, " L0s-dw"),
|
||||
FLAG(override, L1, " L1"),
|
||||
FLAG(override, L1_1, " ASPM-L1.1"),
|
||||
FLAG(override, L1_2, " ASPM-L1.2"),
|
||||
FLAG(override, L1_1_PCIPM, " PCI-PM-L1.1"),
|
||||
FLAG(override, L1_2_PCIPM, " PCI-PM-L1.2"));
|
||||
pci_info(pdev, "ASPM: default states%s%s\n",
|
||||
FLAG(override, L0S, " L0s"),
|
||||
FLAG(override, L1, " L1"));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user