mirror of
https://github.com/LibreELEC/LibreELEC.tv
synced 2025-09-24 19:46:01 +07:00
172 lines
6.3 KiB
Diff
172 lines
6.3 KiB
Diff
From 6b6748ccc444c2128195fda4430846c885c6c5e8 Mon Sep 17 00:00:00 2001
|
|
From: Cristian Ciocaltea <cristian.ciocaltea@collabora.com>
|
|
Date: Mon, 7 Jul 2025 23:23:52 +0300
|
|
Subject: [PATCH 091/113] FROMLIST(v4): phy: rockchip: samsung-hdptx: Switch to
|
|
driver specific HDMI config
|
|
|
|
In preparation to support the FRL operation mode which gets configured
|
|
via the lanes and rate per lane tuple, switch to a driver specific
|
|
struct for configuring the link rate and bpc.
|
|
|
|
This simplifies and optimizes the implementation by allowing implicit
|
|
switches between TMDS and FRL rates, without requiring additional checks
|
|
of the active PHY mode followed by recalculations of the link rate when
|
|
operating in FRL mode.
|
|
|
|
Signed-off-by: Cristian Ciocaltea <cristian.ciocaltea@collabora.com>
|
|
---
|
|
.../phy/rockchip/phy-rockchip-samsung-hdptx.c | 44 +++++++++++--------
|
|
1 file changed, 25 insertions(+), 19 deletions(-)
|
|
|
|
diff --git a/drivers/phy/rockchip/phy-rockchip-samsung-hdptx.c b/drivers/phy/rockchip/phy-rockchip-samsung-hdptx.c
|
|
index 4195387108d8..a44614bc73e9 100644
|
|
--- a/drivers/phy/rockchip/phy-rockchip-samsung-hdptx.c
|
|
+++ b/drivers/phy/rockchip/phy-rockchip-samsung-hdptx.c
|
|
@@ -387,6 +387,11 @@ struct rk_hdptx_phy_cfg {
|
|
unsigned int phy_ids[MAX_HDPTX_PHY_NUM];
|
|
};
|
|
|
|
+struct rk_hdptx_hdmi_cfg {
|
|
+ unsigned long long rate;
|
|
+ unsigned int bpc;
|
|
+};
|
|
+
|
|
struct rk_hdptx_phy {
|
|
struct device *dev;
|
|
struct regmap *regmap;
|
|
@@ -394,7 +399,7 @@ struct rk_hdptx_phy {
|
|
|
|
int phy_id;
|
|
struct phy *phy;
|
|
- struct phy_configure_opts_hdmi hdmi_cfg;
|
|
+ struct rk_hdptx_hdmi_cfg hdmi_cfg;
|
|
struct clk_bulk_data *clks;
|
|
int nr_clks;
|
|
struct reset_control_bulk_data rsts[RST_MAX];
|
|
@@ -965,19 +970,19 @@ static int rk_hdptx_tmds_ropll_cmn_config(struct rk_hdptx_phy *hdptx)
|
|
struct ropll_config rc = {0};
|
|
int i;
|
|
|
|
- if (!hdptx->hdmi_cfg.tmds_char_rate)
|
|
+ if (!hdptx->hdmi_cfg.rate)
|
|
return 0;
|
|
|
|
for (i = 0; i < ARRAY_SIZE(rk_hdptx_tmds_ropll_cfg); i++)
|
|
- if (hdptx->hdmi_cfg.tmds_char_rate == rk_hdptx_tmds_ropll_cfg[i].rate) {
|
|
+ if (hdptx->hdmi_cfg.rate == rk_hdptx_tmds_ropll_cfg[i].rate) {
|
|
cfg = &rk_hdptx_tmds_ropll_cfg[i];
|
|
break;
|
|
}
|
|
|
|
if (!cfg) {
|
|
- if (!rk_hdptx_phy_clk_pll_calc(hdptx->hdmi_cfg.tmds_char_rate, &rc)) {
|
|
+ if (!rk_hdptx_phy_clk_pll_calc(hdptx->hdmi_cfg.rate, &rc)) {
|
|
dev_err(hdptx->dev, "%s cannot find pll cfg for rate=%llu\n",
|
|
- __func__, hdptx->hdmi_cfg.tmds_char_rate);
|
|
+ __func__, hdptx->hdmi_cfg.rate);
|
|
return -EINVAL;
|
|
}
|
|
|
|
@@ -985,7 +990,7 @@ static int rk_hdptx_tmds_ropll_cmn_config(struct rk_hdptx_phy *hdptx)
|
|
}
|
|
|
|
dev_dbg(hdptx->dev, "%s rate=%llu mdiv=%u sdiv=%u sdm_en=%u k_sign=%u k=%u lc=%u\n",
|
|
- __func__, hdptx->hdmi_cfg.tmds_char_rate, cfg->pms_mdiv, cfg->pms_sdiv + 1,
|
|
+ __func__, hdptx->hdmi_cfg.rate, cfg->pms_mdiv, cfg->pms_sdiv + 1,
|
|
cfg->sdm_en, cfg->sdm_num_sign, cfg->sdm_num, cfg->sdm_deno);
|
|
|
|
rk_hdptx_pre_power_up(hdptx);
|
|
@@ -1034,7 +1039,7 @@ static int rk_hdptx_tmds_ropll_mode_config(struct rk_hdptx_phy *hdptx)
|
|
|
|
regmap_write(hdptx->regmap, LNTOP_REG(0200), 0x06);
|
|
|
|
- if (hdptx->hdmi_cfg.tmds_char_rate > HDMI14_MAX_RATE) {
|
|
+ if (hdptx->hdmi_cfg.rate > HDMI14_MAX_RATE) {
|
|
/* For 1/40 bitrate clk */
|
|
rk_hdptx_multi_reg_write(hdptx, rk_hdptx_tmds_lntop_highbr_seq);
|
|
} else {
|
|
@@ -1405,19 +1410,19 @@ static int rk_hdptx_phy_power_on(struct phy *phy)
|
|
int ret, lane;
|
|
|
|
if (mode != PHY_MODE_DP) {
|
|
- if (!hdptx->hdmi_cfg.tmds_char_rate) {
|
|
+ if (!hdptx->hdmi_cfg.rate) {
|
|
/*
|
|
* FIXME: Temporary workaround to setup TMDS char rate
|
|
* from the RK DW HDMI QP bridge driver.
|
|
* Will be removed as soon the switch to the HDMI PHY
|
|
* configuration API has been completed on both ends.
|
|
*/
|
|
- hdptx->hdmi_cfg.tmds_char_rate = phy_get_bus_width(hdptx->phy) & 0xfffffff;
|
|
- hdptx->hdmi_cfg.tmds_char_rate *= 100;
|
|
+ hdptx->hdmi_cfg.rate = phy_get_bus_width(hdptx->phy) & 0xfffffff;
|
|
+ hdptx->hdmi_cfg.rate *= 100;
|
|
}
|
|
|
|
dev_dbg(hdptx->dev, "%s rate=%llu bpc=%u\n", __func__,
|
|
- hdptx->hdmi_cfg.tmds_char_rate, hdptx->hdmi_cfg.bpc);
|
|
+ hdptx->hdmi_cfg.rate, hdptx->hdmi_cfg.bpc);
|
|
}
|
|
|
|
ret = rk_hdptx_phy_consumer_get(hdptx);
|
|
@@ -1764,12 +1769,13 @@ static int rk_hdptx_phy_configure(struct phy *phy, union phy_configure_opts *opt
|
|
if (ret) {
|
|
dev_err(hdptx->dev, "invalid hdmi params for phy configure\n");
|
|
} else {
|
|
- hdptx->hdmi_cfg = opts->hdmi;
|
|
+ hdptx->hdmi_cfg.rate = opts->hdmi.tmds_char_rate;
|
|
+ hdptx->hdmi_cfg.bpc = opts->hdmi.bpc;
|
|
hdptx->restrict_rate_change = true;
|
|
}
|
|
|
|
dev_dbg(hdptx->dev, "%s rate=%llu bpc=%u\n", __func__,
|
|
- hdptx->hdmi_cfg.tmds_char_rate, hdptx->hdmi_cfg.bpc);
|
|
+ hdptx->hdmi_cfg.rate, hdptx->hdmi_cfg.bpc);
|
|
return ret;
|
|
}
|
|
|
|
@@ -1949,7 +1955,7 @@ static long rk_hdptx_phy_clk_round_rate(struct clk_hw *hw, unsigned long rate,
|
|
* To be dropped as soon as the RK DW HDMI QP bridge driver
|
|
* switches to make use of phy_configure().
|
|
*/
|
|
- if (!hdptx->restrict_rate_change && rate != hdptx->hdmi_cfg.tmds_char_rate) {
|
|
+ if (!hdptx->restrict_rate_change && rate != hdptx->hdmi_cfg.rate) {
|
|
struct phy_configure_opts_hdmi hdmi = {
|
|
.tmds_char_rate = rate,
|
|
};
|
|
@@ -1958,7 +1964,7 @@ static long rk_hdptx_phy_clk_round_rate(struct clk_hw *hw, unsigned long rate,
|
|
if (ret)
|
|
return ret;
|
|
|
|
- hdptx->hdmi_cfg = hdmi;
|
|
+ hdptx->hdmi_cfg.rate = rate;
|
|
}
|
|
|
|
/*
|
|
@@ -1966,7 +1972,7 @@ static long rk_hdptx_phy_clk_round_rate(struct clk_hw *hw, unsigned long rate,
|
|
* hence ensure rk_hdptx_phy_clk_set_rate() won't be invoked with
|
|
* a different rate argument.
|
|
*/
|
|
- return DIV_ROUND_CLOSEST_ULL(hdptx->hdmi_cfg.tmds_char_rate * 8, hdptx->hdmi_cfg.bpc);
|
|
+ return DIV_ROUND_CLOSEST_ULL(hdptx->hdmi_cfg.rate * 8, hdptx->hdmi_cfg.bpc);
|
|
}
|
|
|
|
static int rk_hdptx_phy_clk_set_rate(struct clk_hw *hw, unsigned long rate,
|
|
@@ -1976,10 +1982,10 @@ static int rk_hdptx_phy_clk_set_rate(struct clk_hw *hw, unsigned long rate,
|
|
unsigned long long tmds_rate = DIV_ROUND_CLOSEST_ULL(rate * hdptx->hdmi_cfg.bpc, 8);
|
|
|
|
/* Revert any unlikely TMDS char rate change since round_rate() */
|
|
- if (hdptx->hdmi_cfg.tmds_char_rate != tmds_rate) {
|
|
+ if (hdptx->hdmi_cfg.rate != tmds_rate) {
|
|
dev_warn(hdptx->dev, "Reverting unexpected rate change from %llu to %llu\n",
|
|
- tmds_rate, hdptx->hdmi_cfg.tmds_char_rate);
|
|
- hdptx->hdmi_cfg.tmds_char_rate = tmds_rate;
|
|
+ tmds_rate, hdptx->hdmi_cfg.rate);
|
|
+ hdptx->hdmi_cfg.rate = tmds_rate;
|
|
}
|
|
|
|
/*
|
|
--
|
|
2.34.1
|
|
|