* [PATCH 0/5] PCI: qcom: Add link retention support
@ 2026-01-09 7:21 Krishna Chaitanya Chundru
2026-01-09 7:21 ` [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up Krishna Chaitanya Chundru
` (5 more replies)
0 siblings, 6 replies; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-09 7:21 UTC (permalink / raw)
To: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci,
Krishna Chaitanya Chundru
This patch series introduces support for retaining the PCIe link across
bootloader and kernel handoff on Qualcomm platforms, specifically
X1E80100. The goal is to reduce boot time and avoid unnecessary link
reinitialization when the link is already up.
We are not enabling link retantion support for all the targets, as there
is no guarantee that the bootloader on all targets has initialized the
PCIe link in max supported speed. So we are enabling for hamoa & glymur
target only for now based on the config flag.
If the link is up and has link_retain is set to true in the
ithe driver config data then enable retain logic in the controller.
In phy as we already have skip init logic, the phy patch uses same
assumption that if there is phy no csr and bootloader has done the init
then driver can skip resetting the phy when phy status indicates it is
up.
Problem:-
1) As part of late init calls of clock & GENPD(for power domains) the
framework is disabling all the unvoted resources by that time and also
there is no sync state to keep them enabled till the probe is completed.
Due to dependencies with regulators and phy, qcom pcie probe is happening
after late init which is causing the resources(clocks & power domains) to
be off which causes the link to go down. To avoid this we need to use these
two kernel command line arguments (clk_ignore_unused & pd_ignore_unused)
to skip disabling clocks and gendp power domains as part of late init
for initial version. Once it is resolved we can avoid those kernel command
line arguments.
Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
---
Krishna Chaitanya Chundru (5):
phy: qcom: qmp-pcie: Skip PHY reset if already up
PCI: dwc: Add support for retaining link during host init
PCI: qcom: Keep PERST# GPIO state as-is during probe
PCI: qcom: Add link retention support
PCI: qcom: enable Link retain logic for Hamoa
drivers/pci/controller/dwc/pcie-designware-host.c | 11 ++--
drivers/pci/controller/dwc/pcie-designware.h | 1 +
drivers/pci/controller/dwc/pcie-qcom.c | 62 ++++++++++++++++++++---
drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++----
4 files changed, 83 insertions(+), 19 deletions(-)
---
base-commit: fc065cadc7ed048bedbb23cb6b7c4475198f431c
change-id: 20251001-link_retain-f181307947e4
Best regards,
--
Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
^ permalink raw reply [flat|nested] 22+ messages in thread
* [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
@ 2026-01-09 7:21 ` Krishna Chaitanya Chundru
2026-01-09 9:23 ` Abel Vesa
2026-01-09 13:08 ` Dmitry Baryshkov
2026-01-09 7:21 ` [PATCH 2/5] PCI: dwc: Add support for retaining link during host init Krishna Chaitanya Chundru
` (4 subsequent siblings)
5 siblings, 2 replies; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-09 7:21 UTC (permalink / raw)
To: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci,
Krishna Chaitanya Chundru
If the bootloader has already powered up the PCIe PHY, doing a full
reset and waiting for it to come up again slows down boot time.
Add a check for PHY status and skip the reset steps when the PHY is
already active. In this case, only enable the required resources during
power-on. This works alongside the existing logic that skips the init
sequence.
Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
---
drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++++++++++++++----------
1 file changed, 18 insertions(+), 10 deletions(-)
diff --git a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
index 86b1b7e2da86a8675e3e48e90b782afb21cafd77..c93e613cf80b2612f0f225fa2125f78dbec1a33f 100644
--- a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
+++ b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
@@ -3153,6 +3153,7 @@ struct qmp_pcie {
const struct qmp_phy_cfg *cfg;
bool tcsr_4ln_config;
bool skip_init;
+ bool skip_reset;
void __iomem *serdes;
void __iomem *pcs;
@@ -4537,6 +4538,9 @@ static int qmp_pcie_init(struct phy *phy)
qphy_checkbits(pcs, cfg->regs[QPHY_START_CTRL], SERDES_START | PCS_START) &&
qphy_checkbits(pcs, cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL], cfg->pwrdn_ctrl);
+ qmp->skip_reset = qmp->skip_init && !qphy_checkbits(pcs, cfg->regs[QPHY_PCS_STATUS],
+ cfg->phy_status);
+
if (!qmp->skip_init && !cfg->tbls.serdes_num) {
dev_err(qmp->dev, "Init sequence not available\n");
return -ENODATA;
@@ -4560,13 +4564,15 @@ static int qmp_pcie_init(struct phy *phy)
}
}
- ret = reset_control_assert(qmp->nocsr_reset);
- if (ret) {
- dev_err(qmp->dev, "no-csr reset assert failed\n");
- goto err_assert_reset;
- }
+ if (!qmp->skip_reset) {
+ ret = reset_control_assert(qmp->nocsr_reset);
+ if (ret) {
+ dev_err(qmp->dev, "no-csr reset assert failed\n");
+ goto err_assert_reset;
+ }
- usleep_range(200, 300);
+ usleep_range(200, 300);
+ }
if (!qmp->skip_init) {
ret = reset_control_bulk_deassert(cfg->num_resets, qmp->resets);
@@ -4641,10 +4647,12 @@ static int qmp_pcie_power_on(struct phy *phy)
if (ret)
return ret;
- ret = reset_control_deassert(qmp->nocsr_reset);
- if (ret) {
- dev_err(qmp->dev, "no-csr reset deassert failed\n");
- goto err_disable_pipe_clk;
+ if (!qmp->skip_reset) {
+ ret = reset_control_deassert(qmp->nocsr_reset);
+ if (ret) {
+ dev_err(qmp->dev, "no-csr reset deassert failed\n");
+ goto err_disable_pipe_clk;
+ }
}
if (qmp->skip_init)
--
2.34.1
^ permalink raw reply related [flat|nested] 22+ messages in thread
* [PATCH 2/5] PCI: dwc: Add support for retaining link during host init
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
2026-01-09 7:21 ` [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up Krishna Chaitanya Chundru
@ 2026-01-09 7:21 ` Krishna Chaitanya Chundru
2026-01-09 15:53 ` Bjorn Helgaas
2026-01-09 7:21 ` [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe Krishna Chaitanya Chundru
` (3 subsequent siblings)
5 siblings, 1 reply; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-09 7:21 UTC (permalink / raw)
To: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci,
Krishna Chaitanya Chundru
Some platforms keep the PCIe link up across bootloader and kernel
handoff. In such cases, reinitializing the root complex is unnecessary
if the DWC glue drivers wants to retain the PCIe link.
Introduce a link_retain flag in struct dw_pcie_rp to indicate that
the link should be preserved. When this flag is set by DWC glue drivers,
skip dw_pcie_setup_rc() and only initialize MSI, avoiding redundant
configuration steps.
Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
---
drivers/pci/controller/dwc/pcie-designware-host.c | 11 ++++++++---
drivers/pci/controller/dwc/pcie-designware.h | 1 +
2 files changed, 9 insertions(+), 3 deletions(-)
diff --git a/drivers/pci/controller/dwc/pcie-designware-host.c b/drivers/pci/controller/dwc/pcie-designware-host.c
index 372207c33a857b4c98572bb1e9b61fa0080bc871..d050df3f22e9507749a8f2fedd4c24fca43fb410 100644
--- a/drivers/pci/controller/dwc/pcie-designware-host.c
+++ b/drivers/pci/controller/dwc/pcie-designware-host.c
@@ -655,9 +655,14 @@ int dw_pcie_host_init(struct dw_pcie_rp *pp)
if (ret)
goto err_free_msi;
- ret = dw_pcie_setup_rc(pp);
- if (ret)
- goto err_remove_edma;
+ if (!pp->link_retain) {
+ ret = dw_pcie_setup_rc(pp);
+ if (ret)
+ goto err_remove_edma;
+ } else {
+ dw_pcie_msi_init(pp);
+ }
+
if (!dw_pcie_link_up(pci)) {
ret = dw_pcie_start_link(pci);
diff --git a/drivers/pci/controller/dwc/pcie-designware.h b/drivers/pci/controller/dwc/pcie-designware.h
index 31685951a080456b8834aab2bf79a36c78f46639..8acab751b66a06e8322e027ab55dc0ecfdcf634c 100644
--- a/drivers/pci/controller/dwc/pcie-designware.h
+++ b/drivers/pci/controller/dwc/pcie-designware.h
@@ -439,6 +439,7 @@ struct dw_pcie_rp {
struct pci_config_window *cfg;
bool ecam_enabled;
bool native_ecam;
+ bool link_retain;
};
struct dw_pcie_ep_ops {
--
2.34.1
^ permalink raw reply related [flat|nested] 22+ messages in thread
* [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
2026-01-09 7:21 ` [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up Krishna Chaitanya Chundru
2026-01-09 7:21 ` [PATCH 2/5] PCI: dwc: Add support for retaining link during host init Krishna Chaitanya Chundru
@ 2026-01-09 7:21 ` Krishna Chaitanya Chundru
2026-01-09 11:14 ` Konrad Dybcio
2026-02-16 14:58 ` Manivannan Sadhasivam
2026-01-09 7:21 ` [PATCH 4/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
` (2 subsequent siblings)
5 siblings, 2 replies; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-09 7:21 UTC (permalink / raw)
To: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci,
Krishna Chaitanya Chundru
The PERST# signal is used to reset PCIe devices. Currently, the driver
requests the GPIO with GPIOD_OUT_HIGH, which forces the line high
during probe. This can unintentionally assert reset early, breaking
link retention or causing unexpected device behavior.
Change the request to use GPIOD_ASIS so the driver preserves the
existing state configured by the bootloader or firmware. This allows
platforms that manage PERST# externally to maintain proper reset
sequencing.
Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
---
drivers/pci/controller/dwc/pcie-qcom.c | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
index 7b92e7a1c0d9364a9cefe1450818f9cbfc7fd3ac..9342f9c75f1c3017b55614069a7aa821a6fb8da7 100644
--- a/drivers/pci/controller/dwc/pcie-qcom.c
+++ b/drivers/pci/controller/dwc/pcie-qcom.c
@@ -1711,7 +1711,7 @@ static int qcom_pcie_parse_port(struct qcom_pcie *pcie, struct device_node *node
int ret;
reset = devm_fwnode_gpiod_get(dev, of_fwnode_handle(node),
- "reset", GPIOD_OUT_HIGH, "PERST#");
+ "reset", GPIOD_ASIS, "PERST#");
if (IS_ERR(reset))
return PTR_ERR(reset);
@@ -1772,7 +1772,7 @@ static int qcom_pcie_parse_legacy_binding(struct qcom_pcie *pcie)
if (IS_ERR(phy))
return PTR_ERR(phy);
- reset = devm_gpiod_get_optional(dev, "perst", GPIOD_OUT_HIGH);
+ reset = devm_gpiod_get_optional(dev, "perst", GPIOD_ASIS);
if (IS_ERR(reset))
return PTR_ERR(reset);
--
2.34.1
^ permalink raw reply related [flat|nested] 22+ messages in thread
* [PATCH 4/5] PCI: qcom: Add link retention support
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
` (2 preceding siblings ...)
2026-01-09 7:21 ` [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe Krishna Chaitanya Chundru
@ 2026-01-09 7:21 ` Krishna Chaitanya Chundru
2026-02-16 15:08 ` Manivannan Sadhasivam
2026-01-09 7:21 ` [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa Krishna Chaitanya Chundru
2026-01-15 2:16 ` [PATCH 0/5] PCI: qcom: Add link retention support Qiang Yu
5 siblings, 1 reply; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-09 7:21 UTC (permalink / raw)
To: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci,
Krishna Chaitanya Chundru
Some platforms keep the PCIe link active across bootloader and kernel
handoff. Reinitializing the controller and toggling PERST# in such cases
is unnecessary if driver doesn't want to do link training again.
Introduce link_retain in both qcom_pcie_cfg and qcom_pcie to
indicate when link retention is supported. During initialization, check
the LTSSM state, if the link is already in L0 or L1 idle and LTSSM is
enabled, set pp.link_retain and skip controller reset, PERST# toggling,
and other post-init steps.
If there is a devicetree property to restrict PCIe data rate and lane
width go with the normal execution instead of link retantion logic.
Configure DBI and ATU base in this scenerio, since bootloader DBI & ATU
base may differ from HLOS one. So use the DBI & ATU provided from the
devicetree.
Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
---
drivers/pci/controller/dwc/pcie-qcom.c | 50 ++++++++++++++++++++++++++++++++--
1 file changed, 47 insertions(+), 3 deletions(-)
diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
index 9342f9c75f1c3017b55614069a7aa821a6fb8da7..bdd5bdb462c5f6814c8311be96411173456b6b14 100644
--- a/drivers/pci/controller/dwc/pcie-qcom.c
+++ b/drivers/pci/controller/dwc/pcie-qcom.c
@@ -259,12 +259,14 @@ struct qcom_pcie_ops {
* @override_no_snoop: Override NO_SNOOP attribute in TLP to enable cache
* snooping
* @firmware_managed: Set if the Root Complex is firmware managed
+ * @link_retain: Set if controller supports link retain from bootloader
*/
struct qcom_pcie_cfg {
const struct qcom_pcie_ops *ops;
bool override_no_snoop;
bool firmware_managed;
bool no_l0s;
+ bool link_retain;
};
struct qcom_pcie_port {
@@ -965,6 +967,35 @@ static int qcom_pcie_get_resources_2_7_0(struct qcom_pcie *pcie)
return 0;
}
+static bool qcom_pcie_check_link_retain(struct qcom_pcie *pcie)
+{
+ u32 cap, speed, val, ltssm, width;
+ struct dw_pcie *pci = pcie->pci;
+ u8 offset;
+
+ val = readl(pcie->parf + PARF_LTSSM);
+ ltssm = val & 0x1f;
+ if ((val & LTSSM_EN) &&
+ (ltssm == DW_PCIE_LTSSM_L0 || ltssm == DW_PCIE_LTSSM_L1_IDLE)) {
+ qcom_pcie_configure_dbi_atu_base(pcie);
+
+ offset = dw_pcie_find_capability(pci, PCI_CAP_ID_EXP);
+ cap = dw_pcie_readl_dbi(pci, offset + PCI_EXP_LNKCAP);
+ speed = FIELD_GET(PCI_EXP_LNKCAP_SLS, cap);
+ width = dw_pcie_link_get_max_link_width(pci);
+
+ if (pci->max_link_speed > 0 && speed < pci->max_link_speed)
+ return false;
+
+ if (pci->num_lanes > 0 && width > pci->num_lanes)
+ return false;
+
+ return true;
+ }
+
+ return false;
+}
+
static int qcom_pcie_init_2_7_0(struct qcom_pcie *pcie)
{
struct qcom_pcie_resources_2_7_0 *res = &pcie->res.v2_7_0;
@@ -983,6 +1014,14 @@ static int qcom_pcie_init_2_7_0(struct qcom_pcie *pcie)
if (ret < 0)
goto err_disable_regulators;
+ if (pcie->cfg->link_retain) {
+ pci->pp.link_retain = qcom_pcie_check_link_retain(pcie);
+ if (pci->pp.link_retain) {
+ dev_info(dev, "Enabling link retain\n");
+ return 0;
+ }
+ }
+
ret = reset_control_assert(res->rst);
if (ret) {
dev_err(dev, "reset assert failed (%d)\n", ret);
@@ -1043,6 +1082,9 @@ static int qcom_pcie_post_init_2_7_0(struct qcom_pcie *pcie)
{
const struct qcom_pcie_cfg *pcie_cfg = pcie->cfg;
+ if (pcie->pci->pp.link_retain)
+ return 0;
+
if (pcie_cfg->override_no_snoop)
writel(WR_NO_SNOOP_OVERRIDE_EN | RD_NO_SNOOP_OVERRIDE_EN,
pcie->parf + PARF_NO_SNOOP_OVERRIDE);
@@ -1300,12 +1342,13 @@ static int qcom_pcie_host_init(struct dw_pcie_rp *pp)
struct qcom_pcie *pcie = to_qcom_pcie(pci);
int ret;
- qcom_ep_reset_assert(pcie);
-
ret = pcie->cfg->ops->init(pcie);
if (ret)
return ret;
+ if (!pp->link_retain)
+ qcom_ep_reset_assert(pcie);
+
ret = qcom_pcie_phy_power_on(pcie);
if (ret)
goto err_deinit;
@@ -1316,7 +1359,8 @@ static int qcom_pcie_host_init(struct dw_pcie_rp *pp)
goto err_disable_phy;
}
- qcom_ep_reset_deassert(pcie);
+ if (!pp->link_retain)
+ qcom_ep_reset_deassert(pcie);
if (pcie->cfg->ops->config_sid) {
ret = pcie->cfg->ops->config_sid(pcie);
--
2.34.1
^ permalink raw reply related [flat|nested] 22+ messages in thread
* [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
` (3 preceding siblings ...)
2026-01-09 7:21 ` [PATCH 4/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
@ 2026-01-09 7:21 ` Krishna Chaitanya Chundru
2026-01-09 13:09 ` Dmitry Baryshkov
2026-01-15 2:16 ` [PATCH 0/5] PCI: qcom: Add link retention support Qiang Yu
5 siblings, 1 reply; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-09 7:21 UTC (permalink / raw)
To: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci,
Krishna Chaitanya Chundru
The Hamoa platform supports keeping the PCIe link active across
bootloader and kernel handoff. To take advantage of this, introduce a
specific configuration (cfg_x1e80100) with link_retain = true and
update the device match table to use it.
Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
---
drivers/pci/controller/dwc/pcie-qcom.c | 8 +++++++-
1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
index bdd5bdb462c5f6814c8311be96411173456b6b14..975671a0dd4757074600d5a0966e94220bb18d8c 100644
--- a/drivers/pci/controller/dwc/pcie-qcom.c
+++ b/drivers/pci/controller/dwc/pcie-qcom.c
@@ -1531,6 +1531,12 @@ static const struct qcom_pcie_cfg cfg_sc8280xp = {
.no_l0s = true,
};
+static const struct qcom_pcie_cfg cfg_x1e80100 = {
+ .ops = &ops_1_21_0,
+ .no_l0s = true,
+ .link_retain = true,
+};
+
static const struct qcom_pcie_cfg cfg_fw_managed = {
.firmware_managed = true,
};
@@ -2168,7 +2174,7 @@ static const struct of_device_id qcom_pcie_match[] = {
{ .compatible = "qcom,pcie-sm8450-pcie0", .data = &cfg_1_9_0 },
{ .compatible = "qcom,pcie-sm8450-pcie1", .data = &cfg_1_9_0 },
{ .compatible = "qcom,pcie-sm8550", .data = &cfg_1_9_0 },
- { .compatible = "qcom,pcie-x1e80100", .data = &cfg_sc8280xp },
+ { .compatible = "qcom,pcie-x1e80100", .data = &cfg_x1e80100 },
{ }
};
--
2.34.1
^ permalink raw reply related [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 7:21 ` [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up Krishna Chaitanya Chundru
@ 2026-01-09 9:23 ` Abel Vesa
2026-01-09 13:08 ` Dmitry Baryshkov
1 sibling, 0 replies; 22+ messages in thread
From: Abel Vesa @ 2026-01-09 9:23 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 26-01-09 12:51:06, Krishna Chaitanya Chundru wrote:
> If the bootloader has already powered up the PCIe PHY, doing a full
> reset and waiting for it to come up again slows down boot time.
>
> Add a check for PHY status and skip the reset steps when the PHY is
> already active. In this case, only enable the required resources during
> power-on. This works alongside the existing logic that skips the init
> sequence.
>
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
Reviewed-by: Abel Vesa <abel.vesa@oss.qualcomm.com>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe
2026-01-09 7:21 ` [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe Krishna Chaitanya Chundru
@ 2026-01-09 11:14 ` Konrad Dybcio
2026-02-16 14:58 ` Manivannan Sadhasivam
1 sibling, 0 replies; 22+ messages in thread
From: Konrad Dybcio @ 2026-01-09 11:14 UTC (permalink / raw)
To: Krishna Chaitanya Chundru, Vinod Koul, Neil Armstrong,
Philipp Zabel, Jingoo Han, Manivannan Sadhasivam,
Lorenzo Pieralisi, Krzysztof Wilczyński, Rob Herring,
Bjorn Helgaas
Cc: linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 1/9/26 8:21 AM, Krishna Chaitanya Chundru wrote:
> The PERST# signal is used to reset PCIe devices. Currently, the driver
> requests the GPIO with GPIOD_OUT_HIGH, which forces the line high
> during probe. This can unintentionally assert reset early, breaking
^ de-assert, probably?
Konrad
> link retention or causing unexpected device behavior.
>
> Change the request to use GPIOD_ASIS so the driver preserves the
> existing state configured by the bootloader or firmware. This allows
> platforms that manage PERST# externally to maintain proper reset
> sequencing.
>
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> ---
> drivers/pci/controller/dwc/pcie-qcom.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
> index 7b92e7a1c0d9364a9cefe1450818f9cbfc7fd3ac..9342f9c75f1c3017b55614069a7aa821a6fb8da7 100644
> --- a/drivers/pci/controller/dwc/pcie-qcom.c
> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
> @@ -1711,7 +1711,7 @@ static int qcom_pcie_parse_port(struct qcom_pcie *pcie, struct device_node *node
> int ret;
>
> reset = devm_fwnode_gpiod_get(dev, of_fwnode_handle(node),
> - "reset", GPIOD_OUT_HIGH, "PERST#");
> + "reset", GPIOD_ASIS, "PERST#");
> if (IS_ERR(reset))
> return PTR_ERR(reset);
>
> @@ -1772,7 +1772,7 @@ static int qcom_pcie_parse_legacy_binding(struct qcom_pcie *pcie)
> if (IS_ERR(phy))
> return PTR_ERR(phy);
>
> - reset = devm_gpiod_get_optional(dev, "perst", GPIOD_OUT_HIGH);
> + reset = devm_gpiod_get_optional(dev, "perst", GPIOD_ASIS);
> if (IS_ERR(reset))
> return PTR_ERR(reset);
>
>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 7:21 ` [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up Krishna Chaitanya Chundru
2026-01-09 9:23 ` Abel Vesa
@ 2026-01-09 13:08 ` Dmitry Baryshkov
2026-01-09 13:10 ` Neil Armstrong
1 sibling, 1 reply; 22+ messages in thread
From: Dmitry Baryshkov @ 2026-01-09 13:08 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 12:51:06PM +0530, Krishna Chaitanya Chundru wrote:
> If the bootloader has already powered up the PCIe PHY, doing a full
> reset and waiting for it to come up again slows down boot time.
How big is the delay caused by it?
>
> Add a check for PHY status and skip the reset steps when the PHY is
> already active. In this case, only enable the required resources during
> power-on. This works alongside the existing logic that skips the init
> sequence.
Can we end up in a state where the bootloader has mis-setup the link? Or
the link going bad because of any glitch during the bootup?
>
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> ---
> drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++++++++++++++----------
> 1 file changed, 18 insertions(+), 10 deletions(-)
>
> diff --git a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> index 86b1b7e2da86a8675e3e48e90b782afb21cafd77..c93e613cf80b2612f0f225fa2125f78dbec1a33f 100644
> --- a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> +++ b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> @@ -3153,6 +3153,7 @@ struct qmp_pcie {
> const struct qmp_phy_cfg *cfg;
> bool tcsr_4ln_config;
> bool skip_init;
> + bool skip_reset;
>
> void __iomem *serdes;
> void __iomem *pcs;
> @@ -4537,6 +4538,9 @@ static int qmp_pcie_init(struct phy *phy)
> qphy_checkbits(pcs, cfg->regs[QPHY_START_CTRL], SERDES_START | PCS_START) &&
> qphy_checkbits(pcs, cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL], cfg->pwrdn_ctrl);
>
> + qmp->skip_reset = qmp->skip_init && !qphy_checkbits(pcs, cfg->regs[QPHY_PCS_STATUS],
It is definitely not a long-term state, there is no need to store it in
qmp_pcie struct.
> + cfg->phy_status);
> +
> if (!qmp->skip_init && !cfg->tbls.serdes_num) {
> dev_err(qmp->dev, "Init sequence not available\n");
> return -ENODATA;
> @@ -4560,13 +4564,15 @@ static int qmp_pcie_init(struct phy *phy)
> }
> }
>
> - ret = reset_control_assert(qmp->nocsr_reset);
> - if (ret) {
> - dev_err(qmp->dev, "no-csr reset assert failed\n");
> - goto err_assert_reset;
> - }
> + if (!qmp->skip_reset) {
> + ret = reset_control_assert(qmp->nocsr_reset);
> + if (ret) {
> + dev_err(qmp->dev, "no-csr reset assert failed\n");
> + goto err_assert_reset;
> + }
>
> - usleep_range(200, 300);
> + usleep_range(200, 300);
> + }
>
> if (!qmp->skip_init) {
> ret = reset_control_bulk_deassert(cfg->num_resets, qmp->resets);
> @@ -4641,10 +4647,12 @@ static int qmp_pcie_power_on(struct phy *phy)
> if (ret)
> return ret;
>
> - ret = reset_control_deassert(qmp->nocsr_reset);
> - if (ret) {
> - dev_err(qmp->dev, "no-csr reset deassert failed\n");
> - goto err_disable_pipe_clk;
> + if (!qmp->skip_reset) {
> + ret = reset_control_deassert(qmp->nocsr_reset);
> + if (ret) {
> + dev_err(qmp->dev, "no-csr reset deassert failed\n");
> + goto err_disable_pipe_clk;
> + }
> }
>
> if (qmp->skip_init)
>
> --
> 2.34.1
>
--
With best wishes
Dmitry
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa
2026-01-09 7:21 ` [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa Krishna Chaitanya Chundru
@ 2026-01-09 13:09 ` Dmitry Baryshkov
2026-01-22 8:59 ` Krishna Chaitanya Chundru
0 siblings, 1 reply; 22+ messages in thread
From: Dmitry Baryshkov @ 2026-01-09 13:09 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 12:51:10PM +0530, Krishna Chaitanya Chundru wrote:
> The Hamoa platform supports keeping the PCIe link active across
> bootloader and kernel handoff. To take advantage of this, introduce a
> specific configuration (cfg_x1e80100) with link_retain = true and
> update the device match table to use it.
Why are we enabling it only for this platform?
>
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> ---
> drivers/pci/controller/dwc/pcie-qcom.c | 8 +++++++-
> 1 file changed, 7 insertions(+), 1 deletion(-)
>
> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
> index bdd5bdb462c5f6814c8311be96411173456b6b14..975671a0dd4757074600d5a0966e94220bb18d8c 100644
> --- a/drivers/pci/controller/dwc/pcie-qcom.c
> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
> @@ -1531,6 +1531,12 @@ static const struct qcom_pcie_cfg cfg_sc8280xp = {
> .no_l0s = true,
> };
>
> +static const struct qcom_pcie_cfg cfg_x1e80100 = {
> + .ops = &ops_1_21_0,
> + .no_l0s = true,
> + .link_retain = true,
> +};
> +
> static const struct qcom_pcie_cfg cfg_fw_managed = {
> .firmware_managed = true,
> };
> @@ -2168,7 +2174,7 @@ static const struct of_device_id qcom_pcie_match[] = {
> { .compatible = "qcom,pcie-sm8450-pcie0", .data = &cfg_1_9_0 },
> { .compatible = "qcom,pcie-sm8450-pcie1", .data = &cfg_1_9_0 },
> { .compatible = "qcom,pcie-sm8550", .data = &cfg_1_9_0 },
> - { .compatible = "qcom,pcie-x1e80100", .data = &cfg_sc8280xp },
> + { .compatible = "qcom,pcie-x1e80100", .data = &cfg_x1e80100 },
> { }
> };
>
>
> --
> 2.34.1
>
--
With best wishes
Dmitry
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 13:08 ` Dmitry Baryshkov
@ 2026-01-09 13:10 ` Neil Armstrong
2026-01-09 14:03 ` Dmitry Baryshkov
0 siblings, 1 reply; 22+ messages in thread
From: Neil Armstrong @ 2026-01-09 13:10 UTC (permalink / raw)
To: Dmitry Baryshkov, Krishna Chaitanya Chundru
Cc: Vinod Koul, Philipp Zabel, Jingoo Han, Manivannan Sadhasivam,
Lorenzo Pieralisi, Krzysztof Wilczyński, Rob Herring,
Bjorn Helgaas, linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 1/9/26 14:08, Dmitry Baryshkov wrote:
> On Fri, Jan 09, 2026 at 12:51:06PM +0530, Krishna Chaitanya Chundru wrote:
>> If the bootloader has already powered up the PCIe PHY, doing a full
>> reset and waiting for it to come up again slows down boot time.
>
> How big is the delay caused by it?
>
>>
>> Add a check for PHY status and skip the reset steps when the PHY is
>> already active. In this case, only enable the required resources during
>> power-on. This works alongside the existing logic that skips the init
>> sequence.
>
> Can we end up in a state where the bootloader has mis-setup the link? Or
> the link going bad because of any glitch during the bootup?
Good question, can we add a module parameter to force a full reset of the PHY in case
the bootloader is buggy ?
>
>>
>> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
>> ---
>> drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++++++++++++++----------
>> 1 file changed, 18 insertions(+), 10 deletions(-)
>>
>> diff --git a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
>> index 86b1b7e2da86a8675e3e48e90b782afb21cafd77..c93e613cf80b2612f0f225fa2125f78dbec1a33f 100644
>> --- a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
>> +++ b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
>> @@ -3153,6 +3153,7 @@ struct qmp_pcie {
>> const struct qmp_phy_cfg *cfg;
>> bool tcsr_4ln_config;
>> bool skip_init;
>> + bool skip_reset;
>>
>> void __iomem *serdes;
>> void __iomem *pcs;
>> @@ -4537,6 +4538,9 @@ static int qmp_pcie_init(struct phy *phy)
>> qphy_checkbits(pcs, cfg->regs[QPHY_START_CTRL], SERDES_START | PCS_START) &&
>> qphy_checkbits(pcs, cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL], cfg->pwrdn_ctrl);
>>
>> + qmp->skip_reset = qmp->skip_init && !qphy_checkbits(pcs, cfg->regs[QPHY_PCS_STATUS],
>
> It is definitely not a long-term state, there is no need to store it in
> qmp_pcie struct.
>
>> + cfg->phy_status);
>> +
>> if (!qmp->skip_init && !cfg->tbls.serdes_num) {
>> dev_err(qmp->dev, "Init sequence not available\n");
>> return -ENODATA;
>> @@ -4560,13 +4564,15 @@ static int qmp_pcie_init(struct phy *phy)
>> }
>> }
>>
>> - ret = reset_control_assert(qmp->nocsr_reset);
>> - if (ret) {
>> - dev_err(qmp->dev, "no-csr reset assert failed\n");
>> - goto err_assert_reset;
>> - }
>> + if (!qmp->skip_reset) {
>> + ret = reset_control_assert(qmp->nocsr_reset);
>> + if (ret) {
>> + dev_err(qmp->dev, "no-csr reset assert failed\n");
>> + goto err_assert_reset;
>> + }
>>
>> - usleep_range(200, 300);
>> + usleep_range(200, 300);
>> + }
>>
>> if (!qmp->skip_init) {
>> ret = reset_control_bulk_deassert(cfg->num_resets, qmp->resets);
>> @@ -4641,10 +4647,12 @@ static int qmp_pcie_power_on(struct phy *phy)
>> if (ret)
>> return ret;
>>
>> - ret = reset_control_deassert(qmp->nocsr_reset);
>> - if (ret) {
>> - dev_err(qmp->dev, "no-csr reset deassert failed\n");
>> - goto err_disable_pipe_clk;
>> + if (!qmp->skip_reset) {
>> + ret = reset_control_deassert(qmp->nocsr_reset);
>> + if (ret) {
>> + dev_err(qmp->dev, "no-csr reset deassert failed\n");
>> + goto err_disable_pipe_clk;
>> + }
>> }
>>
>> if (qmp->skip_init)
>>
>> --
>> 2.34.1
>>
>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 13:10 ` Neil Armstrong
@ 2026-01-09 14:03 ` Dmitry Baryshkov
2026-01-14 9:36 ` Vinod Koul
2026-02-16 14:53 ` Manivannan Sadhasivam
0 siblings, 2 replies; 22+ messages in thread
From: Dmitry Baryshkov @ 2026-01-09 14:03 UTC (permalink / raw)
To: Neil Armstrong
Cc: Krishna Chaitanya Chundru, Vinod Koul, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 02:10:49PM +0100, Neil Armstrong wrote:
> On 1/9/26 14:08, Dmitry Baryshkov wrote:
> > On Fri, Jan 09, 2026 at 12:51:06PM +0530, Krishna Chaitanya Chundru wrote:
> > > If the bootloader has already powered up the PCIe PHY, doing a full
> > > reset and waiting for it to come up again slows down boot time.
> >
> > How big is the delay caused by it?
> >
> > >
> > > Add a check for PHY status and skip the reset steps when the PHY is
> > > already active. In this case, only enable the required resources during
> > > power-on. This works alongside the existing logic that skips the init
> > > sequence.
> >
> > Can we end up in a state where the bootloader has mis-setup the link? Or
> > the link going bad because of any glitch during the bootup?
>
> Good question, can we add a module parameter to force a full reset of the PHY in case
> the bootloader is buggy ?
I'd suggest a simpler thing: if the reset was skipped, reset the PHY in
case of an error and retry. That's also one of the reasons why I asked
for skip_reset not to be the persistent value.
>
> >
> > >
> > > Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> > > ---
> > > drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++++++++++++++----------
> > > 1 file changed, 18 insertions(+), 10 deletions(-)
> > >
> > > diff --git a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> > > index 86b1b7e2da86a8675e3e48e90b782afb21cafd77..c93e613cf80b2612f0f225fa2125f78dbec1a33f 100644
> > > --- a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> > > +++ b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> > > @@ -3153,6 +3153,7 @@ struct qmp_pcie {
> > > const struct qmp_phy_cfg *cfg;
> > > bool tcsr_4ln_config;
> > > bool skip_init;
> > > + bool skip_reset;
> > > void __iomem *serdes;
> > > void __iomem *pcs;
> > > @@ -4537,6 +4538,9 @@ static int qmp_pcie_init(struct phy *phy)
> > > qphy_checkbits(pcs, cfg->regs[QPHY_START_CTRL], SERDES_START | PCS_START) &&
> > > qphy_checkbits(pcs, cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL], cfg->pwrdn_ctrl);
> > > + qmp->skip_reset = qmp->skip_init && !qphy_checkbits(pcs, cfg->regs[QPHY_PCS_STATUS],
> >
> > It is definitely not a long-term state, there is no need to store it in
> > qmp_pcie struct.
> >
> > > + cfg->phy_status);
> > > +
> > > if (!qmp->skip_init && !cfg->tbls.serdes_num) {
> > > dev_err(qmp->dev, "Init sequence not available\n");
> > > return -ENODATA;
> > > @@ -4560,13 +4564,15 @@ static int qmp_pcie_init(struct phy *phy)
> > > }
> > > }
> > > - ret = reset_control_assert(qmp->nocsr_reset);
> > > - if (ret) {
> > > - dev_err(qmp->dev, "no-csr reset assert failed\n");
> > > - goto err_assert_reset;
> > > - }
> > > + if (!qmp->skip_reset) {
> > > + ret = reset_control_assert(qmp->nocsr_reset);
> > > + if (ret) {
> > > + dev_err(qmp->dev, "no-csr reset assert failed\n");
> > > + goto err_assert_reset;
> > > + }
> > > - usleep_range(200, 300);
> > > + usleep_range(200, 300);
> > > + }
> > > if (!qmp->skip_init) {
> > > ret = reset_control_bulk_deassert(cfg->num_resets, qmp->resets);
> > > @@ -4641,10 +4647,12 @@ static int qmp_pcie_power_on(struct phy *phy)
> > > if (ret)
> > > return ret;
> > > - ret = reset_control_deassert(qmp->nocsr_reset);
> > > - if (ret) {
> > > - dev_err(qmp->dev, "no-csr reset deassert failed\n");
> > > - goto err_disable_pipe_clk;
> > > + if (!qmp->skip_reset) {
> > > + ret = reset_control_deassert(qmp->nocsr_reset);
> > > + if (ret) {
> > > + dev_err(qmp->dev, "no-csr reset deassert failed\n");
> > > + goto err_disable_pipe_clk;
> > > + }
> > > }
> > > if (qmp->skip_init)
> > >
> > > --
> > > 2.34.1
> > >
> >
>
--
With best wishes
Dmitry
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 2/5] PCI: dwc: Add support for retaining link during host init
2026-01-09 7:21 ` [PATCH 2/5] PCI: dwc: Add support for retaining link during host init Krishna Chaitanya Chundru
@ 2026-01-09 15:53 ` Bjorn Helgaas
2026-01-12 11:29 ` Konrad Dybcio
2026-01-22 8:55 ` Krishna Chaitanya Chundru
0 siblings, 2 replies; 22+ messages in thread
From: Bjorn Helgaas @ 2026-01-09 15:53 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 12:51:07PM +0530, Krishna Chaitanya Chundru wrote:
> Some platforms keep the PCIe link up across bootloader and kernel
> handoff. In such cases, reinitializing the root complex is unnecessary
> if the DWC glue drivers wants to retain the PCIe link.
>
> Introduce a link_retain flag in struct dw_pcie_rp to indicate that
> the link should be preserved. When this flag is set by DWC glue drivers,
> skip dw_pcie_setup_rc() and only initialize MSI, avoiding redundant
> configuration steps.
It sounds like this adds an assumption that the bootloader
initialization is the same as what dw_pcie_setup_rc() would do. This
assumption also applies to future changes in dw_pcie_setup_rc().
It looks like you mention an issue like this in [PATCH 4/5]; DBI & ATU
base being different than "HLOS" (whatever that is). This sounds like
a maintenance issue keeping bootloader and kernel driver assumptions
synchronized.
Is there something in dw_pcie_setup_rc() that takes a lot of time or
forces a link retrain? You mentioned some clock and GENPD issues in
the cover letter, but I don't see the connection between those and
dw_pcie_setup_rc(). If there is a connection, please include it in
this commit log and include a code comment about why
dw_pcie_setup_rc() is being skipped.
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> ---
> drivers/pci/controller/dwc/pcie-designware-host.c | 11 ++++++++---
> drivers/pci/controller/dwc/pcie-designware.h | 1 +
> 2 files changed, 9 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/pci/controller/dwc/pcie-designware-host.c b/drivers/pci/controller/dwc/pcie-designware-host.c
> index 372207c33a857b4c98572bb1e9b61fa0080bc871..d050df3f22e9507749a8f2fedd4c24fca43fb410 100644
> --- a/drivers/pci/controller/dwc/pcie-designware-host.c
> +++ b/drivers/pci/controller/dwc/pcie-designware-host.c
> @@ -655,9 +655,14 @@ int dw_pcie_host_init(struct dw_pcie_rp *pp)
> if (ret)
> goto err_free_msi;
>
> - ret = dw_pcie_setup_rc(pp);
> - if (ret)
> - goto err_remove_edma;
> + if (!pp->link_retain) {
Use positive logic if possible (test "pp->link_retain" instead of
"!pp->link_retain").
I suspect this would be more maintainable if you identified specific
things *inside* dw_pcie_setup_rc() that need to be skipped, and you
added tests there.
> + ret = dw_pcie_setup_rc(pp);
> + if (ret)
> + goto err_remove_edma;
> + } else {
> + dw_pcie_msi_init(pp);
> + }
> +
>
> if (!dw_pcie_link_up(pci)) {
> ret = dw_pcie_start_link(pci);
> diff --git a/drivers/pci/controller/dwc/pcie-designware.h b/drivers/pci/controller/dwc/pcie-designware.h
> index 31685951a080456b8834aab2bf79a36c78f46639..8acab751b66a06e8322e027ab55dc0ecfdcf634c 100644
> --- a/drivers/pci/controller/dwc/pcie-designware.h
> +++ b/drivers/pci/controller/dwc/pcie-designware.h
> @@ -439,6 +439,7 @@ struct dw_pcie_rp {
> struct pci_config_window *cfg;
> bool ecam_enabled;
> bool native_ecam;
> + bool link_retain;
> };
>
> struct dw_pcie_ep_ops {
>
> --
> 2.34.1
>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 2/5] PCI: dwc: Add support for retaining link during host init
2026-01-09 15:53 ` Bjorn Helgaas
@ 2026-01-12 11:29 ` Konrad Dybcio
2026-01-22 8:55 ` Krishna Chaitanya Chundru
1 sibling, 0 replies; 22+ messages in thread
From: Konrad Dybcio @ 2026-01-12 11:29 UTC (permalink / raw)
To: Bjorn Helgaas, Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 1/9/26 4:53 PM, Bjorn Helgaas wrote:
> On Fri, Jan 09, 2026 at 12:51:07PM +0530, Krishna Chaitanya Chundru wrote:
>> Some platforms keep the PCIe link up across bootloader and kernel
>> handoff. In such cases, reinitializing the root complex is unnecessary
>> if the DWC glue drivers wants to retain the PCIe link.
>>
>> Introduce a link_retain flag in struct dw_pcie_rp to indicate that
>> the link should be preserved. When this flag is set by DWC glue drivers,
>> skip dw_pcie_setup_rc() and only initialize MSI, avoiding redundant
>> configuration steps.
>
> It sounds like this adds an assumption that the bootloader
> initialization is the same as what dw_pcie_setup_rc() would do. This
> assumption also applies to future changes in dw_pcie_setup_rc().
>
> It looks like you mention an issue like this in [PATCH 4/5]; DBI & ATU
> base being different than "HLOS" (whatever that is). This sounds like
FYI, "HLOS" is a Qualcomm term for "High-Level OS".. which is a very
pedantic way to say "OS"
Konrad
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 14:03 ` Dmitry Baryshkov
@ 2026-01-14 9:36 ` Vinod Koul
2026-02-16 14:53 ` Manivannan Sadhasivam
1 sibling, 0 replies; 22+ messages in thread
From: Vinod Koul @ 2026-01-14 9:36 UTC (permalink / raw)
To: Dmitry Baryshkov
Cc: Neil Armstrong, Krishna Chaitanya Chundru, Philipp Zabel,
Jingoo Han, Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 09-01-26, 16:03, Dmitry Baryshkov wrote:
> On Fri, Jan 09, 2026 at 02:10:49PM +0100, Neil Armstrong wrote:
> > On 1/9/26 14:08, Dmitry Baryshkov wrote:
> > > On Fri, Jan 09, 2026 at 12:51:06PM +0530, Krishna Chaitanya Chundru wrote:
> > > > If the bootloader has already powered up the PCIe PHY, doing a full
> > > > reset and waiting for it to come up again slows down boot time.
> > >
> > > How big is the delay caused by it?
> > >
> > > >
> > > > Add a check for PHY status and skip the reset steps when the PHY is
> > > > already active. In this case, only enable the required resources during
> > > > power-on. This works alongside the existing logic that skips the init
> > > > sequence.
> > >
> > > Can we end up in a state where the bootloader has mis-setup the link? Or
> > > the link going bad because of any glitch during the bootup?
> >
> > Good question, can we add a module parameter to force a full reset of the PHY in case
> > the bootloader is buggy ?
>
> I'd suggest a simpler thing: if the reset was skipped, reset the PHY in
> case of an error and retry. That's also one of the reasons why I asked
> for skip_reset not to be the persistent value.
That is a better suggestion. Helps skips if it is configured and way to
recover if buggy
--
~Vinod
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 0/5] PCI: qcom: Add link retention support
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
` (4 preceding siblings ...)
2026-01-09 7:21 ` [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa Krishna Chaitanya Chundru
@ 2026-01-15 2:16 ` Qiang Yu
5 siblings, 0 replies; 22+ messages in thread
From: Qiang Yu @ 2026-01-15 2:16 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 12:51:05PM +0530, Krishna Chaitanya Chundru wrote:
> This patch series introduces support for retaining the PCIe link across
> bootloader and kernel handoff on Qualcomm platforms, specifically
> X1E80100. The goal is to reduce boot time and avoid unnecessary link
> reinitialization when the link is already up.
>
> We are not enabling link retantion support for all the targets, as there
> is no guarantee that the bootloader on all targets has initialized the
> PCIe link in max supported speed. So we are enabling for hamoa & glymur
> target only for now based on the config flag.
>
> If the link is up and has link_retain is set to true in the
> ithe driver config data then enable retain logic in the controller.
>
> In phy as we already have skip init logic, the phy patch uses same
> assumption that if there is phy no csr and bootloader has done the init
> then driver can skip resetting the phy when phy status indicates it is
> up.
>
> Problem:-
> 1) As part of late init calls of clock & GENPD(for power domains) the
> framework is disabling all the unvoted resources by that time and also
> there is no sync state to keep them enabled till the probe is completed.
> Due to dependencies with regulators and phy, qcom pcie probe is happening
> after late init which is causing the resources(clocks & power domains) to
> be off which causes the link to go down. To avoid this we need to use these
> two kernel command line arguments (clk_ignore_unused & pd_ignore_unused)
> to skip disabling clocks and gendp power domains as part of late init
> for initial version. Once it is resolved we can avoid those kernel command
> line arguments.
>
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
Tested on Hamoa QCP and Glymur CRD, so
Tested-by: Qiang Yu <qiang.yu@oss.qualcomm.com>
> ---
> Krishna Chaitanya Chundru (5):
> phy: qcom: qmp-pcie: Skip PHY reset if already up
> PCI: dwc: Add support for retaining link during host init
> PCI: qcom: Keep PERST# GPIO state as-is during probe
> PCI: qcom: Add link retention support
> PCI: qcom: enable Link retain logic for Hamoa
>
> drivers/pci/controller/dwc/pcie-designware-host.c | 11 ++--
> drivers/pci/controller/dwc/pcie-designware.h | 1 +
> drivers/pci/controller/dwc/pcie-qcom.c | 62 ++++++++++++++++++++---
> drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++----
> 4 files changed, 83 insertions(+), 19 deletions(-)
> ---
> base-commit: fc065cadc7ed048bedbb23cb6b7c4475198f431c
> change-id: 20251001-link_retain-f181307947e4
>
> Best regards,
> --
> Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
>
>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 2/5] PCI: dwc: Add support for retaining link during host init
2026-01-09 15:53 ` Bjorn Helgaas
2026-01-12 11:29 ` Konrad Dybcio
@ 2026-01-22 8:55 ` Krishna Chaitanya Chundru
1 sibling, 0 replies; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-22 8:55 UTC (permalink / raw)
To: Bjorn Helgaas
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 1/9/2026 9:23 PM, Bjorn Helgaas wrote:
> On Fri, Jan 09, 2026 at 12:51:07PM +0530, Krishna Chaitanya Chundru wrote:
>> Some platforms keep the PCIe link up across bootloader and kernel
>> handoff. In such cases, reinitializing the root complex is unnecessary
>> if the DWC glue drivers wants to retain the PCIe link.
>>
>> Introduce a link_retain flag in struct dw_pcie_rp to indicate that
>> the link should be preserved. When this flag is set by DWC glue drivers,
>> skip dw_pcie_setup_rc() and only initialize MSI, avoiding redundant
>> configuration steps.
> It sounds like this adds an assumption that the bootloader
> initialization is the same as what dw_pcie_setup_rc() would do. This
> assumption also applies to future changes in dw_pcie_setup_rc().
Yes the bootloader is expected to do everything what dw_pcie_setup_r()
does.
> It looks like you mention an issue like this in [PATCH 4/5]; DBI & ATU
> base being different than "HLOS" (whatever that is). This sounds like
> a maintenance issue keeping bootloader and kernel driver assumptions
> synchronized.
As the devicetree changes already pointing to different address from the
boatloader,
I was trying use this method. As changing device tree properties now
might not
be good, but no harm in doing so. I can skip this and make device tree
changes.
> Is there something in dw_pcie_setup_rc() that takes a lot of time or
> forces a link retrain?
I don't think it might not take much time as it is few register writes,
Just doesn't
want to do redundant register writes which are costly in general.
> You mentioned some clock and GENPD issues in
> the cover letter, but I don't see the connection between those and
> dw_pcie_setup_rc(). If there is a connection, please include it in
> this commit log and include a code comment about why
> dw_pcie_setup_rc() is being skipped.
The clock and GENPD issues have no direct relation ship with
dw_pcie_setup_r(). we are skipping them as they are redundant. I will
add a comment in next series on this. - Krishna Chaitanya.
>> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
>> ---
>> drivers/pci/controller/dwc/pcie-designware-host.c | 11 ++++++++---
>> drivers/pci/controller/dwc/pcie-designware.h | 1 +
>> 2 files changed, 9 insertions(+), 3 deletions(-)
>>
>> diff --git a/drivers/pci/controller/dwc/pcie-designware-host.c b/drivers/pci/controller/dwc/pcie-designware-host.c
>> index 372207c33a857b4c98572bb1e9b61fa0080bc871..d050df3f22e9507749a8f2fedd4c24fca43fb410 100644
>> --- a/drivers/pci/controller/dwc/pcie-designware-host.c
>> +++ b/drivers/pci/controller/dwc/pcie-designware-host.c
>> @@ -655,9 +655,14 @@ int dw_pcie_host_init(struct dw_pcie_rp *pp)
>> if (ret)
>> goto err_free_msi;
>>
>> - ret = dw_pcie_setup_rc(pp);
>> - if (ret)
>> - goto err_remove_edma;
>> + if (!pp->link_retain) {
> Use positive logic if possible (test "pp->link_retain" instead of
> "!pp->link_retain").
>
> I suspect this would be more maintainable if you identified specific
> things *inside* dw_pcie_setup_rc() that need to be skipped, and you
> added tests there.
>
>> + ret = dw_pcie_setup_rc(pp);
>> + if (ret)
>> + goto err_remove_edma;
>> + } else {
>> + dw_pcie_msi_init(pp);
>> + }
>> +
>>
>> if (!dw_pcie_link_up(pci)) {
>> ret = dw_pcie_start_link(pci);
>> diff --git a/drivers/pci/controller/dwc/pcie-designware.h b/drivers/pci/controller/dwc/pcie-designware.h
>> index 31685951a080456b8834aab2bf79a36c78f46639..8acab751b66a06e8322e027ab55dc0ecfdcf634c 100644
>> --- a/drivers/pci/controller/dwc/pcie-designware.h
>> +++ b/drivers/pci/controller/dwc/pcie-designware.h
>> @@ -439,6 +439,7 @@ struct dw_pcie_rp {
>> struct pci_config_window *cfg;
>> bool ecam_enabled;
>> bool native_ecam;
>> + bool link_retain;
>> };
>>
>> struct dw_pcie_ep_ops {
>>
>> --
>> 2.34.1
>>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa
2026-01-09 13:09 ` Dmitry Baryshkov
@ 2026-01-22 8:59 ` Krishna Chaitanya Chundru
0 siblings, 0 replies; 22+ messages in thread
From: Krishna Chaitanya Chundru @ 2026-01-22 8:59 UTC (permalink / raw)
To: Dmitry Baryshkov
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Manivannan Sadhasivam, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 1/9/2026 6:39 PM, Dmitry Baryshkov wrote:
> On Fri, Jan 09, 2026 at 12:51:10PM +0530, Krishna Chaitanya Chundru wrote:
>> The Hamoa platform supports keeping the PCIe link active across
>> bootloader and kernel handoff. To take advantage of this, introduce a
>> specific configuration (cfg_x1e80100) with link_retain = true and
>> update the device match table to use it.
> Why are we enabling it only for this platform?
As mentioned in the cover letter we are not trusting every platform boot
loaders,
which have initialized the controller to max speed. That is we are
restricting them to
only for this platform.
- Krishna Chaitanya.
>> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
>> ---
>> drivers/pci/controller/dwc/pcie-qcom.c | 8 +++++++-
>> 1 file changed, 7 insertions(+), 1 deletion(-)
>>
>> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
>> index bdd5bdb462c5f6814c8311be96411173456b6b14..975671a0dd4757074600d5a0966e94220bb18d8c 100644
>> --- a/drivers/pci/controller/dwc/pcie-qcom.c
>> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
>> @@ -1531,6 +1531,12 @@ static const struct qcom_pcie_cfg cfg_sc8280xp = {
>> .no_l0s = true,
>> };
>>
>> +static const struct qcom_pcie_cfg cfg_x1e80100 = {
>> + .ops = &ops_1_21_0,
>> + .no_l0s = true,
>> + .link_retain = true,
>> +};
>> +
>> static const struct qcom_pcie_cfg cfg_fw_managed = {
>> .firmware_managed = true,
>> };
>> @@ -2168,7 +2174,7 @@ static const struct of_device_id qcom_pcie_match[] = {
>> { .compatible = "qcom,pcie-sm8450-pcie0", .data = &cfg_1_9_0 },
>> { .compatible = "qcom,pcie-sm8450-pcie1", .data = &cfg_1_9_0 },
>> { .compatible = "qcom,pcie-sm8550", .data = &cfg_1_9_0 },
>> - { .compatible = "qcom,pcie-x1e80100", .data = &cfg_sc8280xp },
>> + { .compatible = "qcom,pcie-x1e80100", .data = &cfg_x1e80100 },
>> { }
>> };
>>
>>
>> --
>> 2.34.1
>>
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-01-09 14:03 ` Dmitry Baryshkov
2026-01-14 9:36 ` Vinod Koul
@ 2026-02-16 14:53 ` Manivannan Sadhasivam
2026-02-16 14:56 ` Konrad Dybcio
1 sibling, 1 reply; 22+ messages in thread
From: Manivannan Sadhasivam @ 2026-02-16 14:53 UTC (permalink / raw)
To: Dmitry Baryshkov
Cc: Neil Armstrong, Krishna Chaitanya Chundru, Vinod Koul,
Philipp Zabel, Jingoo Han, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 04:03:37PM +0200, Dmitry Baryshkov wrote:
> On Fri, Jan 09, 2026 at 02:10:49PM +0100, Neil Armstrong wrote:
> > On 1/9/26 14:08, Dmitry Baryshkov wrote:
> > > On Fri, Jan 09, 2026 at 12:51:06PM +0530, Krishna Chaitanya Chundru wrote:
> > > > If the bootloader has already powered up the PCIe PHY, doing a full
> > > > reset and waiting for it to come up again slows down boot time.
> > >
> > > How big is the delay caused by it?
> > >
> > > >
> > > > Add a check for PHY status and skip the reset steps when the PHY is
> > > > already active. In this case, only enable the required resources during
> > > > power-on. This works alongside the existing logic that skips the init
> > > > sequence.
> > >
> > > Can we end up in a state where the bootloader has mis-setup the link? Or
> > > the link going bad because of any glitch during the bootup?
> >
> > Good question, can we add a module parameter to force a full reset of the PHY in case
> > the bootloader is buggy ?
>
> I'd suggest a simpler thing: if the reset was skipped, reset the PHY in
> case of an error and retry. That's also one of the reasons why I asked
> for skip_reset not to be the persistent value.
>
I'm not sure what value would resetting the PHY provide in the case of failure.
As per this patch, skip_reset is only going to be set for platforms where
bootloader has already configured the PHY. So in the case of PHY link failure,
simply resetting the PHY won't help IMO as the PHY register contents are going
to be presistent due to nocsr_reset.
- Mani
> >
> > >
> > > >
> > > > Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> > > > ---
> > > > drivers/phy/qualcomm/phy-qcom-qmp-pcie.c | 28 ++++++++++++++++++----------
> > > > 1 file changed, 18 insertions(+), 10 deletions(-)
> > > >
> > > > diff --git a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> > > > index 86b1b7e2da86a8675e3e48e90b782afb21cafd77..c93e613cf80b2612f0f225fa2125f78dbec1a33f 100644
> > > > --- a/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> > > > +++ b/drivers/phy/qualcomm/phy-qcom-qmp-pcie.c
> > > > @@ -3153,6 +3153,7 @@ struct qmp_pcie {
> > > > const struct qmp_phy_cfg *cfg;
> > > > bool tcsr_4ln_config;
> > > > bool skip_init;
> > > > + bool skip_reset;
> > > > void __iomem *serdes;
> > > > void __iomem *pcs;
> > > > @@ -4537,6 +4538,9 @@ static int qmp_pcie_init(struct phy *phy)
> > > > qphy_checkbits(pcs, cfg->regs[QPHY_START_CTRL], SERDES_START | PCS_START) &&
> > > > qphy_checkbits(pcs, cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL], cfg->pwrdn_ctrl);
> > > > + qmp->skip_reset = qmp->skip_init && !qphy_checkbits(pcs, cfg->regs[QPHY_PCS_STATUS],
> > >
> > > It is definitely not a long-term state, there is no need to store it in
> > > qmp_pcie struct.
> > >
> > > > + cfg->phy_status);
> > > > +
> > > > if (!qmp->skip_init && !cfg->tbls.serdes_num) {
> > > > dev_err(qmp->dev, "Init sequence not available\n");
> > > > return -ENODATA;
> > > > @@ -4560,13 +4564,15 @@ static int qmp_pcie_init(struct phy *phy)
> > > > }
> > > > }
> > > > - ret = reset_control_assert(qmp->nocsr_reset);
> > > > - if (ret) {
> > > > - dev_err(qmp->dev, "no-csr reset assert failed\n");
> > > > - goto err_assert_reset;
> > > > - }
> > > > + if (!qmp->skip_reset) {
> > > > + ret = reset_control_assert(qmp->nocsr_reset);
> > > > + if (ret) {
> > > > + dev_err(qmp->dev, "no-csr reset assert failed\n");
> > > > + goto err_assert_reset;
> > > > + }
> > > > - usleep_range(200, 300);
> > > > + usleep_range(200, 300);
> > > > + }
> > > > if (!qmp->skip_init) {
> > > > ret = reset_control_bulk_deassert(cfg->num_resets, qmp->resets);
> > > > @@ -4641,10 +4647,12 @@ static int qmp_pcie_power_on(struct phy *phy)
> > > > if (ret)
> > > > return ret;
> > > > - ret = reset_control_deassert(qmp->nocsr_reset);
> > > > - if (ret) {
> > > > - dev_err(qmp->dev, "no-csr reset deassert failed\n");
> > > > - goto err_disable_pipe_clk;
> > > > + if (!qmp->skip_reset) {
> > > > + ret = reset_control_deassert(qmp->nocsr_reset);
> > > > + if (ret) {
> > > > + dev_err(qmp->dev, "no-csr reset deassert failed\n");
> > > > + goto err_disable_pipe_clk;
> > > > + }
> > > > }
> > > > if (qmp->skip_init)
> > > >
> > > > --
> > > > 2.34.1
> > > >
> > >
> >
>
> --
> With best wishes
> Dmitry
--
மணிவண்ணன் சதாசிவம்
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up
2026-02-16 14:53 ` Manivannan Sadhasivam
@ 2026-02-16 14:56 ` Konrad Dybcio
0 siblings, 0 replies; 22+ messages in thread
From: Konrad Dybcio @ 2026-02-16 14:56 UTC (permalink / raw)
To: Manivannan Sadhasivam, Dmitry Baryshkov
Cc: Neil Armstrong, Krishna Chaitanya Chundru, Vinod Koul,
Philipp Zabel, Jingoo Han, Lorenzo Pieralisi,
Krzysztof Wilczyński, Rob Herring, Bjorn Helgaas,
linux-arm-msm, linux-phy, linux-kernel, linux-pci
On 2/16/26 3:53 PM, Manivannan Sadhasivam wrote:
> On Fri, Jan 09, 2026 at 04:03:37PM +0200, Dmitry Baryshkov wrote:
>> On Fri, Jan 09, 2026 at 02:10:49PM +0100, Neil Armstrong wrote:
>>> On 1/9/26 14:08, Dmitry Baryshkov wrote:
>>>> On Fri, Jan 09, 2026 at 12:51:06PM +0530, Krishna Chaitanya Chundru wrote:
>>>>> If the bootloader has already powered up the PCIe PHY, doing a full
>>>>> reset and waiting for it to come up again slows down boot time.
>>>>
>>>> How big is the delay caused by it?
>>>>
>>>>>
>>>>> Add a check for PHY status and skip the reset steps when the PHY is
>>>>> already active. In this case, only enable the required resources during
>>>>> power-on. This works alongside the existing logic that skips the init
>>>>> sequence.
>>>>
>>>> Can we end up in a state where the bootloader has mis-setup the link? Or
>>>> the link going bad because of any glitch during the bootup?
>>>
>>> Good question, can we add a module parameter to force a full reset of the PHY in case
>>> the bootloader is buggy ?
>>
>> I'd suggest a simpler thing: if the reset was skipped, reset the PHY in
>> case of an error and retry. That's also one of the reasons why I asked
>> for skip_reset not to be the persistent value.
>>
>
> I'm not sure what value would resetting the PHY provide in the case of failure.
> As per this patch, skip_reset is only going to be set for platforms where
> bootloader has already configured the PHY. So in the case of PHY link failure,
> simply resetting the PHY won't help IMO as the PHY register contents are going
> to be presistent due to nocsr_reset.
We can pull the not-nocsr_reset though?
Konrad
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe
2026-01-09 7:21 ` [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe Krishna Chaitanya Chundru
2026-01-09 11:14 ` Konrad Dybcio
@ 2026-02-16 14:58 ` Manivannan Sadhasivam
1 sibling, 0 replies; 22+ messages in thread
From: Manivannan Sadhasivam @ 2026-02-16 14:58 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Lorenzo Pieralisi, Krzysztof Wilczyński, Rob Herring,
Bjorn Helgaas, linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 12:51:08PM +0530, Krishna Chaitanya Chundru wrote:
> The PERST# signal is used to reset PCIe devices. Currently, the driver
> requests the GPIO with GPIOD_OUT_HIGH, which forces the line high
> during probe. This can unintentionally assert reset early, breaking
> link retention or causing unexpected device behavior.
>
There is no way asserting PERST# is going to cause 'unexpected device behavior'.
> Change the request to use GPIOD_ASIS so the driver preserves the
> existing state configured by the bootloader or firmware. This allows
> platforms that manage PERST# externally to maintain proper reset
> sequencing.
>
You should also mention the fact that the driver asserts PERST# during the start
of qcom_pcie_host_init(). So requesting PERST# with GPIOD_OUT_HIGH is redundant
anyway.
- Mani
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> ---
> drivers/pci/controller/dwc/pcie-qcom.c | 4 ++--
> 1 file changed, 2 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
> index 7b92e7a1c0d9364a9cefe1450818f9cbfc7fd3ac..9342f9c75f1c3017b55614069a7aa821a6fb8da7 100644
> --- a/drivers/pci/controller/dwc/pcie-qcom.c
> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
> @@ -1711,7 +1711,7 @@ static int qcom_pcie_parse_port(struct qcom_pcie *pcie, struct device_node *node
> int ret;
>
> reset = devm_fwnode_gpiod_get(dev, of_fwnode_handle(node),
> - "reset", GPIOD_OUT_HIGH, "PERST#");
> + "reset", GPIOD_ASIS, "PERST#");
> if (IS_ERR(reset))
> return PTR_ERR(reset);
>
> @@ -1772,7 +1772,7 @@ static int qcom_pcie_parse_legacy_binding(struct qcom_pcie *pcie)
> if (IS_ERR(phy))
> return PTR_ERR(phy);
>
> - reset = devm_gpiod_get_optional(dev, "perst", GPIOD_OUT_HIGH);
> + reset = devm_gpiod_get_optional(dev, "perst", GPIOD_ASIS);
> if (IS_ERR(reset))
> return PTR_ERR(reset);
>
>
> --
> 2.34.1
>
--
மணிவண்ணன் சதாசிவம்
^ permalink raw reply [flat|nested] 22+ messages in thread
* Re: [PATCH 4/5] PCI: qcom: Add link retention support
2026-01-09 7:21 ` [PATCH 4/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
@ 2026-02-16 15:08 ` Manivannan Sadhasivam
0 siblings, 0 replies; 22+ messages in thread
From: Manivannan Sadhasivam @ 2026-02-16 15:08 UTC (permalink / raw)
To: Krishna Chaitanya Chundru
Cc: Vinod Koul, Neil Armstrong, Philipp Zabel, Jingoo Han,
Lorenzo Pieralisi, Krzysztof Wilczyński, Rob Herring,
Bjorn Helgaas, linux-arm-msm, linux-phy, linux-kernel, linux-pci
On Fri, Jan 09, 2026 at 12:51:09PM +0530, Krishna Chaitanya Chundru wrote:
> Some platforms keep the PCIe link active across bootloader and kernel
> handoff. Reinitializing the controller and toggling PERST# in such cases
> is unnecessary if driver doesn't want to do link training again.
>
> Introduce link_retain in both qcom_pcie_cfg and qcom_pcie to
> indicate when link retention is supported. During initialization, check
> the LTSSM state, if the link is already in L0 or L1 idle and LTSSM is
> enabled, set pp.link_retain and skip controller reset, PERST# toggling,
> and other post-init steps.
>
> If there is a devicetree property to restrict PCIe data rate and lane
> width go with the normal execution instead of link retantion logic.
>
Mention the properties here and also make it clear that the link will not be
retained if the values do not match bootloader programmed ones.
> Configure DBI and ATU base in this scenerio, since bootloader DBI & ATU
> base may differ from HLOS one. So use the DBI & ATU provided from the
> devicetree.
>
> Signed-off-by: Krishna Chaitanya Chundru <krishna.chundru@oss.qualcomm.com>
> ---
> drivers/pci/controller/dwc/pcie-qcom.c | 50 ++++++++++++++++++++++++++++++++--
> 1 file changed, 47 insertions(+), 3 deletions(-)
>
> diff --git a/drivers/pci/controller/dwc/pcie-qcom.c b/drivers/pci/controller/dwc/pcie-qcom.c
> index 9342f9c75f1c3017b55614069a7aa821a6fb8da7..bdd5bdb462c5f6814c8311be96411173456b6b14 100644
> --- a/drivers/pci/controller/dwc/pcie-qcom.c
> +++ b/drivers/pci/controller/dwc/pcie-qcom.c
> @@ -259,12 +259,14 @@ struct qcom_pcie_ops {
> * @override_no_snoop: Override NO_SNOOP attribute in TLP to enable cache
> * snooping
> * @firmware_managed: Set if the Root Complex is firmware managed
> + * @link_retain: Set if controller supports link retain from bootloader
s/"link retain"/"retaining link"
> */
> struct qcom_pcie_cfg {
> const struct qcom_pcie_ops *ops;
> bool override_no_snoop;
> bool firmware_managed;
> bool no_l0s;
> + bool link_retain;
> };
>
> struct qcom_pcie_port {
> @@ -965,6 +967,35 @@ static int qcom_pcie_get_resources_2_7_0(struct qcom_pcie *pcie)
> return 0;
> }
>
> +static bool qcom_pcie_check_link_retain(struct qcom_pcie *pcie)
> +{
> + u32 cap, speed, val, ltssm, width;
> + struct dw_pcie *pci = pcie->pci;
> + u8 offset;
> +
> + val = readl(pcie->parf + PARF_LTSSM);
> + ltssm = val & 0x1f;
> + if ((val & LTSSM_EN) &&
> + (ltssm == DW_PCIE_LTSSM_L0 || ltssm == DW_PCIE_LTSSM_L1_IDLE)) {
> + qcom_pcie_configure_dbi_atu_base(pcie);
> +
> + offset = dw_pcie_find_capability(pci, PCI_CAP_ID_EXP);
> + cap = dw_pcie_readl_dbi(pci, offset + PCI_EXP_LNKCAP);
> + speed = FIELD_GET(PCI_EXP_LNKCAP_SLS, cap);
> + width = dw_pcie_link_get_max_link_width(pci);
> +
> + if (pci->max_link_speed > 0 && speed < pci->max_link_speed)
> + return false;
> +
> + if (pci->num_lanes > 0 && width > pci->num_lanes)
> + return false;
IIUC, these checks are in place to override the link retention if the users want
to change the lane/width count than what was already programmed by the
bootloader.
If so, please add comment on top of this helper to make it explicit.
> +
> + return true;
> + }
> +
> + return false;
> +}
> +
> static int qcom_pcie_init_2_7_0(struct qcom_pcie *pcie)
> {
> struct qcom_pcie_resources_2_7_0 *res = &pcie->res.v2_7_0;
> @@ -983,6 +1014,14 @@ static int qcom_pcie_init_2_7_0(struct qcom_pcie *pcie)
> if (ret < 0)
> goto err_disable_regulators;
>
> + if (pcie->cfg->link_retain) {
> + pci->pp.link_retain = qcom_pcie_check_link_retain(pcie);
> + if (pci->pp.link_retain) {
> + dev_info(dev, "Enabling link retain\n");
"Retaining PCIe link"
- Mani
--
மணிவண்ணன் சதாசிவம்
^ permalink raw reply [flat|nested] 22+ messages in thread
end of thread, other threads:[~2026-02-16 15:08 UTC | newest]
Thread overview: 22+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-01-09 7:21 [PATCH 0/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
2026-01-09 7:21 ` [PATCH 1/5] phy: qcom: qmp-pcie: Skip PHY reset if already up Krishna Chaitanya Chundru
2026-01-09 9:23 ` Abel Vesa
2026-01-09 13:08 ` Dmitry Baryshkov
2026-01-09 13:10 ` Neil Armstrong
2026-01-09 14:03 ` Dmitry Baryshkov
2026-01-14 9:36 ` Vinod Koul
2026-02-16 14:53 ` Manivannan Sadhasivam
2026-02-16 14:56 ` Konrad Dybcio
2026-01-09 7:21 ` [PATCH 2/5] PCI: dwc: Add support for retaining link during host init Krishna Chaitanya Chundru
2026-01-09 15:53 ` Bjorn Helgaas
2026-01-12 11:29 ` Konrad Dybcio
2026-01-22 8:55 ` Krishna Chaitanya Chundru
2026-01-09 7:21 ` [PATCH 3/5] PCI: qcom: Keep PERST# GPIO state as-is during probe Krishna Chaitanya Chundru
2026-01-09 11:14 ` Konrad Dybcio
2026-02-16 14:58 ` Manivannan Sadhasivam
2026-01-09 7:21 ` [PATCH 4/5] PCI: qcom: Add link retention support Krishna Chaitanya Chundru
2026-02-16 15:08 ` Manivannan Sadhasivam
2026-01-09 7:21 ` [PATCH 5/5] PCI: qcom: enable Link retain logic for Hamoa Krishna Chaitanya Chundru
2026-01-09 13:09 ` Dmitry Baryshkov
2026-01-22 8:59 ` Krishna Chaitanya Chundru
2026-01-15 2:16 ` [PATCH 0/5] PCI: qcom: Add link retention support Qiang Yu
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox