diff options
Diffstat (limited to 'meta-amdfalconx86/recipes-kernel/linux/files/1128-ASoC-AMD-add-pm-ops.patch')
-rw-r--r-- | meta-amdfalconx86/recipes-kernel/linux/files/1128-ASoC-AMD-add-pm-ops.patch | 106 |
1 files changed, 106 insertions, 0 deletions
diff --git a/meta-amdfalconx86/recipes-kernel/linux/files/1128-ASoC-AMD-add-pm-ops.patch b/meta-amdfalconx86/recipes-kernel/linux/files/1128-ASoC-AMD-add-pm-ops.patch new file mode 100644 index 00000000..cf6d3eda --- /dev/null +++ b/meta-amdfalconx86/recipes-kernel/linux/files/1128-ASoC-AMD-add-pm-ops.patch @@ -0,0 +1,106 @@ +From 2cb46c7ba1f892f2bf66f0e050434dd18bd0c2ed Mon Sep 17 00:00:00 2001 +From: Maruthi Srinivas Bayyavarapu <Maruthi.Bayyavarapu@amd.com> +Date: Mon, 21 Dec 2015 15:37:47 +0530 +Subject: [PATCH 03/17] ASoC: AMD: add pm ops + +genpd will power off/on ACP to manage runtime ACP PM. ACP runtime PM +hooks are added to get it deinitialized and initialized respectively, +after it is powered off/on. + +When system goes to suspend when audio usecase is active, ACP will +be powered off through genpd. When it resumes, ACP needs to be +initialized and reconfigured. + +Signed-off-by: Maruthi Bayyavarapu <maruthi.bayyavarapu@amd.com> +Reviewed-by: Alex Deucher <alexander.deucher@amd.com> +Signed-off-by: Alex Deucher <alexander.deucher@amd.com> +Signed-off-by: Kalyan Alle <kalyan.alle@amd.com> +--- + sound/soc/amd/acp-pcm-dma.c | 48 +++++++++++++++++++++++++++++++++++++++++++++ + 1 file changed, 48 insertions(+) + +diff --git a/sound/soc/amd/acp-pcm-dma.c b/sound/soc/amd/acp-pcm-dma.c +index 0724d78..c0819b5 100644 +--- a/sound/soc/amd/acp-pcm-dma.c ++++ b/sound/soc/amd/acp-pcm-dma.c +@@ -16,6 +16,7 @@ + #include <linux/module.h> + #include <linux/delay.h> + #include <linux/sizes.h> ++#include <linux/pm_runtime.h> + + #include <sound/soc.h> + +@@ -885,6 +886,10 @@ static int acp_audio_probe(struct platform_device *pdev) + return status; + } + ++ pm_runtime_set_autosuspend_delay(&pdev->dev, 10000); ++ pm_runtime_use_autosuspend(&pdev->dev); ++ pm_runtime_enable(&pdev->dev); ++ + return status; + } + +@@ -894,15 +899,58 @@ static int acp_audio_remove(struct platform_device *pdev) + + acp_deinit(adata->acp_mmio); + snd_soc_unregister_platform(&pdev->dev); ++ pm_runtime_disable(&pdev->dev); + + return 0; + } + ++static int acp_pcm_resume(struct device *dev) ++{ ++ struct audio_drv_data *adata = dev_get_drvdata(dev); ++ ++ acp_init(adata->acp_mmio); ++ ++ if (adata->play_stream && adata->play_stream->runtime) ++ config_acp_dma(adata->acp_mmio, ++ adata->play_stream->runtime->private_data); ++ if (adata->capture_stream && adata->capture_stream->runtime) ++ config_acp_dma(adata->acp_mmio, ++ adata->capture_stream->runtime->private_data); ++ ++ acp_reg_write(1, adata->acp_mmio, mmACP_EXTERNAL_INTR_ENB); ++ return 0; ++} ++ ++static int acp_pcm_runtime_suspend(struct device *dev) ++{ ++ struct audio_drv_data *adata = dev_get_drvdata(dev); ++ ++ acp_deinit(adata->acp_mmio); ++ acp_reg_write(0, adata->acp_mmio, mmACP_EXTERNAL_INTR_ENB); ++ return 0; ++} ++ ++static int acp_pcm_runtime_resume(struct device *dev) ++{ ++ struct audio_drv_data *adata = dev_get_drvdata(dev); ++ ++ acp_init(adata->acp_mmio); ++ acp_reg_write(1, adata->acp_mmio, mmACP_EXTERNAL_INTR_ENB); ++ return 0; ++} ++ ++static const struct dev_pm_ops acp_pm_ops = { ++ .resume = acp_pcm_resume, ++ .runtime_suspend = acp_pcm_runtime_suspend, ++ .runtime_resume = acp_pcm_runtime_resume, ++}; ++ + static struct platform_driver acp_dma_driver = { + .probe = acp_audio_probe, + .remove = acp_audio_remove, + .driver = { + .name = "acp_audio_dma", ++ .pm = &acp_pm_ops, + }, + }; + +-- +2.7.4 + |