Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

PCI: meson: Report that link is up while in ASPM L0s and L1 states

Previously meson_pcie_link_up() only returned true if the link was in the
L0 state. This was incorrect because hardware autonomously manages
transitions between L0, L0s, and L1 while both components on the link stay
in D0. Those states should all be treated as "link is active".

Returning false when the device was in L0s or L1 broke config accesses
because dw_pcie_other_conf_map_bus() fails if the link is down, which
caused errors like this:

meson-pcie fc000000.pcie: error: wait linkup timeout
pci 0000:01:00.0: BAR 0: error updating (0xfc700004 != 0xffffffff)

Remove the LTSSM state check, timeout, speed check, and error message from
meson_pcie_link_up(), the dw_pcie_ops.link_up() method, so it is a simple
boolean check of whether the link is active. Timeouts and error messages
are handled at a higher level, e.g., dw_pcie_wait_for_link().

Fixes: 9c0ef6d34fdb ("PCI: amlogic: Add the Amlogic Meson PCIe controller driver")
Reported-by: Linnaea Lavia <linnaea-von-lavia@live.com>
Closes: https://lore.kernel.org/r/DM4PR05MB102707B8CDF84D776C39F22F2C7F0A@DM4PR05MB10270.namprd05.prod.outlook.com
[bhelgaas: squash removal of unused WAIT_LINKUP_TIMEOUT by
Martin Blumenstingl <martin.blumenstingl@googlemail.com>:
https://patch.msgid.link/20260105125625.239497-1-martin.blumenstingl@googlemail.com]
Signed-off-by: Bjorn Helgaas <bhelgaas@google.com>
Tested-by: Linnaea Lavia <linnaea-von-lavia@live.com>
Tested-by: Neil Armstrong <neil.armstrong@linaro.org> # on BananaPi M2S
Reviewed-by: Neil Armstrong <neil.armstrong@linaro.org>
Cc: stable@vger.kernel.org
Link: https://patch.msgid.link/20251103221930.1831376-1-helgaas@kernel.org
Link: https://patch.msgid.link/20260105125625.239497-1-martin.blumenstingl@googlemail.com

+3 -34
+3 -34
drivers/pci/controller/dwc/pci-meson.c
··· 37 #define PCIE_CFG_STATUS17 0x44 38 #define PM_CURRENT_STATE(x) (((x) >> 7) & 0x1) 39 40 - #define WAIT_LINKUP_TIMEOUT 4000 41 #define PORT_CLK_RATE 100000000UL 42 #define MAX_PAYLOAD_SIZE 256 43 #define MAX_READ_REQ_SIZE 256 ··· 349 static bool meson_pcie_link_up(struct dw_pcie *pci) 350 { 351 struct meson_pcie *mp = to_meson_pcie(pci); 352 - struct device *dev = pci->dev; 353 - u32 speed_okay = 0; 354 - u32 cnt = 0; 355 - u32 state12, state17, smlh_up, ltssm_up, rdlh_up; 356 357 - do { 358 - state12 = meson_cfg_readl(mp, PCIE_CFG_STATUS12); 359 - state17 = meson_cfg_readl(mp, PCIE_CFG_STATUS17); 360 - smlh_up = IS_SMLH_LINK_UP(state12); 361 - rdlh_up = IS_RDLH_LINK_UP(state12); 362 - ltssm_up = IS_LTSSM_UP(state12); 363 - 364 - if (PM_CURRENT_STATE(state17) < PCIE_GEN3) 365 - speed_okay = 1; 366 - 367 - if (smlh_up) 368 - dev_dbg(dev, "smlh_link_up is on\n"); 369 - if (rdlh_up) 370 - dev_dbg(dev, "rdlh_link_up is on\n"); 371 - if (ltssm_up) 372 - dev_dbg(dev, "ltssm_up is on\n"); 373 - if (speed_okay) 374 - dev_dbg(dev, "speed_okay\n"); 375 - 376 - if (smlh_up && rdlh_up && ltssm_up && speed_okay) 377 - return true; 378 - 379 - cnt++; 380 - 381 - udelay(10); 382 - } while (cnt < WAIT_LINKUP_TIMEOUT); 383 - 384 - dev_err(dev, "error: wait linkup timeout\n"); 385 - return false; 386 } 387 388 static int meson_pcie_host_init(struct dw_pcie_rp *pp)
··· 37 #define PCIE_CFG_STATUS17 0x44 38 #define PM_CURRENT_STATE(x) (((x) >> 7) & 0x1) 39 40 #define PORT_CLK_RATE 100000000UL 41 #define MAX_PAYLOAD_SIZE 256 42 #define MAX_READ_REQ_SIZE 256 ··· 350 static bool meson_pcie_link_up(struct dw_pcie *pci) 351 { 352 struct meson_pcie *mp = to_meson_pcie(pci); 353 + u32 state12; 354 355 + state12 = meson_cfg_readl(mp, PCIE_CFG_STATUS12); 356 + return IS_SMLH_LINK_UP(state12) && IS_RDLH_LINK_UP(state12); 357 } 358 359 static int meson_pcie_host_init(struct dw_pcie_rp *pp)