Add `qmp_phy_usbc_type` enum and a `type` field in `qmp_usbc` to
distinguish between USB and DP PHYs.

- Introduce `qmp_phy_usbc_type` enum with USB and DP types.
- Update device match table to associate compatible strings with type
  and config.
- Wrap existing USB-specific logic with type checks to prepare for
  future DP support.

No functional changes and serves as a preparatory step for adding DP PHY
support.

Signed-off-by: Xiangxu Yin <[email protected]>
---
 drivers/phy/qualcomm/phy-qcom-qmp-usbc.c | 195 ++++++++++++++++++++-----------
 1 file changed, 126 insertions(+), 69 deletions(-)

diff --git a/drivers/phy/qualcomm/phy-qcom-qmp-usbc.c 
b/drivers/phy/qualcomm/phy-qcom-qmp-usbc.c
index 
078752dbc66f9b9844c003e7755fff6466ea1d6c..647e2f54b744bf099ea667e672c606dd7aef3bcf
 100644
--- a/drivers/phy/qualcomm/phy-qcom-qmp-usbc.c
+++ b/drivers/phy/qualcomm/phy-qcom-qmp-usbc.c
@@ -286,6 +286,16 @@ static const struct qmp_phy_init_tbl 
qcm2290_usb3_pcs_tbl[] = {
        QMP_PHY_INIT_CFG(QPHY_V3_PCS_RX_SIGDET_LVL, 0x88),
 };
 
+enum qmp_phy_usbc_type {
+       QMP_PHY_USBC_USB,
+       QMP_PHY_USBC_DP,
+};
+
+struct qmp_phy_cfg {
+       int type;
+       const void *cfg;
+};
+
 struct qmp_usbc_usb_offsets {
        u16 serdes;
        u16 pcs;
@@ -454,23 +464,40 @@ static const struct qmp_phy_usb_cfg sdm660_usb3phy_cfg = {
        .regs                   = qmp_v3_usb3phy_regs_layout_qcm2290,
 };
 
+static const struct qmp_phy_cfg msm8998_phy_usb3_cfg = {
+       .type = QMP_PHY_USBC_USB,
+       .cfg = &msm8998_usb3phy_cfg,
+};
+
+static const struct qmp_phy_cfg qcm2290_phy_usb3_cfg = {
+       .type = QMP_PHY_USBC_USB,
+       .cfg = &qcm2290_usb3phy_cfg,
+};
+
+static const struct qmp_phy_cfg sdm660_phy_usb3_cfg = {
+       .type = QMP_PHY_USBC_USB,
+       .cfg = &sdm660_usb3phy_cfg,
+};
+
 #define to_usb_cfg(x) ((struct qmp_phy_usb_cfg *)((x)->cfg))
 #define to_usb_layout(x) ((struct qmp_phy_usb_layout *)((x)->layout))
 
 static int qmp_usbc_generic_init(struct phy *phy)
 {
        struct qmp_usbc *qmp = phy_get_drvdata(phy);
-       struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
-       struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
        int num_vregs;
-       unsigned int reg_pwr_dn;
        u32 val;
        int ret;
+       unsigned int reg_pwr_dn;
 
-       num_vregs = cfg->num_vregs;
-       reg_pwr_dn = cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL];
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
 
-       ret = regulator_bulk_enable(cfg->num_vregs, qmp->vregs);
+               num_vregs = cfg->num_vregs;
+               reg_pwr_dn = cfg->regs[QPHY_PCS_POWER_DOWN_CONTROL];
+       }
+
+       ret = regulator_bulk_enable(num_vregs, qmp->vregs);
        if (ret) {
                dev_err(qmp->dev, "failed to enable regulators, err=%d\n", ret);
                return ret;
@@ -497,8 +524,12 @@ static int qmp_usbc_generic_init(struct phy *phy)
        if (qmp->orientation == TYPEC_ORIENTATION_REVERSE)
                val |= SW_PORTSELECT_VAL;
 
-       qphy_setbits(layout->pcs, reg_pwr_dn, SW_PWRDN);
-       writel(val, layout->pcs_misc);
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
+
+               qphy_setbits(layout->pcs, reg_pwr_dn, SW_PWRDN);
+               writel(val, layout->pcs_misc);
+       }
 
        return 0;
 
@@ -513,13 +544,18 @@ static int qmp_usbc_generic_init(struct phy *phy)
 static int qmp_usbc_generic_exit(struct phy *phy)
 {
        struct qmp_usbc *qmp = phy_get_drvdata(phy);
-       struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
+       int num_vregs;
 
        reset_control_bulk_assert(qmp->num_resets, qmp->resets);
 
        clk_bulk_disable_unprepare(qmp->num_clks, qmp->clks);
 
-       regulator_bulk_disable(cfg->num_vregs, qmp->vregs);
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
+
+               num_vregs = cfg->num_vregs;
+       }
+       regulator_bulk_disable(num_vregs, qmp->vregs);
 
        return 0;
 }
@@ -650,7 +686,7 @@ static const struct phy_ops qmp_usbc_usb_phy_ops = {
 
 static void qmp_usbc_enable_autonomous_mode(struct qmp_usbc *qmp)
 {
-       const struct qmp_phy_usb_cfg *cfg = qmp->cfg;
+       const struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
        struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
        void __iomem *pcs = layout->pcs;
        u32 intr_mask;
@@ -698,18 +734,20 @@ static void qmp_usbc_disable_autonomous_mode(struct 
qmp_usbc *qmp)
 static int __maybe_unused qmp_usbc_runtime_suspend(struct device *dev)
 {
        struct qmp_usbc *qmp = dev_get_drvdata(dev);
-       struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
-
-       dev_vdbg(dev, "Suspending QMP phy, mode:%d\n", layout->mode);
 
        if (!qmp->phy->init_count) {
                dev_vdbg(dev, "PHY not initialized, bailing out\n");
                return 0;
        }
 
-       qmp_usbc_enable_autonomous_mode(qmp);
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
+
+               dev_vdbg(dev, "Suspending QMP phy, mode:%d\n", layout->mode);
+               qmp_usbc_enable_autonomous_mode(qmp);
+               clk_disable_unprepare(layout->pipe_clk);
+       }
 
-       clk_disable_unprepare(layout->pipe_clk);
        clk_bulk_disable_unprepare(qmp->num_clks, qmp->clks);
 
        return 0;
@@ -718,11 +756,8 @@ static int __maybe_unused qmp_usbc_runtime_suspend(struct 
device *dev)
 static int __maybe_unused qmp_usbc_runtime_resume(struct device *dev)
 {
        struct qmp_usbc *qmp = dev_get_drvdata(dev);
-       struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
        int ret = 0;
 
-       dev_vdbg(dev, "Resuming QMP phy, mode:%d\n", layout->mode);
-
        if (!qmp->phy->init_count) {
                dev_vdbg(dev, "PHY not initialized, bailing out\n");
                return 0;
@@ -732,14 +767,19 @@ static int __maybe_unused qmp_usbc_runtime_resume(struct 
device *dev)
        if (ret)
                return ret;
 
-       ret = clk_prepare_enable(layout->pipe_clk);
-       if (ret) {
-               dev_err(dev, "pipe_clk enable failed, err=%d\n", ret);
-               clk_bulk_disable_unprepare(qmp->num_clks, qmp->clks);
-               return ret;
-       }
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               struct qmp_phy_usb_layout *layout = to_usb_layout(qmp);
+
+               dev_vdbg(dev, "Resuming QMP phy, mode:%d\n", layout->mode);
+               ret = clk_prepare_enable(layout->pipe_clk);
+               if (ret) {
+                       dev_err(dev, "pipe_clk enable failed, err=%d\n", ret);
+                       clk_bulk_disable_unprepare(qmp->num_clks, qmp->clks);
+                       return ret;
+               }
 
-       qmp_usbc_disable_autonomous_mode(qmp);
+               qmp_usbc_disable_autonomous_mode(qmp);
+       }
 
        return 0;
 }
@@ -751,20 +791,28 @@ static const struct dev_pm_ops qmp_usbc_pm_ops = {
 
 static int qmp_usbc_vreg_init(struct qmp_usbc *qmp)
 {
-       struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
        struct device *dev = qmp->dev;
-       int i;
+       int ret, i;
 
-       int num = cfg->num_vregs;
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               struct qmp_phy_usb_cfg *cfg = to_usb_cfg(qmp);
+               int num = cfg->num_vregs;
 
-       qmp->vregs = devm_kcalloc(dev, num, sizeof(*qmp->vregs), GFP_KERNEL);
-       if (!qmp->vregs)
-               return -ENOMEM;
+               qmp->vregs = devm_kcalloc(dev, num, sizeof(*qmp->vregs), 
GFP_KERNEL);
+               if (!qmp->vregs)
+                       return -ENOMEM;
 
-       for (i = 0; i < num; i++)
-               qmp->vregs[i].supply = cfg->vreg_list[i];
+               for (i = 0; i < num; i++)
+                       qmp->vregs[i].supply = cfg->vreg_list[i];
 
-       return devm_regulator_bulk_get(dev, num, qmp->vregs);
+               ret = devm_regulator_bulk_get(dev, num, qmp->vregs);
+               if (ret) {
+                       dev_err(dev, "failed at devm_regulator_bulk_get\n");
+                       return ret;
+               }
+       }
+
+       return 0;
 }
 
 static int qmp_usbc_reset_init(struct qmp_usbc *qmp,
@@ -1061,6 +1109,7 @@ static int qmp_usbc_probe(struct platform_device *pdev)
        struct phy_provider *phy_provider;
        struct device_node *np;
        struct qmp_usbc *qmp;
+       const struct qmp_phy_cfg *data_cfg;
        int ret;
 
        qmp = devm_kzalloc(dev, sizeof(*qmp), GFP_KERNEL);
@@ -1072,39 +1121,45 @@ static int qmp_usbc_probe(struct platform_device *pdev)
 
        qmp->orientation = TYPEC_ORIENTATION_NORMAL;
 
-       qmp->cfg = of_device_get_match_data(dev);
-       if (!qmp->cfg)
+       data_cfg = of_device_get_match_data(dev);
+       if (!data_cfg)
                return -EINVAL;
 
        mutex_init(&qmp->phy_mutex);
 
+       qmp->type = data_cfg->type;
+       qmp->cfg = data_cfg->cfg;
+
        ret = qmp_usbc_vreg_init(qmp);
        if (ret)
                return ret;
 
-       qmp->layout = devm_kzalloc(dev, sizeof(struct qmp_phy_usb_layout), 
GFP_KERNEL);
-       if (!qmp->layout)
-               return -ENOMEM;
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               qmp->layout = devm_kzalloc(dev, sizeof(struct 
qmp_phy_usb_layout), GFP_KERNEL);
+               if (!qmp->layout)
+                       return -ENOMEM;
+
+               ret = qmp_usbc_parse_vls_clamp(qmp);
+               if (ret)
+                       return ret;
+
+               /* Check for legacy binding with child node. */
+               np = of_get_child_by_name(dev->of_node, "phy");
+               if (np) {
+                       ret = qmp_usbc_parse_usb_dt_legacy(qmp, np);
+               } else {
+                       np = of_node_get(dev->of_node);
+                       ret = qmp_usbc_parse_usb_dt(qmp);
+               }
+
+               if (ret)
+                       goto err_node_put;
+       }
 
        ret = qmp_usbc_typec_switch_register(qmp);
        if (ret)
                return ret;
 
-       ret = qmp_usbc_parse_vls_clamp(qmp);
-       if (ret)
-               return ret;
-
-       /* Check for legacy binding with child node. */
-       np = of_get_child_by_name(dev->of_node, "phy");
-       if (np) {
-               ret = qmp_usbc_parse_usb_dt_legacy(qmp, np);
-       } else {
-               np = of_node_get(dev->of_node);
-               ret = qmp_usbc_parse_usb_dt(qmp);
-       }
-       if (ret)
-               goto err_node_put;
-
        pm_runtime_set_active(dev);
        ret = devm_pm_runtime_enable(dev);
        if (ret)
@@ -1115,15 +1170,17 @@ static int qmp_usbc_probe(struct platform_device *pdev)
         */
        pm_runtime_forbid(dev);
 
-       ret = phy_pipe_clk_register(qmp, np);
-       if (ret)
-               goto err_node_put;
-
-       qmp->phy = devm_phy_create(dev, np, &qmp_usbc_usb_phy_ops);
-       if (IS_ERR(qmp->phy)) {
-               ret = PTR_ERR(qmp->phy);
-               dev_err(dev, "failed to create PHY: %d\n", ret);
-               goto err_node_put;
+       if (qmp->type == QMP_PHY_USBC_USB) {
+               ret = phy_pipe_clk_register(qmp, np);
+               if (ret)
+                       goto err_node_put;
+
+               qmp->phy = devm_phy_create(dev, np, &qmp_usbc_usb_phy_ops);
+               if (IS_ERR(qmp->phy)) {
+                       ret = PTR_ERR(qmp->phy);
+                       dev_err(dev, "failed to create PHY: %d\n", ret);
+                       goto err_node_put;
+               }
        }
 
        phy_set_drvdata(qmp->phy, qmp);
@@ -1142,19 +1199,19 @@ static int qmp_usbc_probe(struct platform_device *pdev)
 static const struct of_device_id qmp_usbc_of_match_table[] = {
        {
                .compatible = "qcom,msm8998-qmp-usb3-phy",
-               .data = &msm8998_usb3phy_cfg,
+               .data =  &msm8998_phy_usb3_cfg,
        }, {
                .compatible = "qcom,qcm2290-qmp-usb3-phy",
-               .data = &qcm2290_usb3phy_cfg,
+               .data = &qcm2290_phy_usb3_cfg,
        }, {
                .compatible = "qcom,qcs615-qmp-usb3-phy",
-               .data = &qcm2290_usb3phy_cfg,
+               .data = &qcm2290_phy_usb3_cfg,
        }, {
                .compatible = "qcom,sdm660-qmp-usb3-phy",
-               .data = &sdm660_usb3phy_cfg,
+               .data =  &sdm660_phy_usb3_cfg,
        }, {
                .compatible = "qcom,sm6115-qmp-usb3-phy",
-               .data = &qcm2290_usb3phy_cfg,
+               .data =  &qcm2290_phy_usb3_cfg,
        },
        { },
 };

-- 
2.34.1

Reply via email to