summaryrefslogtreecommitdiffstats
path: root/sound/soc/codecs/lpass-macro-common.c
diff options
context:
space:
mode:
authorSrinivasa Rao Mandadapu <quic_srivasam@quicinc.com>2022-02-26 19:09:18 +0100
committerMark Brown <broonie@kernel.org>2022-02-28 14:30:37 +0100
commit9e3d83c52844f955aa2975f78cee48bf9f72f5e1 (patch)
treef63b833a6f6b608d9b27dcd0507473ae305179c1 /sound/soc/codecs/lpass-macro-common.c
parentASoC: codecs: add pm runtime support for Qualcomm codecs (diff)
downloadlinux-9e3d83c52844f955aa2975f78cee48bf9f72f5e1.tar.xz
linux-9e3d83c52844f955aa2975f78cee48bf9f72f5e1.zip
ASoC: codecs: Add power domains support in digital macro codecs
Add support for enabling required power domains in digital macro codecs. macro and dcodec power domains are being requested as clocks by HLOS in ADSP based architectures and ADSP internally handling as powerdomains. In ADSP bypass case need to handle them as power domains explicitly. Signed-off-by: Srinivasa Rao Mandadapu <quic_srivasam@quicinc.com> Co-developed-by: Venkata Prasad Potturu <quic_potturu@quicinc.com> Signed-off-by: Venkata Prasad Potturu <quic_potturu@quicinc.com> Reported-by: kernel test robot <lkp@intel.com> Link: https://lore.kernel.org/r/1645898959-11231-2-git-send-email-quic_srivasam@quicinc.com Signed-off-by: Mark Brown <broonie@kernel.org>
Diffstat (limited to 'sound/soc/codecs/lpass-macro-common.c')
-rw-r--r--sound/soc/codecs/lpass-macro-common.c67
1 files changed, 67 insertions, 0 deletions
diff --git a/sound/soc/codecs/lpass-macro-common.c b/sound/soc/codecs/lpass-macro-common.c
new file mode 100644
index 000000000000..6cede75ed3b5
--- /dev/null
+++ b/sound/soc/codecs/lpass-macro-common.c
@@ -0,0 +1,67 @@
+// SPDX-License-Identifier: GPL-2.0-only
+// Copyright (c) 2022, The Linux Foundation. All rights reserved.
+
+#include <linux/export.h>
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/of_platform.h>
+#include <linux/platform_device.h>
+#include <linux/pm_domain.h>
+#include <linux/pm_runtime.h>
+
+#include "lpass-macro-common.h"
+
+struct lpass_macro *lpass_macro_pds_init(struct device *dev)
+{
+ struct lpass_macro *l_pds;
+ int ret;
+
+ if (!of_find_property(dev->of_node, "power-domains", NULL))
+ return NULL;
+
+ l_pds = devm_kzalloc(dev, sizeof(*l_pds), GFP_KERNEL);
+ if (!l_pds)
+ return ERR_PTR(-ENOMEM);
+
+ l_pds->macro_pd = dev_pm_domain_attach_by_name(dev, "macro");
+ if (IS_ERR_OR_NULL(l_pds->macro_pd))
+ return NULL;
+
+ ret = pm_runtime_get_sync(l_pds->macro_pd);
+ if (ret < 0) {
+ pm_runtime_put_noidle(l_pds->macro_pd);
+ goto macro_err;
+ }
+
+ l_pds->dcodec_pd = dev_pm_domain_attach_by_name(dev, "dcodec");
+ if (IS_ERR_OR_NULL(l_pds->dcodec_pd))
+ goto dcodec_err;
+
+ ret = pm_runtime_get_sync(l_pds->dcodec_pd);
+ if (ret < 0) {
+ pm_runtime_put_noidle(l_pds->dcodec_pd);
+ goto dcodec_sync_err;
+ }
+ return l_pds;
+
+dcodec_sync_err:
+ dev_pm_domain_detach(l_pds->dcodec_pd, false);
+dcodec_err:
+ pm_runtime_put(l_pds->macro_pd);
+macro_err:
+ dev_pm_domain_detach(l_pds->macro_pd, false);
+ return ERR_PTR(ret);
+}
+EXPORT_SYMBOL_GPL(lpass_macro_pds_init);
+
+void lpass_macro_pds_exit(struct lpass_macro *pds)
+{
+ pm_runtime_put(pds->macro_pd);
+ dev_pm_domain_detach(pds->macro_pd, false);
+ pm_runtime_put(pds->dcodec_pd);
+ dev_pm_domain_detach(pds->dcodec_pd, false);
+}
+EXPORT_SYMBOL_GPL(lpass_macro_pds_exit);
+
+MODULE_DESCRIPTION("Common macro driver");
+MODULE_LICENSE("GPL");