From e38cbb75248a4027389c8a3d0bbd27bb760ba992 Mon Sep 17 00:00:00 2001 From: Pengpeng Hou Date: Sat, 4 Jul 2026 11:49:46 +0800 Subject: ASoC: codecs: lpass-rx-macro: Propagate regcache_sync() errors regcache_sync() can fail while replaying cached register state. The RX macro MCLK helper and runtime resume path currently ignore that failure and report success. Propagate the error from the MCLK helper users and from runtime resume. If runtime resume fails after enabling clocks, restore cache-only/dirty state and unwind the clocks acquired by the resume path. Signed-off-by: Pengpeng Hou Link: https://patch.msgid.link/20260704034946.20369-1-pengpeng@iscas.ac.cn Signed-off-by: Mark Brown --- sound/soc/codecs/lpass-rx-macro.c | 31 ++++++++++++++++++++++--------- 1 file changed, 22 insertions(+), 9 deletions(-) diff --git a/sound/soc/codecs/lpass-rx-macro.c b/sound/soc/codecs/lpass-rx-macro.c index 6233aa9f5bc6..550fc76109c6 100644 --- a/sound/soc/codecs/lpass-rx-macro.c +++ b/sound/soc/codecs/lpass-rx-macro.c @@ -2030,9 +2030,10 @@ static struct snd_soc_dai_driver rx_macro_dai[] = { }, }; -static void rx_macro_mclk_enable(struct rx_macro *rx, bool mclk_enable) +static int rx_macro_mclk_enable(struct rx_macro *rx, bool mclk_enable) { struct regmap *regmap = rx->regmap; + int ret; if (mclk_enable) { if (rx->rx_mclk_users == 0) { @@ -2047,14 +2048,16 @@ static void rx_macro_mclk_enable(struct rx_macro *rx, bool mclk_enable) CDC_RX_FS_MCLK_CNT_EN_MASK, CDC_RX_FS_MCLK_CNT_ENABLE); regcache_mark_dirty(regmap); - regcache_sync(regmap); + ret = regcache_sync(regmap); + if (ret) + return ret; } rx->rx_mclk_users++; } else { if (rx->rx_mclk_users <= 0) { dev_err(rx->dev, "%s: clock already disabled\n", __func__); rx->rx_mclk_users = 0; - return; + return 0; } rx->rx_mclk_users--; if (rx->rx_mclk_users == 0) { @@ -2068,6 +2071,8 @@ static void rx_macro_mclk_enable(struct rx_macro *rx, bool mclk_enable) CDC_RX_CLK_MCLK2_EN_MASK, 0x0); } } + + return 0; } static int rx_macro_mclk_event(struct snd_soc_dapm_widget *w, @@ -2079,11 +2084,9 @@ static int rx_macro_mclk_event(struct snd_soc_dapm_widget *w, switch (event) { case SND_SOC_DAPM_PRE_PMU: - rx_macro_mclk_enable(rx, true); - break; + return rx_macro_mclk_enable(rx, true); case SND_SOC_DAPM_POST_PMD: - rx_macro_mclk_enable(rx, false); - break; + return rx_macro_mclk_enable(rx, false); default: dev_err(component->dev, "%s: invalid DAPM event %d\n", __func__, event); ret = -EINVAL; @@ -3677,7 +3680,11 @@ static int swclk_gate_enable(struct clk_hw *hw) return ret; } - rx_macro_mclk_enable(rx, true); + ret = rx_macro_mclk_enable(rx, true); + if (ret) { + clk_disable_unprepare(rx->mclk); + return ret; + } regmap_update_bits(rx->regmap, CDC_RX_CLK_RST_CTRL_SWR_CONTROL, CDC_RX_SWR_CLK_EN_MASK, 1); @@ -4003,9 +4010,15 @@ static int rx_macro_runtime_resume(struct device *dev) goto err_fsgen; } regcache_cache_only(rx->regmap, false); - regcache_sync(rx->regmap); + ret = regcache_sync(rx->regmap); + if (ret) + goto err_sync; return 0; +err_sync: + regcache_cache_only(rx->regmap, true); + regcache_mark_dirty(rx->regmap); + clk_disable_unprepare(rx->fsgen); err_fsgen: clk_disable_unprepare(rx->npl); err_npl: -- cgit v1.2.3