diff options
author | Bjorn Helgaas <bhelgaas@google.com> | 2023-10-28 13:31:01 -0500 |
---|---|---|
committer | Bjorn Helgaas <bhelgaas@google.com> | 2023-10-28 13:31:01 -0500 |
commit | db20113d702e4f44d614676a967d0f74013fd25b (patch) | |
tree | 56638b19dd8676f2274e28c60aa96edcd9d79ce3 /drivers/pci/controller/dwc/pcie-designware-ep.c | |
parent | eecffeb045738b0214219c3ad44cd0502836efdf (diff) | |
parent | 6c4b39937f4e65688ea294725ae432b2565821ff (diff) |
Merge branch 'pci/controller/rcar'
- Add generic T_PVPERL macro for the required interval between power being
stable and PERST# being inactive (Yoshihiro Shimoda)
- Factor out dw_pcie_link_set_max_link_width() (Yoshihiro Shimoda)
- Update PCI_EXP_LNKCAP_MLW so Link Capabilities shows the correct max link
width (Yoshihiro Shimoda)
- Drop tegra194 PCI_EXP_LNKCAP_MLW setting since dw_pcie_setup() already
does it (Yoshihiro Shimoda)
- Add dwc support for different dbi and dbi2 register offsets, to be used
for R-Car Gen4 controllers (Yoshihiro Shimoda)
- Add EDMA_UNROLL capability flag for R-Car Gen4 controllers that don't
correctly advertise unrolled mapping via their eDMA CTRL register
(Yoshihiro Shimoda)
- Export dw_pcie_ep_exit() for use by the modular R-Car Gen4 driver
(Yoshihiro Shimoda)
- Add .pre_init() and .deinit() hooks for use by R-Car Gen4 controllers
(Yoshihiro Shimoda)
- Increase snps,dw-pcie DT reg and reg-names maxItems for R-Car Gen4
controllers (Yoshihiro Shimoda)
- Add rcar-gen4-pci host and endpoint DT bindings and drivers (Yoshihiro
Shimoda)
- Add Renesas R8A779F0 Device ID to pci_endpoint_test to allow testing on
R-Car S4-8 (Yoshihiro Shimoda)
* pci/controller/rcar:
misc: pci_endpoint_test: Add Device ID for R-Car S4-8 PCIe controller
MAINTAINERS: Update PCI DRIVER FOR RENESAS R-CAR for R-Car Gen4
PCI: rcar-gen4: Add endpoint mode support
PCI: rcar-gen4: Add R-Car Gen4 PCIe controller support for host mode
dt-bindings: PCI: renesas: Add R-Car Gen4 PCIe Endpoint
dt-bindings: PCI: renesas: Add R-Car Gen4 PCIe Host
dt-bindings: PCI: dwc: Update maxItems of reg and reg-names
PCI: dwc: endpoint: Introduce .pre_init() and .deinit()
PCI: dwc: Expose dw_pcie_write_dbi2() to module
PCI: dwc: Expose dw_pcie_ep_exit() to module
PCI: dwc: Add EDMA_UNROLL capability flag
PCI: dwc: endpoint: Add multiple PFs support for dbi2
PCI: tegra194: Drop PCI_EXP_LNKSTA_NLW setting
PCI: dwc: Add missing PCI_EXP_LNKCAP_MLW handling
PCI: dwc: Add dw_pcie_link_set_max_link_width()
PCI: Add T_PVPERL macro
Diffstat (limited to 'drivers/pci/controller/dwc/pcie-designware-ep.c')
-rw-r--r-- | drivers/pci/controller/dwc/pcie-designware-ep.c | 45 |
1 files changed, 36 insertions, 9 deletions
diff --git a/drivers/pci/controller/dwc/pcie-designware-ep.c b/drivers/pci/controller/dwc/pcie-designware-ep.c index f9182f8d552f..d34a5e87ad18 100644 --- a/drivers/pci/controller/dwc/pcie-designware-ep.c +++ b/drivers/pci/controller/dwc/pcie-designware-ep.c @@ -52,21 +52,35 @@ static unsigned int dw_pcie_ep_func_select(struct dw_pcie_ep *ep, u8 func_no) return func_offset; } +static unsigned int dw_pcie_ep_get_dbi2_offset(struct dw_pcie_ep *ep, u8 func_no) +{ + unsigned int dbi2_offset = 0; + + if (ep->ops->get_dbi2_offset) + dbi2_offset = ep->ops->get_dbi2_offset(ep, func_no); + else if (ep->ops->func_conf_select) /* for backward compatibility */ + dbi2_offset = ep->ops->func_conf_select(ep, func_no); + + return dbi2_offset; +} + static void __dw_pcie_ep_reset_bar(struct dw_pcie *pci, u8 func_no, enum pci_barno bar, int flags) { - u32 reg; - unsigned int func_offset = 0; + unsigned int func_offset, dbi2_offset; struct dw_pcie_ep *ep = &pci->ep; + u32 reg, reg_dbi2; func_offset = dw_pcie_ep_func_select(ep, func_no); + dbi2_offset = dw_pcie_ep_get_dbi2_offset(ep, func_no); reg = func_offset + PCI_BASE_ADDRESS_0 + (4 * bar); + reg_dbi2 = dbi2_offset + PCI_BASE_ADDRESS_0 + (4 * bar); dw_pcie_dbi_ro_wr_en(pci); - dw_pcie_writel_dbi2(pci, reg, 0x0); + dw_pcie_writel_dbi2(pci, reg_dbi2, 0x0); dw_pcie_writel_dbi(pci, reg, 0x0); if (flags & PCI_BASE_ADDRESS_MEM_TYPE_64) { - dw_pcie_writel_dbi2(pci, reg + 4, 0x0); + dw_pcie_writel_dbi2(pci, reg_dbi2 + 4, 0x0); dw_pcie_writel_dbi(pci, reg + 4, 0x0); } dw_pcie_dbi_ro_wr_dis(pci); @@ -228,16 +242,18 @@ static int dw_pcie_ep_set_bar(struct pci_epc *epc, u8 func_no, u8 vfunc_no, { struct dw_pcie_ep *ep = epc_get_drvdata(epc); struct dw_pcie *pci = to_dw_pcie_from_ep(ep); + unsigned int func_offset, dbi2_offset; enum pci_barno bar = epf_bar->barno; size_t size = epf_bar->size; int flags = epf_bar->flags; - unsigned int func_offset = 0; + u32 reg, reg_dbi2; int ret, type; - u32 reg; func_offset = dw_pcie_ep_func_select(ep, func_no); + dbi2_offset = dw_pcie_ep_get_dbi2_offset(ep, func_no); reg = PCI_BASE_ADDRESS_0 + (4 * bar) + func_offset; + reg_dbi2 = PCI_BASE_ADDRESS_0 + (4 * bar) + dbi2_offset; if (!(flags & PCI_BASE_ADDRESS_SPACE)) type = PCIE_ATU_TYPE_MEM; @@ -253,11 +269,11 @@ static int dw_pcie_ep_set_bar(struct pci_epc *epc, u8 func_no, u8 vfunc_no, dw_pcie_dbi_ro_wr_en(pci); - dw_pcie_writel_dbi2(pci, reg, lower_32_bits(size - 1)); + dw_pcie_writel_dbi2(pci, reg_dbi2, lower_32_bits(size - 1)); dw_pcie_writel_dbi(pci, reg, flags); if (flags & PCI_BASE_ADDRESS_MEM_TYPE_64) { - dw_pcie_writel_dbi2(pci, reg + 4, upper_32_bits(size - 1)); + dw_pcie_writel_dbi2(pci, reg_dbi2 + 4, upper_32_bits(size - 1)); dw_pcie_writel_dbi(pci, reg + 4, 0); } @@ -621,7 +637,11 @@ void dw_pcie_ep_exit(struct dw_pcie_ep *ep) epc->mem->window.page_size); pci_epc_mem_exit(epc); + + if (ep->ops->deinit) + ep->ops->deinit(ep); } +EXPORT_SYMBOL_GPL(dw_pcie_ep_exit); static unsigned int dw_pcie_ep_find_ext_capability(struct dw_pcie *pci, int cap) { @@ -723,6 +743,9 @@ int dw_pcie_ep_init(struct dw_pcie_ep *ep) ep->phys_base = res->start; ep->addr_size = resource_size(res); + if (ep->ops->pre_init) + ep->ops->pre_init(ep); + dw_pcie_version_detect(pci); dw_pcie_iatu_detect(pci); @@ -777,7 +800,7 @@ int dw_pcie_ep_init(struct dw_pcie_ep *ep) ep->page_size); if (ret < 0) { dev_err(dev, "Failed to initialize address space\n"); - return ret; + goto err_ep_deinit; } ep->msi_mem = pci_epc_mem_alloc_addr(epc, &ep->msi_mem_phys, @@ -814,6 +837,10 @@ err_free_epc_mem: err_exit_epc_mem: pci_epc_mem_exit(epc); +err_ep_deinit: + if (ep->ops->deinit) + ep->ops->deinit(ep); + return ret; } EXPORT_SYMBOL_GPL(dw_pcie_ep_init); |