Hello,
This series fixes the issue seen on Qcom EP platforms implementing the DWC
core while setting the BAR size. Currently, whatever the BAR size getting
programmed through pci_epc_set_bar() on the EP side is not reflected on the
host side during enumeration.
Debugging that issue revealed that the DWC Spec mandates asserting the DBI
CS2 register in addition to DBI CS while programming some read only and
shadow registers. So on the Qcom EP platforms, the driver needs to assert
DBI_CS2 in ELBI region before writing DBI2 registers and deassert it once
done.
This is done by implementing the write_dbi2() callback exposed by the DWC
core driver in the Qcom PCIe EP driver.
This series has been tested on Qcom SM8450 based development platform.
- Mani
Changes in v2:
- Switch to write_dbi2() callback as suggested by Sergey
Manivannan Sadhasivam (1):
PCI: qcom-ep: Implement write_dbi2() callback for writing DBI2
registers properly
drivers/pci/controller/dwc/pcie-qcom-ep.c | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
--
2.25.1
DWC core driver exposes the write_dbi2() callback for writing to the DBI2
registers in a vendor specific way. On the Qcom EP plaforms, DBI_CS2 bit in
the ELBI region needs to be asserted before writing to any DBI2 registers
and deasserted once done. So let's implement the callback for the Qcom PCIe
EP driver so that the DBI2 writes are handled properly in the hardware.
Without this callback, DBI2 register writes like BAR size won't go through
and as a result, the default BAR size is set for all BARs.
Cc: [email protected] # 5.16+
Fixes: f55fee56a631 ("PCI: qcom-ep: Add Qualcomm PCIe Endpoint controller driver")
Suggested-by: Serge Semin <[email protected]>
Signed-off-by: Manivannan Sadhasivam <[email protected]>
---
drivers/pci/controller/dwc/pcie-qcom-ep.c | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
diff --git a/drivers/pci/controller/dwc/pcie-qcom-ep.c b/drivers/pci/controller/dwc/pcie-qcom-ep.c
index 32c8d9e37876..7da0599f70e7 100644
--- a/drivers/pci/controller/dwc/pcie-qcom-ep.c
+++ b/drivers/pci/controller/dwc/pcie-qcom-ep.c
@@ -124,6 +124,7 @@
/* ELBI registers */
#define ELBI_SYS_STTS 0x08
+#define ELBI_CS2_ENABLE 0xa4
/* DBI registers */
#define DBI_CON_STATUS 0x44
@@ -262,6 +263,21 @@ static void qcom_pcie_dw_stop_link(struct dw_pcie *pci)
disable_irq(pcie_ep->perst_irq);
}
+static void qcom_pcie_write_dbi2(struct dw_pcie *pci, void __iomem *base,
+ u32 reg, size_t size, u32 val)
+{
+ struct qcom_pcie_ep *pcie_ep = to_pcie_ep(pci);
+ int ret;
+
+ writel(1, pcie_ep->elbi + ELBI_CS2_ENABLE);
+
+ ret = dw_pcie_write(pci->dbi_base2 + reg, size, val);
+ if (ret)
+ dev_err(pci->dev, "Failed to write DBI2 register (0x%x): %d\n", reg, ret);
+
+ writel(0, pcie_ep->elbi + ELBI_CS2_ENABLE);
+}
+
static void qcom_pcie_ep_icc_update(struct qcom_pcie_ep *pcie_ep)
{
struct dw_pcie *pci = &pcie_ep->pci;
@@ -500,6 +516,7 @@ static const struct dw_pcie_ops pci_ops = {
.link_up = qcom_pcie_dw_link_up,
.start_link = qcom_pcie_dw_start_link,
.stop_link = qcom_pcie_dw_stop_link,
+ .write_dbi2 = qcom_pcie_write_dbi2,
};
static int qcom_pcie_ep_get_io_resources(struct platform_device *pdev,
--
2.25.1
On Wed, Oct 25, 2023 at 06:30:29PM +0530, Manivannan Sadhasivam wrote:
> DWC core driver exposes the write_dbi2() callback for writing to the DBI2
> registers in a vendor specific way. On the Qcom EP plaforms, DBI_CS2 bit in
> the ELBI region needs to be asserted before writing to any DBI2 registers
> and deasserted once done. So let's implement the callback for the Qcom PCIe
> EP driver so that the DBI2 writes are handled properly in the hardware.
>
> Without this callback, DBI2 register writes like BAR size won't go through
> and as a result, the default BAR size is set for all BARs.
>
> Cc: [email protected] # 5.16+
> Fixes: f55fee56a631 ("PCI: qcom-ep: Add Qualcomm PCIe Endpoint controller driver")
> Suggested-by: Serge Semin <[email protected]>
> Signed-off-by: Manivannan Sadhasivam <[email protected]>
Reviewed-by: Serge Semin <[email protected]>
+1 tiny note below
> ---
> drivers/pci/controller/dwc/pcie-qcom-ep.c | 17 +++++++++++++++++
> 1 file changed, 17 insertions(+)
>
> diff --git a/drivers/pci/controller/dwc/pcie-qcom-ep.c b/drivers/pci/controller/dwc/pcie-qcom-ep.c
> index 32c8d9e37876..7da0599f70e7 100644
> --- a/drivers/pci/controller/dwc/pcie-qcom-ep.c
> +++ b/drivers/pci/controller/dwc/pcie-qcom-ep.c
> @@ -124,6 +124,7 @@
>
> /* ELBI registers */
> #define ELBI_SYS_STTS 0x08
> +#define ELBI_CS2_ENABLE 0xa4
>
> /* DBI registers */
> #define DBI_CON_STATUS 0x44
> @@ -262,6 +263,21 @@ static void qcom_pcie_dw_stop_link(struct dw_pcie *pci)
> disable_irq(pcie_ep->perst_irq);
> }
>
> +static void qcom_pcie_write_dbi2(struct dw_pcie *pci, void __iomem *base,
Just a general observation. I am not sure whether it's a local
convention or not, but it looks like the rest of the Qcom dw_pcie_ops
callbacks have the "qcom_pcie_dw_" prefix.
-Serge(y)
> + u32 reg, size_t size, u32 val)
> +{
> + struct qcom_pcie_ep *pcie_ep = to_pcie_ep(pci);
> + int ret;
> +
> + writel(1, pcie_ep->elbi + ELBI_CS2_ENABLE);
> +
> + ret = dw_pcie_write(pci->dbi_base2 + reg, size, val);
> + if (ret)
> + dev_err(pci->dev, "Failed to write DBI2 register (0x%x): %d\n", reg, ret);
> +
> + writel(0, pcie_ep->elbi + ELBI_CS2_ENABLE);
> +}
> +
> static void qcom_pcie_ep_icc_update(struct qcom_pcie_ep *pcie_ep)
> {
> struct dw_pcie *pci = &pcie_ep->pci;
> @@ -500,6 +516,7 @@ static const struct dw_pcie_ops pci_ops = {
> .link_up = qcom_pcie_dw_link_up,
> .start_link = qcom_pcie_dw_start_link,
> .stop_link = qcom_pcie_dw_stop_link,
> + .write_dbi2 = qcom_pcie_write_dbi2,
> };
>
> static int qcom_pcie_ep_get_io_resources(struct platform_device *pdev,
> --
> 2.25.1
>
Hello,
> This series fixes the issue seen on Qcom EP platforms implementing the DWC
> core while setting the BAR size. Currently, whatever the BAR size getting
> programmed through pci_epc_set_bar() on the EP side is not reflected on the
> host side during enumeration.
>
> Debugging that issue revealed that the DWC Spec mandates asserting the DBI
> CS2 register in addition to DBI CS while programming some read only and
> shadow registers. So on the Qcom EP platforms, the driver needs to assert
> DBI_CS2 in ELBI region before writing DBI2 registers and deassert it once
> done.
>
> This is done by implementing the write_dbi2() callback exposed by the DWC
> core driver in the Qcom PCIe EP driver.
>
> This series has been tested on Qcom SM8450 based development platform.
Applied to controller/qcom-ep, thank you!
[1/1] PCI: qcom-ep: Add dedicated callback for writing to DBI2 registers
https://git.kernel.org/pci/pci/c/a07d2497ed65
Krzysztof