]> www.infradead.org Git - users/hch/misc.git/commitdiff
PCI: mediatek-gen3: Implement sys clock ready time setting
authorAngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com>
Thu, 3 Jul 2025 12:08:45 +0000 (14:08 +0200)
committerManivannan Sadhasivam <mani@kernel.org>
Tue, 19 Aug 2025 14:35:51 +0000 (20:05 +0530)
In preparation to add support for the PCI-Express Gen3 controller
found in newer MediaTek SoCs, such as the Dimensity 9400 MT6991
and the MT8196 Chromebook SoC, add the definition for the PCIE
Resource Control register and a new sys_clk_rdy_time_us variable
in platform data.

If sys_clk_rdy_time_us is found (> 0), set the new value in the
aforementioned register only after configuring the controller to
RC mode, as this may otherwise be reset.

Overriding the register defaults for SYS_CLK_RDY_TIME allows to
work around sys_clk_rdy signal glitching in MT6991 and MT8196.

Signed-off-by: AngeloGioacchino Del Regno <angelogioacchino.delregno@collabora.com>
[mani: used FIELD_MODIFY() to simplify mask and update]
Signed-off-by: Manivannan Sadhasivam <mani@kernel.org>
Link: https://patch.msgid.link/20250703120847.121826-2-angelogioacchino.delregno@collabora.com
drivers/pci/controller/pcie-mediatek-gen3.c

index 97147f43e41c58162c0b843f21a9caa0e6ebc268..aa7bd22b144c62d86d7d78d848acdbd4772f6da2 100644 (file)
 #define PCIE_MSI_SET_ADDR_HI_BASE      0xc80
 #define PCIE_MSI_SET_ADDR_HI_OFFSET    0x04
 
+#define PCIE_RESOURCE_CTRL_REG         0xd2c
+#define PCIE_RSRC_SYS_CLK_RDY_TIME_MASK        GENMASK(7, 0)
+
 #define PCIE_ICMD_PM_REG               0x198
 #define PCIE_TURN_OFF_LINK             BIT(4)
 
@@ -149,6 +152,7 @@ enum mtk_gen3_pcie_flags {
  * struct mtk_gen3_pcie_pdata - differentiate between host generations
  * @power_up: pcie power_up callback
  * @phy_resets: phy reset lines SoC data.
+ * @sys_clk_rdy_time_us: System clock ready time override (microseconds)
  * @flags: pcie device flags.
  */
 struct mtk_gen3_pcie_pdata {
@@ -157,6 +161,7 @@ struct mtk_gen3_pcie_pdata {
                const char *id[MAX_NUM_PHY_RESETS];
                int num_resets;
        } phy_resets;
+       u8 sys_clk_rdy_time_us;
        u32 flags;
 };
 
@@ -435,6 +440,14 @@ static int mtk_pcie_startup_port(struct mtk_gen3_pcie *pcie)
                writel_relaxed(val, pcie->base + PCIE_CONF_LINK2_CTL_STS);
        }
 
+       /* If parameter is present, adjust SYS_CLK_RDY_TIME to avoid glitching */
+       if (pcie->soc->sys_clk_rdy_time_us) {
+               val = readl_relaxed(pcie->base + PCIE_RESOURCE_CTRL_REG);
+               FIELD_MODIFY(PCIE_RSRC_SYS_CLK_RDY_TIME_MASK, &val,
+                            pcie->soc->sys_clk_rdy_time_us);
+               writel_relaxed(val, pcie->base + PCIE_RESOURCE_CTRL_REG);
+       }
+
        /* Set class code */
        val = readl_relaxed(pcie->base + PCIE_PCI_IDS_1);
        val &= ~GENMASK(31, 8);