Linux PCI subsystem development
 help / color / mirror / Atom feed
* [PATCH 0/2] PCI: dwc: Handle return value from endpoint .init/.preinit callbacks
@ 2026-07-28  1:24 Marek Vasut
  2026-07-28  1:24 ` [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback Marek Vasut
  2026-07-28  1:24 ` [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback Marek Vasut
  0 siblings, 2 replies; 5+ messages in thread
From: Marek Vasut @ 2026-07-28  1:24 UTC (permalink / raw)
  To: linux-pci
  Cc: Marek Vasut, Krzysztof Wilczyński, Anand Moon, Bjorn Helgaas,
	Frank Li, Geert Uytterhoeven, Heiko Stuebner, Jesper Nilsson,
	Jingoo Han, Koichiro Den, Lorenzo Pieralisi, Magnus Damm,
	Manivannan Sadhasivam, Minghuan Lian, Mingkai Hu,
	Nicolas Frattaroli, Niklas Cassel, Qianfeng Rong, Qiang Yu,
	Rob Herring, Roy Zang, Shawn Lin, Siddharth Vadapalli,
	Srikanth Thokala, Vignesh Raghavendra, Yoshihiro Shimoda,
	Yuho Choi, imx, linux-arm-kernel, linux-kernel, linux-omap,
	linux-renesas-soc, linux-rockchip

This is a trivial preparatory change which allows checking
the struct dw_pcie_ep_ops .init/.pre_init return values.

Currently only the Layerscape PCIe controller benefits from this as
its ls_pcie_ep_init() may fail in dw_pcie_ep_get_func_from_ep() call,
but the Renesas R-Car Gen5 will benefit from this next.

Since this affects many controller glues and has a huge CC list,
I am sending this separately from the R-Car Gen5 patches.

Marek Vasut (2):
  PCI: dwc: Handle return value from endpoint .init callback
  PCI: dwc: Handle return value from endpoint .pre_init callback

 drivers/pci/controller/dwc/pci-dra7xx.c         |  4 +++-
 drivers/pci/controller/dwc/pci-keystone.c       |  4 +++-
 drivers/pci/controller/dwc/pci-layerscape-ep.c  |  6 ++++--
 drivers/pci/controller/dwc/pcie-artpec6.c       |  4 +++-
 drivers/pci/controller/dwc/pcie-designware-ep.c | 14 ++++++++++----
 drivers/pci/controller/dwc/pcie-designware.h    |  4 ++--
 drivers/pci/controller/dwc/pcie-dw-rockchip.c   |  4 +++-
 drivers/pci/controller/dwc/pcie-keembay.c       |  4 +++-
 drivers/pci/controller/dwc/pcie-rcar-gen4.c     |  6 ++++--
 9 files changed, 35 insertions(+), 15 deletions(-)

---
Cc: "Krzysztof Wilczyński" <kwilczynski@kernel.org>
Cc: Anand Moon <linux.amoon@gmail.com>
Cc: Bjorn Helgaas <bhelgaas@google.com>
Cc: Frank Li <Frank.Li@nxp.com>
Cc: Geert Uytterhoeven <geert+renesas@glider.be>
Cc: Heiko Stuebner <heiko@sntech.de>
Cc: Jesper Nilsson <jesper.nilsson@axis.com>
Cc: Jingoo Han <jingoohan1@gmail.com>
Cc: Koichiro Den <den@valinux.co.jp>
Cc: Lorenzo Pieralisi <lpieralisi@kernel.org>
Cc: Magnus Damm <magnus.damm@gmail.com>
Cc: Manivannan Sadhasivam <mani@kernel.org>
Cc: Minghuan Lian <minghuan.Lian@nxp.com>
Cc: Mingkai Hu <mingkai.hu@nxp.com>
Cc: Nicolas Frattaroli <nicolas.frattaroli@collabora.com>
Cc: Niklas Cassel <cassel@kernel.org>
Cc: Qianfeng Rong <rongqianfeng@vivo.com>
Cc: Qiang Yu <qiang.yu@oss.qualcomm.com>
Cc: Rob Herring <robh@kernel.org>
Cc: Roy Zang <roy.zang@nxp.com>
Cc: Shawn Lin <shawn.lin@rock-chips.com>
Cc: Siddharth Vadapalli <s-vadapalli@ti.com>
Cc: Srikanth Thokala <srikanth.thokala@intel.com>
Cc: Vignesh Raghavendra <vigneshr@ti.com>
Cc: Yoshihiro Shimoda <yoshihiro.shimoda.uh@renesas.com>
Cc: Yuho Choi <dbgh9129@gmail.com>
Cc: imx@lists.linux.dev
Cc: linux-arm-kernel@lists.infradead.org
Cc: linux-kernel@vger.kernel.org
Cc: linux-omap@vger.kernel.org
Cc: linux-pci@vger.kernel.org
Cc: linux-renesas-soc@vger.kernel.org
Cc: linux-rockchip@lists.infradead.org

-- 
2.53.0


^ permalink raw reply	[flat|nested] 5+ messages in thread

* [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback
  2026-07-28  1:24 [PATCH 0/2] PCI: dwc: Handle return value from endpoint .init/.preinit callbacks Marek Vasut
@ 2026-07-28  1:24 ` Marek Vasut
  2026-07-28  1:40   ` sashiko-bot
  2026-07-28  1:24 ` [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback Marek Vasut
  1 sibling, 1 reply; 5+ messages in thread
From: Marek Vasut @ 2026-07-28  1:24 UTC (permalink / raw)
  To: linux-pci
  Cc: Marek Vasut, Krzysztof Wilczyński, Anand Moon, Bjorn Helgaas,
	Frank Li, Geert Uytterhoeven, Heiko Stuebner, Jesper Nilsson,
	Jingoo Han, Koichiro Den, Lorenzo Pieralisi, Magnus Damm,
	Manivannan Sadhasivam, Minghuan Lian, Mingkai Hu,
	Nicolas Frattaroli, Niklas Cassel, Qianfeng Rong, Qiang Yu,
	Rob Herring, Roy Zang, Shawn Lin, Siddharth Vadapalli,
	Srikanth Thokala, Vignesh Raghavendra, Yoshihiro Shimoda,
	Yuho Choi, imx, linux-arm-kernel, linux-kernel, linux-omap,
	linux-renesas-soc, linux-rockchip

Add return value handling for struct dw_pcie_ep_ops .init callback.

Signed-off-by: Marek Vasut <marek.vasut+renesas@mailbox.org>
---
Cc: "Krzysztof Wilczyński" <kwilczynski@kernel.org>
Cc: Anand Moon <linux.amoon@gmail.com>
Cc: Bjorn Helgaas <bhelgaas@google.com>
Cc: Frank Li <Frank.Li@nxp.com>
Cc: Geert Uytterhoeven <geert+renesas@glider.be>
Cc: Heiko Stuebner <heiko@sntech.de>
Cc: Jesper Nilsson <jesper.nilsson@axis.com>
Cc: Jingoo Han <jingoohan1@gmail.com>
Cc: Koichiro Den <den@valinux.co.jp>
Cc: Lorenzo Pieralisi <lpieralisi@kernel.org>
Cc: Magnus Damm <magnus.damm@gmail.com>
Cc: Manivannan Sadhasivam <mani@kernel.org>
Cc: Minghuan Lian <minghuan.Lian@nxp.com>
Cc: Mingkai Hu <mingkai.hu@nxp.com>
Cc: Nicolas Frattaroli <nicolas.frattaroli@collabora.com>
Cc: Niklas Cassel <cassel@kernel.org>
Cc: Qianfeng Rong <rongqianfeng@vivo.com>
Cc: Qiang Yu <qiang.yu@oss.qualcomm.com>
Cc: Rob Herring <robh@kernel.org>
Cc: Roy Zang <roy.zang@nxp.com>
Cc: Shawn Lin <shawn.lin@rock-chips.com>
Cc: Siddharth Vadapalli <s-vadapalli@ti.com>
Cc: Srikanth Thokala <srikanth.thokala@intel.com>
Cc: Vignesh Raghavendra <vigneshr@ti.com>
Cc: Yoshihiro Shimoda <yoshihiro.shimoda.uh@renesas.com>
Cc: Yuho Choi <dbgh9129@gmail.com>
Cc: imx@lists.linux.dev
Cc: linux-arm-kernel@lists.infradead.org
Cc: linux-kernel@vger.kernel.org
Cc: linux-omap@vger.kernel.org
Cc: linux-pci@vger.kernel.org
Cc: linux-renesas-soc@vger.kernel.org
Cc: linux-rockchip@lists.infradead.org
---
 drivers/pci/controller/dwc/pci-dra7xx.c         | 4 +++-
 drivers/pci/controller/dwc/pci-keystone.c       | 4 +++-
 drivers/pci/controller/dwc/pci-layerscape-ep.c  | 6 ++++--
 drivers/pci/controller/dwc/pcie-artpec6.c       | 4 +++-
 drivers/pci/controller/dwc/pcie-designware-ep.c | 7 +++++--
 drivers/pci/controller/dwc/pcie-designware.h    | 2 +-
 drivers/pci/controller/dwc/pcie-dw-rockchip.c   | 4 +++-
 drivers/pci/controller/dwc/pcie-keembay.c       | 4 +++-
 8 files changed, 25 insertions(+), 10 deletions(-)

diff --git a/drivers/pci/controller/dwc/pci-dra7xx.c b/drivers/pci/controller/dwc/pci-dra7xx.c
index 3fc889944f021..6ae5b27e27b32 100644
--- a/drivers/pci/controller/dwc/pci-dra7xx.c
+++ b/drivers/pci/controller/dwc/pci-dra7xx.c
@@ -373,12 +373,14 @@ static const struct dw_pcie_host_ops dra7xx_pcie_host_ops = {
 	.init = dra7xx_pcie_host_init,
 };
 
-static void dra7xx_pcie_ep_init(struct dw_pcie_ep *ep)
+static int dra7xx_pcie_ep_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *pci = to_dw_pcie_from_ep(ep);
 	struct dra7xx_pcie *dra7xx = to_dra7xx_pcie(pci);
 
 	dra7xx_pcie_enable_wrapper_interrupts(dra7xx);
+
+	return 0;
 }
 
 static void dra7xx_pcie_raise_intx_irq(struct dra7xx_pcie *dra7xx)
diff --git a/drivers/pci/controller/dwc/pci-keystone.c b/drivers/pci/controller/dwc/pci-keystone.c
index f1b27aed488de..602516239a573 100644
--- a/drivers/pci/controller/dwc/pci-keystone.c
+++ b/drivers/pci/controller/dwc/pci-keystone.c
@@ -876,7 +876,7 @@ static const struct dw_pcie_ops ks_pcie_dw_pcie_ops = {
 	.write_dbi2 = ks_pcie_am654_write_dbi2,
 };
 
-static void ks_pcie_am654_ep_init(struct dw_pcie_ep *ep)
+static int ks_pcie_am654_ep_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *pci = to_dw_pcie_from_ep(ep);
 	int flags;
@@ -885,6 +885,8 @@ static void ks_pcie_am654_ep_init(struct dw_pcie_ep *ep)
 	flags = PCI_BASE_ADDRESS_SPACE_MEMORY | PCI_BASE_ADDRESS_MEM_TYPE_32;
 	dw_pcie_writel_dbi2(pci, PCI_BASE_ADDRESS_0, APP_ADDR_SPACE_0 - 1);
 	dw_pcie_writel_dbi(pci, PCI_BASE_ADDRESS_0, flags);
+
+	return 0;
 }
 
 static void ks_pcie_am654_raise_intx_irq(struct keystone_pcie *ks_pcie)
diff --git a/drivers/pci/controller/dwc/pci-layerscape-ep.c b/drivers/pci/controller/dwc/pci-layerscape-ep.c
index 8936975ff104e..527c57114dcfe 100644
--- a/drivers/pci/controller/dwc/pci-layerscape-ep.c
+++ b/drivers/pci/controller/dwc/pci-layerscape-ep.c
@@ -147,7 +147,7 @@ ls_pcie_ep_get_features(struct dw_pcie_ep *ep)
 	return pcie->ls_epc;
 }
 
-static void ls_pcie_ep_init(struct dw_pcie_ep *ep)
+static int ls_pcie_ep_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *pci = to_dw_pcie_from_ep(ep);
 	struct ls_pcie_ep *pcie = to_ls_pcie_ep(pci);
@@ -155,10 +155,12 @@ static void ls_pcie_ep_init(struct dw_pcie_ep *ep)
 
 	ep_func = dw_pcie_ep_get_func_from_ep(ep, 0);
 	if (!ep_func)
-		return;
+		return -ENODEV;
 
 	pcie->ls_epc->msi_capable = ep_func->msi_cap ? true : false;
 	pcie->ls_epc->msix_capable = ep_func->msix_cap ? true : false;
+
+	return 0;
 }
 
 static int ls_pcie_ep_raise_irq(struct dw_pcie_ep *ep, u8 func_no,
diff --git a/drivers/pci/controller/dwc/pcie-artpec6.c b/drivers/pci/controller/dwc/pcie-artpec6.c
index 5cd227dda9a10..7f0ba506dd1cf 100644
--- a/drivers/pci/controller/dwc/pcie-artpec6.c
+++ b/drivers/pci/controller/dwc/pcie-artpec6.c
@@ -335,7 +335,7 @@ static const struct dw_pcie_host_ops artpec6_pcie_host_ops = {
 	.init = artpec6_pcie_host_init,
 };
 
-static void artpec6_pcie_ep_init(struct dw_pcie_ep *ep)
+static int artpec6_pcie_ep_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *pci = to_dw_pcie_from_ep(ep);
 	struct artpec6_pcie *artpec6_pcie = to_artpec6_pcie(pci);
@@ -344,6 +344,8 @@ static void artpec6_pcie_ep_init(struct dw_pcie_ep *ep)
 	artpec6_pcie_init_phy(artpec6_pcie);
 	artpec6_pcie_deassert_core_reset(artpec6_pcie);
 	artpec6_pcie_wait_for_phy(artpec6_pcie);
+
+	return 0;
 }
 
 static int artpec6_pcie_raise_irq(struct dw_pcie_ep *ep, u8 func_no,
diff --git a/drivers/pci/controller/dwc/pcie-designware-ep.c b/drivers/pci/controller/dwc/pcie-designware-ep.c
index 7d2794945704e..d78fb845582b2 100644
--- a/drivers/pci/controller/dwc/pcie-designware-ep.c
+++ b/drivers/pci/controller/dwc/pcie-designware-ep.c
@@ -1367,8 +1367,11 @@ int dw_pcie_ep_init_registers(struct dw_pcie_ep *ep)
 		list_add_tail(&ep_func->list, &ep->func_list);
 	}
 
-	if (ep->ops->init)
-		ep->ops->init(ep);
+	if (ep->ops->init) {
+		ret = ep->ops->init(ep);
+		if (ret)
+			goto err_remove_edma;
+	}
 
 	dw_pcie_ep_disable_bars(ep);
 
diff --git a/drivers/pci/controller/dwc/pcie-designware.h b/drivers/pci/controller/dwc/pcie-designware.h
index de4b245b1758c..004b433f17135 100644
--- a/drivers/pci/controller/dwc/pcie-designware.h
+++ b/drivers/pci/controller/dwc/pcie-designware.h
@@ -475,7 +475,7 @@ struct dw_pcie_rp {
 
 struct dw_pcie_ep_ops {
 	void	(*pre_init)(struct dw_pcie_ep *ep);
-	void	(*init)(struct dw_pcie_ep *ep);
+	int	(*init)(struct dw_pcie_ep *ep);
 	int	(*raise_irq)(struct dw_pcie_ep *ep, u8 func_no,
 			     unsigned int type, u16 interrupt_num);
 	const struct pci_epc_features* (*get_features)(struct dw_pcie_ep *ep);
diff --git a/drivers/pci/controller/dwc/pcie-dw-rockchip.c b/drivers/pci/controller/dwc/pcie-dw-rockchip.c
index 731d93663ccae..bd5d1a2472a40 100644
--- a/drivers/pci/controller/dwc/pcie-dw-rockchip.c
+++ b/drivers/pci/controller/dwc/pcie-dw-rockchip.c
@@ -469,12 +469,14 @@ static void rockchip_pcie_ep_hide_broken_ats_cap_rk3588(struct dw_pcie_ep *ep)
 	dw_pcie_remove_ext_capability(pci, PCI_EXT_CAP_ID_ATS);
 }
 
-static void rockchip_pcie_ep_init(struct dw_pcie_ep *ep)
+static int rockchip_pcie_ep_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *pci = to_dw_pcie_from_ep(ep);
 
 	rockchip_pcie_enable_l0s(pci);
 	rockchip_pcie_ep_hide_broken_ats_cap_rk3588(ep);
+
+	return 0;
 };
 
 static int rockchip_pcie_raise_irq(struct dw_pcie_ep *ep, u8 func_no,
diff --git a/drivers/pci/controller/dwc/pcie-keembay.c b/drivers/pci/controller/dwc/pcie-keembay.c
index 42fb5f24a2230..b11e66c10fffa 100644
--- a/drivers/pci/controller/dwc/pcie-keembay.c
+++ b/drivers/pci/controller/dwc/pcie-keembay.c
@@ -278,12 +278,14 @@ static int keembay_pcie_setup_msi_irq(struct keembay_pcie *pcie)
 	return 0;
 }
 
-static void keembay_pcie_ep_init(struct dw_pcie_ep *ep)
+static int keembay_pcie_ep_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *pci = to_dw_pcie_from_ep(ep);
 	struct keembay_pcie *pcie = dev_get_drvdata(pci->dev);
 
 	writel(EDMA_INT_EN, pcie->apb_base + PCIE_REGS_INTERRUPT_ENABLE);
+
+	return 0;
 }
 
 static int keembay_pcie_ep_raise_irq(struct dw_pcie_ep *ep, u8 func_no,
-- 
2.53.0


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback
  2026-07-28  1:24 [PATCH 0/2] PCI: dwc: Handle return value from endpoint .init/.preinit callbacks Marek Vasut
  2026-07-28  1:24 ` [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback Marek Vasut
@ 2026-07-28  1:24 ` Marek Vasut
  2026-07-28  1:37   ` sashiko-bot
  1 sibling, 1 reply; 5+ messages in thread
From: Marek Vasut @ 2026-07-28  1:24 UTC (permalink / raw)
  To: linux-pci
  Cc: Marek Vasut, Krzysztof Wilczyński, Anand Moon, Bjorn Helgaas,
	Frank Li, Geert Uytterhoeven, Heiko Stuebner, Jesper Nilsson,
	Jingoo Han, Koichiro Den, Lorenzo Pieralisi, Magnus Damm,
	Manivannan Sadhasivam, Minghuan Lian, Mingkai Hu,
	Nicolas Frattaroli, Niklas Cassel, Qianfeng Rong, Qiang Yu,
	Rob Herring, Roy Zang, Shawn Lin, Siddharth Vadapalli,
	Srikanth Thokala, Vignesh Raghavendra, Yoshihiro Shimoda,
	Yuho Choi, imx, linux-arm-kernel, linux-kernel, linux-omap,
	linux-renesas-soc, linux-rockchip

Add return value handling for struct dw_pcie_ep_ops .pre_init callback.

Signed-off-by: Marek Vasut <marek.vasut+renesas@mailbox.org>
---
Cc: "Krzysztof Wilczyński" <kwilczynski@kernel.org>
Cc: Anand Moon <linux.amoon@gmail.com>
Cc: Bjorn Helgaas <bhelgaas@google.com>
Cc: Frank Li <Frank.Li@nxp.com>
Cc: Geert Uytterhoeven <geert+renesas@glider.be>
Cc: Heiko Stuebner <heiko@sntech.de>
Cc: Jesper Nilsson <jesper.nilsson@axis.com>
Cc: Jingoo Han <jingoohan1@gmail.com>
Cc: Koichiro Den <den@valinux.co.jp>
Cc: Lorenzo Pieralisi <lpieralisi@kernel.org>
Cc: Magnus Damm <magnus.damm@gmail.com>
Cc: Manivannan Sadhasivam <mani@kernel.org>
Cc: Minghuan Lian <minghuan.Lian@nxp.com>
Cc: Mingkai Hu <mingkai.hu@nxp.com>
Cc: Nicolas Frattaroli <nicolas.frattaroli@collabora.com>
Cc: Niklas Cassel <cassel@kernel.org>
Cc: Qianfeng Rong <rongqianfeng@vivo.com>
Cc: Qiang Yu <qiang.yu@oss.qualcomm.com>
Cc: Rob Herring <robh@kernel.org>
Cc: Roy Zang <roy.zang@nxp.com>
Cc: Shawn Lin <shawn.lin@rock-chips.com>
Cc: Siddharth Vadapalli <s-vadapalli@ti.com>
Cc: Srikanth Thokala <srikanth.thokala@intel.com>
Cc: Vignesh Raghavendra <vigneshr@ti.com>
Cc: Yoshihiro Shimoda <yoshihiro.shimoda.uh@renesas.com>
Cc: Yuho Choi <dbgh9129@gmail.com>
Cc: imx@lists.linux.dev
Cc: linux-arm-kernel@lists.infradead.org
Cc: linux-kernel@vger.kernel.org
Cc: linux-omap@vger.kernel.org
Cc: linux-pci@vger.kernel.org
Cc: linux-renesas-soc@vger.kernel.org
Cc: linux-rockchip@lists.infradead.org
---
 drivers/pci/controller/dwc/pcie-designware-ep.c | 7 +++++--
 drivers/pci/controller/dwc/pcie-designware.h    | 2 +-
 drivers/pci/controller/dwc/pcie-rcar-gen4.c     | 6 ++++--
 3 files changed, 10 insertions(+), 5 deletions(-)

diff --git a/drivers/pci/controller/dwc/pcie-designware-ep.c b/drivers/pci/controller/dwc/pcie-designware-ep.c
index d78fb845582b2..b00239097d893 100644
--- a/drivers/pci/controller/dwc/pcie-designware-ep.c
+++ b/drivers/pci/controller/dwc/pcie-designware-ep.c
@@ -1524,8 +1524,11 @@ int dw_pcie_ep_init(struct dw_pcie_ep *ep)
 	if (ret)
 		return ret;
 
-	if (ep->ops->pre_init)
-		ep->ops->pre_init(ep);
+	if (ep->ops->pre_init) {
+		ret = ep->ops->pre_init(ep);
+		if (ret)
+			return ret;
+	}
 
 	ret = pci_epc_mem_init(epc, ep->phys_base, ep->addr_size,
 			       ep->page_size);
diff --git a/drivers/pci/controller/dwc/pcie-designware.h b/drivers/pci/controller/dwc/pcie-designware.h
index 004b433f17135..6546dc3aa2075 100644
--- a/drivers/pci/controller/dwc/pcie-designware.h
+++ b/drivers/pci/controller/dwc/pcie-designware.h
@@ -474,7 +474,7 @@ struct dw_pcie_rp {
 };
 
 struct dw_pcie_ep_ops {
-	void	(*pre_init)(struct dw_pcie_ep *ep);
+	int	(*pre_init)(struct dw_pcie_ep *ep);
 	int	(*init)(struct dw_pcie_ep *ep);
 	int	(*raise_irq)(struct dw_pcie_ep *ep, u8 func_no,
 			     unsigned int type, u16 interrupt_num);
diff --git a/drivers/pci/controller/dwc/pcie-rcar-gen4.c b/drivers/pci/controller/dwc/pcie-rcar-gen4.c
index 5f7211b91ee5b..fbe465a29068f 100644
--- a/drivers/pci/controller/dwc/pcie-rcar-gen4.c
+++ b/drivers/pci/controller/dwc/pcie-rcar-gen4.c
@@ -481,7 +481,7 @@ static void rcar_gen4_remove_dw_pcie_rp(struct rcar_gen4_pcie *rcar)
 }
 
 /* Endpoint mode */
-static void rcar_gen4_pcie_ep_pre_init(struct dw_pcie_ep *ep)
+static int rcar_gen4_pcie_ep_pre_init(struct dw_pcie_ep *ep)
 {
 	struct dw_pcie *dw = to_dw_pcie_from_ep(ep);
 	struct rcar_gen4_pcie *rcar = to_rcar_gen4_pcie(dw);
@@ -489,9 +489,11 @@ static void rcar_gen4_pcie_ep_pre_init(struct dw_pcie_ep *ep)
 
 	ret = rcar_gen4_pcie_common_init(rcar);
 	if (ret)
-		return;
+		return ret;
 
 	writel(PCIEDMAINTSTSEN_INIT, rcar->base + PCIEDMAINTSTSEN);
+
+	return 0;
 }
 
 static void rcar_gen4_pcie_ep_deinit(struct rcar_gen4_pcie *rcar)
-- 
2.53.0


^ permalink raw reply related	[flat|nested] 5+ messages in thread

* Re: [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback
  2026-07-28  1:24 ` [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback Marek Vasut
@ 2026-07-28  1:37   ` sashiko-bot
  0 siblings, 0 replies; 5+ messages in thread
From: sashiko-bot @ 2026-07-28  1:37 UTC (permalink / raw)
  To: Marek Vasut; +Cc: wsa+renesas, linux-pci, Frank.Li, imx

Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
- [High] Unconditional cleanup in the rcar_gen4 endpoint driver leads to a double-disable of clocks and an unsafe unclocked register write when `pre_init` fails.
--

--- Patch [2]: [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback ---
commit 275f56803dca69c843553d94d9e95ba4e8dc68ae
Author: Marek Vasut <marek.vasut+renesas@mailbox.org>

PCI: dwc: Handle return value from endpoint .pre_init callback

This commit updates the DWC PCIe endpoint code to check and propagate the
return value of the .pre_init() callback. Drivers implementing this callback
are updated to return integer status codes rather than void.

> diff --git a/drivers/pci/controller/dwc/pcie-designware-ep.c b/drivers/pci/controller/dwc/pcie-designware-ep.c
> index d78fb845582b2..b00239097d893 100644
> --- a/drivers/pci/controller/dwc/pcie-designware-ep.c
> +++ b/drivers/pci/controller/dwc/pcie-designware-ep.c
[ ... ]
> @@ -1524,8 +1524,11 @@ int dw_pcie_ep_init(struct dw_pcie_ep *ep)
>  	if (ret)
>  		return ret;
>  
> -	if (ep->ops->pre_init)
> -		ep->ops->pre_init(ep);
> +	if (ep->ops->pre_init) {
> +		ret = ep->ops->pre_init(ep);
> +		if (ret)
> +			return ret;
> +	}
>  
>  	ret = pci_epc_mem_init(epc, ep->phys_base, ep->addr_size,
>  			       ep->page_size);
> diff --git a/drivers/pci/controller/dwc/pcie-rcar-gen4.c b/drivers/pci/controller/dwc/pcie-rcar-gen4.c
> index 8b03c42f8c84c..55ef0da9146c2 100644
> --- a/drivers/pci/controller/dwc/pcie-rcar-gen4.c
> +++ b/drivers/pci/controller/dwc/pcie-rcar-gen4.c
[ ... ]
> @@ -373,7 +373,7 @@ static void rcar_gen4_remove_dw_pcie_rp(struct rcar_gen4_pcie *rcar)
>  }
>  
>  /* Endpoint mode */
> -static void rcar_gen4_pcie_ep_pre_init(struct dw_pcie_ep *ep)
> +static int rcar_gen4_pcie_ep_pre_init(struct dw_pcie_ep *ep)
>  {
>  	struct dw_pcie *dw = to_dw_pcie_from_ep(ep);
>  	struct rcar_gen4_pcie *rcar = to_rcar_gen4_pcie(dw);
> @@ -381,9 +381,11 @@ static void rcar_gen4_pcie_ep_pre_init(struct dw_pcie_ep *ep)
>  
>  	ret = rcar_gen4_pcie_common_init(rcar);
>  	if (ret)
> -		return;
> +		return ret;

[Severity: High]
If rcar_gen4_pcie_common_init() fails, it will disable the PCIe clocks before
returning the error. With this patch, the error is now propagated back up
through dw_pcie_ep_init().

The caller of dw_pcie_ep_init() will then unconditionally perform cleanup:

drivers/pci/controller/dwc/pcie-rcar-gen4.c:rcar_gen4_add_dw_pcie_ep() {
	...
	ret = dw_pcie_ep_init(ep);
	if (ret) {
		rcar_gen4_pcie_ep_deinit(rcar);
		return ret;
	}
	...
}

Because rcar_gen4_pcie_ep_deinit() accesses the unclocked PCIEDMAINTSTSEN
register and then calls rcar_gen4_pcie_common_deinit(), could this result in
writing to an unclocked register and triggering a synchronous external abort?

Could it also cause a clock framework reference count underflow when the clocks
are disabled a second time during the cleanup?

>  
>  	writel(PCIEDMAINTSTSEN_INIT, rcar->base + PCIEDMAINTSTSEN);
> +
> +	return 0;
>  }
>  
>  static void rcar_gen4_pcie_ep_deinit(struct rcar_gen4_pcie *rcar)

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260728012548.465139-1-marek.vasut+renesas@mailbox.org?part=2

^ permalink raw reply	[flat|nested] 5+ messages in thread

* Re: [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback
  2026-07-28  1:24 ` [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback Marek Vasut
@ 2026-07-28  1:40   ` sashiko-bot
  0 siblings, 0 replies; 5+ messages in thread
From: sashiko-bot @ 2026-07-28  1:40 UTC (permalink / raw)
  To: Marek Vasut; +Cc: Frank.Li, imx, wsa+renesas, linux-pci

Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:

Pre-existing issues:
- [High] Double execution of `dw_pcie_edma_remove()` on the `dw_pcie_ep_init_registers()` error path leads to double-free of eDMA IRQs and DMA device unregistration list corruption.
--

--- Patch [1]: [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback ---
commit cb2920cc5e4b5269e0e38169339b1b10e422e580
Author: Marek Vasut <marek.vasut+renesas@mailbox.org>

PCI: dwc: Handle return value from endpoint .init callback

Add return value handling for struct dw_pcie_ep_ops .init callback.

> diff --git a/drivers/pci/controller/dwc/pcie-designware-ep.c b/drivers/pci/controller/dwc/pcie-designware-ep.c
> index 7d2794945704e..d78fb845582b2 100644
> --- a/drivers/pci/controller/dwc/pcie-designware-ep.c
> +++ b/drivers/pci/controller/dwc/pcie-designware-ep.c
[ ... ]
> @@ -1367,8 +1367,11 @@ int dw_pcie_ep_init_registers(struct dw_pcie_ep *ep)
>  		list_add_tail(&ep_func->list, &ep->func_list);
>  	}
>  
> -	if (ep->ops->init)
> -		ep->ops->init(ep);
> +	if (ep->ops->init) {
> +		ret = ep->ops->init(ep);
> +		if (ret)
> +			goto err_remove_edma;
> +	}

[Severity: High]
This is a pre-existing issue, but by handling the return value here, this
error path becomes more easily reachable. Can this lead to a double-free
of eDMA IRQs and list corruption?

If ep->ops->init() fails, the code jumps to err_remove_edma which calls
dw_pcie_edma_remove(pci) and returns the error code.

The caller typically catches this error and cleans up again:

drivers/pci/controller/dwc/pci-layerscape-ep.c:ls_pcie_ep_probe() {
    ...
    ret = dw_pcie_ep_init_registers(&pci->ep);
    if (ret) {
        ...
        dw_pcie_ep_deinit(&pci->ep);
        return ret;
    }
}

dw_pcie_ep_deinit() then calls dw_pcie_ep_cleanup(), which unconditionally
executes dw_pcie_edma_remove(pci) a second time.

Since dw_edma_remove() does not clear its internal state (chip->dw = NULL)
after freeing resources, will this second invocation cause a double-free
or kernel oops during a device probe failure?

>  
>  	dw_pcie_ep_disable_bars(ep);
>

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260728012548.465139-1-marek.vasut+renesas@mailbox.org?part=1

^ permalink raw reply	[flat|nested] 5+ messages in thread

end of thread, other threads:[~2026-07-28  1:40 UTC | newest]

Thread overview: 5+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-07-28  1:24 [PATCH 0/2] PCI: dwc: Handle return value from endpoint .init/.preinit callbacks Marek Vasut
2026-07-28  1:24 ` [PATCH 1/2] PCI: dwc: Handle return value from endpoint .init callback Marek Vasut
2026-07-28  1:40   ` sashiko-bot
2026-07-28  1:24 ` [PATCH 2/2] PCI: dwc: Handle return value from endpoint .pre_init callback Marek Vasut
2026-07-28  1:37   ` sashiko-bot

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox