^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Copyright (c) 2012-2014,2017 The Linux Foundation. All rights reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) * Copyright (c) 2018-2020, Linaro Limited
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) #include <linux/clk.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) #include <linux/delay.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) #include <linux/err.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <linux/io.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/of.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/phy/phy.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/platform_device.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/regulator/consumer.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <linux/reset.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18) #include <linux/slab.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20) #define PHY_CTRL0 0x6C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) #define PHY_CTRL1 0x70
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) #define PHY_CTRL2 0x74
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) #define PHY_CTRL4 0x7C
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) /* PHY_CTRL bits */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) #define REF_PHY_EN BIT(0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) #define LANE0_PWR_ON BIT(2)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) #define SWI_PCS_CLK_SEL BIT(4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) #define TST_PWR_DOWN BIT(4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) #define PHY_RESET BIT(7)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) #define NUM_BULK_CLKS 3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) #define NUM_BULK_REGS 2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35) struct ssphy_priv {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) void __iomem *base;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) struct device *dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38) struct reset_control *reset_com;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) struct reset_control *reset_phy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) struct regulator_bulk_data regs[NUM_BULK_REGS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) struct clk_bulk_data clks[NUM_BULK_CLKS];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) enum phy_mode mode;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) static inline void qcom_ssphy_updatel(void __iomem *addr, u32 mask, u32 val)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) writel((readl(addr) & ~mask) | val, addr);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50) static int qcom_ssphy_do_reset(struct ssphy_priv *priv)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) if (!priv->reset_com) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55) qcom_ssphy_updatel(priv->base + PHY_CTRL1, PHY_RESET,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) PHY_RESET);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) usleep_range(10, 20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) qcom_ssphy_updatel(priv->base + PHY_CTRL1, PHY_RESET, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59) } else {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) ret = reset_control_assert(priv->reset_com);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) dev_err(priv->dev, "Failed to assert reset com\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) ret = reset_control_assert(priv->reset_phy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) dev_err(priv->dev, "Failed to assert reset phy\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) usleep_range(10, 20);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) ret = reset_control_deassert(priv->reset_com);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) dev_err(priv->dev, "Failed to deassert reset com\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) ret = reset_control_deassert(priv->reset_phy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) dev_err(priv->dev, "Failed to deassert reset phy\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) static int qcom_ssphy_power_on(struct phy *phy)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) struct ssphy_priv *priv = phy_get_drvdata(phy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) ret = regulator_bulk_enable(NUM_BULK_REGS, priv->regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) ret = clk_bulk_prepare_enable(NUM_BULK_CLKS, priv->clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) goto err_disable_regulator;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) ret = qcom_ssphy_do_reset(priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) goto err_disable_clock;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) writeb(SWI_PCS_CLK_SEL, priv->base + PHY_CTRL0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) qcom_ssphy_updatel(priv->base + PHY_CTRL4, LANE0_PWR_ON, LANE0_PWR_ON);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) qcom_ssphy_updatel(priv->base + PHY_CTRL2, REF_PHY_EN, REF_PHY_EN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) qcom_ssphy_updatel(priv->base + PHY_CTRL4, TST_PWR_DOWN, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) err_disable_clock:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) clk_bulk_disable_unprepare(NUM_BULK_CLKS, priv->clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) err_disable_regulator:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) regulator_bulk_disable(NUM_BULK_REGS, priv->regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) static int qcom_ssphy_power_off(struct phy *phy)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) struct ssphy_priv *priv = phy_get_drvdata(phy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) qcom_ssphy_updatel(priv->base + PHY_CTRL4, LANE0_PWR_ON, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) qcom_ssphy_updatel(priv->base + PHY_CTRL2, REF_PHY_EN, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) qcom_ssphy_updatel(priv->base + PHY_CTRL4, TST_PWR_DOWN, TST_PWR_DOWN);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) clk_bulk_disable_unprepare(NUM_BULK_CLKS, priv->clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) regulator_bulk_disable(NUM_BULK_REGS, priv->regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) static int qcom_ssphy_init_clock(struct ssphy_priv *priv)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) priv->clks[0].id = "ref";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) priv->clks[1].id = "ahb";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) priv->clks[2].id = "pipe";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) return devm_clk_bulk_get(priv->dev, NUM_BULK_CLKS, priv->clks);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) static int qcom_ssphy_init_regulator(struct ssphy_priv *priv)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) priv->regs[0].supply = "vdd";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) priv->regs[1].supply = "vdda1p8";
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) ret = devm_regulator_bulk_get(priv->dev, NUM_BULK_REGS, priv->regs);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) if (ret) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) if (ret != -EPROBE_DEFER)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) dev_err(priv->dev, "Failed to get regulators\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) static int qcom_ssphy_init_reset(struct ssphy_priv *priv)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) priv->reset_com = devm_reset_control_get_optional_exclusive(priv->dev, "com");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) if (IS_ERR(priv->reset_com)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) dev_err(priv->dev, "Failed to get reset control com\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) return PTR_ERR(priv->reset_com);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) if (priv->reset_com) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) /* if reset_com is present, reset_phy is no longer optional */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) priv->reset_phy = devm_reset_control_get_exclusive(priv->dev, "phy");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) if (IS_ERR(priv->reset_phy)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) dev_err(priv->dev, "Failed to get reset control phy\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) return PTR_ERR(priv->reset_phy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) static const struct phy_ops qcom_ssphy_ops = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) .power_off = qcom_ssphy_power_off,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) .power_on = qcom_ssphy_power_on,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) .owner = THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) static int qcom_ssphy_probe(struct platform_device *pdev)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) struct device *dev = &pdev->dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) struct phy_provider *provider;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) struct ssphy_priv *priv;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) struct phy *phy;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) priv = devm_kzalloc(dev, sizeof(struct ssphy_priv), GFP_KERNEL);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) if (!priv)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) return -ENOMEM;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) priv->dev = dev;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) priv->mode = PHY_MODE_INVALID;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) priv->base = devm_platform_ioremap_resource(pdev, 0);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) if (IS_ERR(priv->base))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) return PTR_ERR(priv->base);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) ret = qcom_ssphy_init_clock(priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) ret = qcom_ssphy_init_reset(priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) ret = qcom_ssphy_init_regulator(priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) if (ret)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) phy = devm_phy_create(dev, dev->of_node, &qcom_ssphy_ops);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) if (IS_ERR(phy)) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) dev_err(dev, "Failed to create the SS phy\n");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) return PTR_ERR(phy);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) phy_set_drvdata(phy, priv);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) provider = devm_of_phy_provider_register(dev, of_phy_simple_xlate);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) return PTR_ERR_OR_ZERO(provider);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) static const struct of_device_id qcom_ssphy_match[] = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) { .compatible = "qcom,usb-ss-28nm-phy", },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) { },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) MODULE_DEVICE_TABLE(of, qcom_ssphy_match);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) static struct platform_driver qcom_ssphy_driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) .probe = qcom_ssphy_probe,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) .driver = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) .name = "qcom-usb-ssphy",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) .of_match_table = qcom_ssphy_match,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) },
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) module_platform_driver(qcom_ssphy_driver);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) MODULE_DESCRIPTION("Qualcomm SuperSpeed USB PHY driver");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) MODULE_LICENSE("GPL v2");