Loading asoc/codecs/bolero/bolero-cdc.c +7 −4 Original line number Diff line number Diff line Loading @@ -14,6 +14,7 @@ #include <soc/snd_event.h> #include <linux/pm_runtime.h> #include <soc/swr-common.h> #include <dsp/digital-cdc-rsc-mgr.h> #include "bolero-cdc.h" #include "internal.h" #include "bolero-clk-rsc.h" Loading Loading @@ -1388,7 +1389,7 @@ int bolero_runtime_resume(struct device *dev) } if (priv->core_hw_vote_count == 0) { ret = clk_prepare_enable(priv->lpass_core_hw_vote); ret = digital_cdc_rsc_mgr_hw_vote_enable(priv->lpass_core_hw_vote); if (ret < 0) { dev_err(dev, "%s:lpass core hw enable failed\n", __func__); Loading @@ -1406,7 +1407,7 @@ int bolero_runtime_resume(struct device *dev) } if (priv->core_audio_vote_count == 0) { ret = clk_prepare_enable(priv->lpass_audio_hw_vote); ret = digital_cdc_rsc_mgr_hw_vote_enable(priv->lpass_audio_hw_vote); if (ret < 0) { dev_err(dev, "%s:lpass audio hw enable failed\n", __func__); Loading @@ -1431,7 +1432,8 @@ int bolero_runtime_suspend(struct device *dev) mutex_lock(&priv->vote_lock); if (priv->lpass_core_hw_vote != NULL) { if (--priv->core_hw_vote_count == 0) clk_disable_unprepare(priv->lpass_core_hw_vote); digital_cdc_rsc_mgr_hw_vote_disable( priv->lpass_core_hw_vote); if (priv->core_hw_vote_count < 0) priv->core_hw_vote_count = 0; } else { Loading @@ -1443,7 +1445,8 @@ int bolero_runtime_suspend(struct device *dev) if (priv->lpass_audio_hw_vote != NULL) { if (--priv->core_audio_vote_count == 0) clk_disable_unprepare(priv->lpass_audio_hw_vote); digital_cdc_rsc_mgr_hw_vote_disable( priv->lpass_audio_hw_vote); if (priv->core_audio_vote_count < 0) priv->core_audio_vote_count = 0; } else { Loading asoc/codecs/bolero/va-macro.c +5 −2 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ #include <asoc/msm-cdc-pinctrl.h> #include <soc/swr-common.h> #include <soc/swr-wcd.h> #include <dsp/digital-cdc-rsc-mgr.h> #include "bolero-cdc.h" #include "bolero-cdc-registers.h" #include "bolero-clk-rsc.h" Loading Loading @@ -444,7 +445,8 @@ static int va_macro_swr_pwr_event(struct snd_soc_dapm_widget *w, switch (event) { case SND_SOC_DAPM_PRE_PMU: if (va_priv->lpass_audio_hw_vote) { ret = clk_prepare_enable(va_priv->lpass_audio_hw_vote); ret = digital_cdc_rsc_mgr_hw_vote_enable( va_priv->lpass_audio_hw_vote); if (ret) dev_err(va_dev, "%s: lpass audio hw enable failed\n", Loading @@ -467,7 +469,8 @@ static int va_macro_swr_pwr_event(struct snd_soc_dapm_widget *w, if (bolero_tx_clk_switch(component, CLK_SRC_TX_RCG)) dev_dbg(va_dev, "%s: clock switch failed\n",__func__); if (va_priv->lpass_audio_hw_vote) clk_disable_unprepare(va_priv->lpass_audio_hw_vote); digital_cdc_rsc_mgr_hw_vote_disable( va_priv->lpass_audio_hw_vote); break; default: dev_err(va_priv->dev, Loading dsp/Kbuild +4 −0 Original line number Diff line number Diff line Loading @@ -186,6 +186,10 @@ ifdef CONFIG_VOICE_MHI Q6_OBJS += voice_mhi.o endif ifdef CONFIG_DIGITAL_CDC_RSC_MGR Q6_OBJS += digital-cdc-rsc-mgr.o endif LINUX_INC += -Iinclude/linux INCS += $(COMMON_INC) \ Loading dsp/digital-cdc-rsc-mgr.c 0 → 100644 +100 −0 Original line number Diff line number Diff line /* SPDX-License-Identifier: GPL-2.0-only */ /* * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. */ #include <linux/clk.h> #include <linux/clk-provider.h> #include <linux/ratelimit.h> #include <dsp/digital-cdc-rsc-mgr.h> struct mutex hw_vote_lock; static bool is_init_done; /** * digital_cdc_rsc_mgr_hw_vote_enable - Enables hw vote in DSP * * @vote_handle: vote handle for which voting needs to be done * * Returns 0 on success or -EINVAL/error code on failure */ int digital_cdc_rsc_mgr_hw_vote_enable(struct clk* vote_handle) { int ret = 0; if (!is_init_done || vote_handle == NULL) { pr_err_ratelimited("%s: init failed or vote handle NULL\n", __func__); return -EINVAL; } mutex_lock(&hw_vote_lock); ret = clk_prepare_enable(vote_handle); mutex_unlock(&hw_vote_lock); pr_debug("%s: return %d\n", __func__, ret); trace_printk("%s: return %d\n", __func__, ret); return ret; } EXPORT_SYMBOL(digital_cdc_rsc_mgr_hw_vote_enable); /** * digital_cdc_rsc_mgr_hw_vote_disable - Disables hw vote in DSP * * @vote_handle: vote handle for which voting needs to be disabled * */ void digital_cdc_rsc_mgr_hw_vote_disable(struct clk* vote_handle) { if (!is_init_done || vote_handle == NULL) { pr_err_ratelimited("%s: init failed or vote handle NULL\n", __func__); return; } mutex_lock(&hw_vote_lock); clk_disable_unprepare(vote_handle); mutex_unlock(&hw_vote_lock); trace_printk("%s\n", __func__); } EXPORT_SYMBOL(digital_cdc_rsc_mgr_hw_vote_disable); /** * digital_cdc_rsc_mgr_hw_vote_reset - Resets hw vote count * */ void digital_cdc_rsc_mgr_hw_vote_reset(struct clk* vote_handle) { int count = 0; if (!is_init_done || vote_handle == NULL) { pr_err_ratelimited("%s: init failed or vote handle NULL\n", __func__); return; } mutex_lock(&hw_vote_lock); while (__clk_is_enabled(vote_handle)) { clk_disable_unprepare(vote_handle); count++; } pr_debug("%s: Vote count after SSR: %d\n", __func__, count); trace_printk("%s: Vote count after SSR: %d\n", __func__, count); while (count--) clk_prepare_enable(vote_handle); mutex_unlock(&hw_vote_lock); } EXPORT_SYMBOL(digital_cdc_rsc_mgr_hw_vote_reset); void digital_cdc_rsc_mgr_init() { mutex_init(&hw_vote_lock); is_init_done = true; } void digital_cdc_rsc_mgr_exit() { mutex_destroy(&hw_vote_lock); is_init_done = false; } dsp/q6_init.c +3 −1 Original line number Diff line number Diff line // SPDX-License-Identifier: GPL-2.0-only /* * Copyright (c) 2017, 2019 The Linux Foundation. All rights reserved. * Copyright (c) 2017, 2019-2020 The Linux Foundation. All rights reserved. */ #include <linux/kernel.h> Loading @@ -24,11 +24,13 @@ static int __init audio_q6_init(void) avtimer_init(); msm_mdf_init(); voice_mhi_init(); digital_cdc_rsc_mgr_init(); return 0; } static void __exit audio_q6_exit(void) { digital_cdc_rsc_mgr_exit(); msm_mdf_exit(); avtimer_exit(); audio_slimslave_exit(); Loading Loading
asoc/codecs/bolero/bolero-cdc.c +7 −4 Original line number Diff line number Diff line Loading @@ -14,6 +14,7 @@ #include <soc/snd_event.h> #include <linux/pm_runtime.h> #include <soc/swr-common.h> #include <dsp/digital-cdc-rsc-mgr.h> #include "bolero-cdc.h" #include "internal.h" #include "bolero-clk-rsc.h" Loading Loading @@ -1388,7 +1389,7 @@ int bolero_runtime_resume(struct device *dev) } if (priv->core_hw_vote_count == 0) { ret = clk_prepare_enable(priv->lpass_core_hw_vote); ret = digital_cdc_rsc_mgr_hw_vote_enable(priv->lpass_core_hw_vote); if (ret < 0) { dev_err(dev, "%s:lpass core hw enable failed\n", __func__); Loading @@ -1406,7 +1407,7 @@ int bolero_runtime_resume(struct device *dev) } if (priv->core_audio_vote_count == 0) { ret = clk_prepare_enable(priv->lpass_audio_hw_vote); ret = digital_cdc_rsc_mgr_hw_vote_enable(priv->lpass_audio_hw_vote); if (ret < 0) { dev_err(dev, "%s:lpass audio hw enable failed\n", __func__); Loading @@ -1431,7 +1432,8 @@ int bolero_runtime_suspend(struct device *dev) mutex_lock(&priv->vote_lock); if (priv->lpass_core_hw_vote != NULL) { if (--priv->core_hw_vote_count == 0) clk_disable_unprepare(priv->lpass_core_hw_vote); digital_cdc_rsc_mgr_hw_vote_disable( priv->lpass_core_hw_vote); if (priv->core_hw_vote_count < 0) priv->core_hw_vote_count = 0; } else { Loading @@ -1443,7 +1445,8 @@ int bolero_runtime_suspend(struct device *dev) if (priv->lpass_audio_hw_vote != NULL) { if (--priv->core_audio_vote_count == 0) clk_disable_unprepare(priv->lpass_audio_hw_vote); digital_cdc_rsc_mgr_hw_vote_disable( priv->lpass_audio_hw_vote); if (priv->core_audio_vote_count < 0) priv->core_audio_vote_count = 0; } else { Loading
asoc/codecs/bolero/va-macro.c +5 −2 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ #include <asoc/msm-cdc-pinctrl.h> #include <soc/swr-common.h> #include <soc/swr-wcd.h> #include <dsp/digital-cdc-rsc-mgr.h> #include "bolero-cdc.h" #include "bolero-cdc-registers.h" #include "bolero-clk-rsc.h" Loading Loading @@ -444,7 +445,8 @@ static int va_macro_swr_pwr_event(struct snd_soc_dapm_widget *w, switch (event) { case SND_SOC_DAPM_PRE_PMU: if (va_priv->lpass_audio_hw_vote) { ret = clk_prepare_enable(va_priv->lpass_audio_hw_vote); ret = digital_cdc_rsc_mgr_hw_vote_enable( va_priv->lpass_audio_hw_vote); if (ret) dev_err(va_dev, "%s: lpass audio hw enable failed\n", Loading @@ -467,7 +469,8 @@ static int va_macro_swr_pwr_event(struct snd_soc_dapm_widget *w, if (bolero_tx_clk_switch(component, CLK_SRC_TX_RCG)) dev_dbg(va_dev, "%s: clock switch failed\n",__func__); if (va_priv->lpass_audio_hw_vote) clk_disable_unprepare(va_priv->lpass_audio_hw_vote); digital_cdc_rsc_mgr_hw_vote_disable( va_priv->lpass_audio_hw_vote); break; default: dev_err(va_priv->dev, Loading
dsp/Kbuild +4 −0 Original line number Diff line number Diff line Loading @@ -186,6 +186,10 @@ ifdef CONFIG_VOICE_MHI Q6_OBJS += voice_mhi.o endif ifdef CONFIG_DIGITAL_CDC_RSC_MGR Q6_OBJS += digital-cdc-rsc-mgr.o endif LINUX_INC += -Iinclude/linux INCS += $(COMMON_INC) \ Loading
dsp/digital-cdc-rsc-mgr.c 0 → 100644 +100 −0 Original line number Diff line number Diff line /* SPDX-License-Identifier: GPL-2.0-only */ /* * Copyright (c) 2019-2020, The Linux Foundation. All rights reserved. */ #include <linux/clk.h> #include <linux/clk-provider.h> #include <linux/ratelimit.h> #include <dsp/digital-cdc-rsc-mgr.h> struct mutex hw_vote_lock; static bool is_init_done; /** * digital_cdc_rsc_mgr_hw_vote_enable - Enables hw vote in DSP * * @vote_handle: vote handle for which voting needs to be done * * Returns 0 on success or -EINVAL/error code on failure */ int digital_cdc_rsc_mgr_hw_vote_enable(struct clk* vote_handle) { int ret = 0; if (!is_init_done || vote_handle == NULL) { pr_err_ratelimited("%s: init failed or vote handle NULL\n", __func__); return -EINVAL; } mutex_lock(&hw_vote_lock); ret = clk_prepare_enable(vote_handle); mutex_unlock(&hw_vote_lock); pr_debug("%s: return %d\n", __func__, ret); trace_printk("%s: return %d\n", __func__, ret); return ret; } EXPORT_SYMBOL(digital_cdc_rsc_mgr_hw_vote_enable); /** * digital_cdc_rsc_mgr_hw_vote_disable - Disables hw vote in DSP * * @vote_handle: vote handle for which voting needs to be disabled * */ void digital_cdc_rsc_mgr_hw_vote_disable(struct clk* vote_handle) { if (!is_init_done || vote_handle == NULL) { pr_err_ratelimited("%s: init failed or vote handle NULL\n", __func__); return; } mutex_lock(&hw_vote_lock); clk_disable_unprepare(vote_handle); mutex_unlock(&hw_vote_lock); trace_printk("%s\n", __func__); } EXPORT_SYMBOL(digital_cdc_rsc_mgr_hw_vote_disable); /** * digital_cdc_rsc_mgr_hw_vote_reset - Resets hw vote count * */ void digital_cdc_rsc_mgr_hw_vote_reset(struct clk* vote_handle) { int count = 0; if (!is_init_done || vote_handle == NULL) { pr_err_ratelimited("%s: init failed or vote handle NULL\n", __func__); return; } mutex_lock(&hw_vote_lock); while (__clk_is_enabled(vote_handle)) { clk_disable_unprepare(vote_handle); count++; } pr_debug("%s: Vote count after SSR: %d\n", __func__, count); trace_printk("%s: Vote count after SSR: %d\n", __func__, count); while (count--) clk_prepare_enable(vote_handle); mutex_unlock(&hw_vote_lock); } EXPORT_SYMBOL(digital_cdc_rsc_mgr_hw_vote_reset); void digital_cdc_rsc_mgr_init() { mutex_init(&hw_vote_lock); is_init_done = true; } void digital_cdc_rsc_mgr_exit() { mutex_destroy(&hw_vote_lock); is_init_done = false; }
dsp/q6_init.c +3 −1 Original line number Diff line number Diff line // SPDX-License-Identifier: GPL-2.0-only /* * Copyright (c) 2017, 2019 The Linux Foundation. All rights reserved. * Copyright (c) 2017, 2019-2020 The Linux Foundation. All rights reserved. */ #include <linux/kernel.h> Loading @@ -24,11 +24,13 @@ static int __init audio_q6_init(void) avtimer_init(); msm_mdf_init(); voice_mhi_init(); digital_cdc_rsc_mgr_init(); return 0; } static void __exit audio_q6_exit(void) { digital_cdc_rsc_mgr_exit(); msm_mdf_exit(); avtimer_exit(); audio_slimslave_exit(); Loading