summaryrefslogtreecommitdiff
path: root/sound/soc/fsl
diff options
context:
space:
mode:
authorMark Brown <broonie@kernel.org>2024-03-26 17:10:50 +0300
committerMark Brown <broonie@kernel.org>2024-03-26 17:10:50 +0300
commitef71b33022ddd54840c6447677eb8a87e374399a (patch)
tree1306daf0bc704859da743b9b452641300168a6d0 /sound/soc/fsl
parent22247e402d824546cdd6ec422c0dc51181269d54 (diff)
parentc14445bdcb98feddf9afaeb05e6193cc1f8eec1a (diff)
downloadlinux-ef71b33022ddd54840c6447677eb8a87e374399a.tar.xz
ASoC: fsl: Support register and unregister rpmsg
Merge series from Chancel Liu <chancel.liu@nxp.com>: echo /lib/firmware/fw.elf > /sys/class/remoteproc/remoteproc0/firmware (A) echo start > /sys/class/remoteproc/remoteproc0/state (B) echo stop > /sys/class/remoteproc/remoteproc0/state The rpmsg sound card is registered in (A) and unregistered in (B). After "start", imx-audio-rpmsg registers devices for ASoC platform driver and machine driver. Then sound card is registered. After "stop", imx-audio-rpmsg unregisters devices for ASoC platform driver and machine driver. Then sound card is unregistered.
Diffstat (limited to 'sound/soc/fsl')
-rw-r--r--sound/soc/fsl/fsl_rpmsg.c43
-rw-r--r--sound/soc/fsl/imx-audio-rpmsg.c21
-rw-r--r--sound/soc/fsl/imx-pcm-rpmsg.c11
-rw-r--r--sound/soc/fsl/imx-rpmsg.c28
4 files changed, 71 insertions, 32 deletions
diff --git a/sound/soc/fsl/fsl_rpmsg.c b/sound/soc/fsl/fsl_rpmsg.c
index 00852f174a69..bc41a0666856 100644
--- a/sound/soc/fsl/fsl_rpmsg.c
+++ b/sound/soc/fsl/fsl_rpmsg.c
@@ -135,7 +135,6 @@ static struct snd_soc_dai_driver fsl_rpmsg_dai = {
static const struct snd_soc_component_driver fsl_component = {
.name = "fsl-rpmsg",
- .legacy_dai_naming = 1,
};
static const struct fsl_rpmsg_soc_data imx7ulp_data = {
@@ -190,19 +189,40 @@ MODULE_DEVICE_TABLE(of, fsl_rpmsg_ids);
static int fsl_rpmsg_probe(struct platform_device *pdev)
{
struct device_node *np = pdev->dev.of_node;
+ struct snd_soc_dai_driver *dai_drv;
+ const char *dai_name;
struct fsl_rpmsg *rpmsg;
int ret;
+ dai_drv = devm_kzalloc(&pdev->dev, sizeof(struct snd_soc_dai_driver), GFP_KERNEL);
+ if (!dai_drv)
+ return -ENOMEM;
+ memcpy(dai_drv, &fsl_rpmsg_dai, sizeof(fsl_rpmsg_dai));
+
rpmsg = devm_kzalloc(&pdev->dev, sizeof(struct fsl_rpmsg), GFP_KERNEL);
if (!rpmsg)
return -ENOMEM;
rpmsg->soc_data = of_device_get_match_data(&pdev->dev);
- fsl_rpmsg_dai.playback.rates = rpmsg->soc_data->rates;
- fsl_rpmsg_dai.capture.rates = rpmsg->soc_data->rates;
- fsl_rpmsg_dai.playback.formats = rpmsg->soc_data->formats;
- fsl_rpmsg_dai.capture.formats = rpmsg->soc_data->formats;
+ if (rpmsg->soc_data) {
+ dai_drv->playback.rates = rpmsg->soc_data->rates;
+ dai_drv->capture.rates = rpmsg->soc_data->rates;
+ dai_drv->playback.formats = rpmsg->soc_data->formats;
+ dai_drv->capture.formats = rpmsg->soc_data->formats;
+ }
+
+ /* Use rpmsg channel name as cpu dai name */
+ ret = of_property_read_string(np, "fsl,rpmsg-channel-name", &dai_name);
+ if (ret) {
+ if (ret == -EINVAL) {
+ dai_name = "rpmsg-audio-channel";
+ } else {
+ dev_err(&pdev->dev, "Failed to get rpmsg channel name: %d!\n", ret);
+ return ret;
+ }
+ }
+ dai_drv->name = dai_name;
if (of_property_read_bool(np, "fsl,enable-lpa")) {
rpmsg->enable_lpa = 1;
@@ -236,21 +256,10 @@ static int fsl_rpmsg_probe(struct platform_device *pdev)
pm_runtime_enable(&pdev->dev);
ret = devm_snd_soc_register_component(&pdev->dev, &fsl_component,
- &fsl_rpmsg_dai, 1);
+ dai_drv, 1);
if (ret)
goto err_pm_disable;
- rpmsg->card_pdev = platform_device_register_data(&pdev->dev,
- "imx-audio-rpmsg",
- PLATFORM_DEVID_AUTO,
- NULL,
- 0);
- if (IS_ERR(rpmsg->card_pdev)) {
- dev_err(&pdev->dev, "failed to register rpmsg card\n");
- ret = PTR_ERR(rpmsg->card_pdev);
- goto err_pm_disable;
- }
-
return 0;
err_pm_disable:
diff --git a/sound/soc/fsl/imx-audio-rpmsg.c b/sound/soc/fsl/imx-audio-rpmsg.c
index 289e47c03d40..38aafb8954c7 100644
--- a/sound/soc/fsl/imx-audio-rpmsg.c
+++ b/sound/soc/fsl/imx-audio-rpmsg.c
@@ -12,6 +12,7 @@
*/
struct imx_audio_rpmsg {
struct platform_device *rpmsg_pdev;
+ struct platform_device *card_pdev;
};
static int imx_audio_rpmsg_cb(struct rpmsg_device *rpdev, void *data, int len,
@@ -87,14 +88,24 @@ static int imx_audio_rpmsg_probe(struct rpmsg_device *rpdev)
/* Register platform driver for rpmsg routine */
data->rpmsg_pdev = platform_device_register_data(&rpdev->dev,
- IMX_PCM_DRV_NAME,
- PLATFORM_DEVID_AUTO,
+ rpdev->id.name,
+ PLATFORM_DEVID_NONE,
NULL, 0);
if (IS_ERR(data->rpmsg_pdev)) {
dev_err(&rpdev->dev, "failed to register rpmsg platform.\n");
ret = PTR_ERR(data->rpmsg_pdev);
}
+ data->card_pdev = platform_device_register_data(&rpdev->dev,
+ "imx-audio-rpmsg",
+ PLATFORM_DEVID_AUTO,
+ rpdev->id.name,
+ strlen(rpdev->id.name) + 1);
+ if (IS_ERR(data->card_pdev)) {
+ dev_err(&rpdev->dev, "failed to register rpmsg card.\n");
+ ret = PTR_ERR(data->card_pdev);
+ }
+
return ret;
}
@@ -105,6 +116,9 @@ static void imx_audio_rpmsg_remove(struct rpmsg_device *rpdev)
if (data->rpmsg_pdev)
platform_device_unregister(data->rpmsg_pdev);
+ if (data->card_pdev)
+ platform_device_unregister(data->card_pdev);
+
dev_info(&rpdev->dev, "audio rpmsg driver is removed\n");
}
@@ -113,6 +127,7 @@ static struct rpmsg_device_id imx_audio_rpmsg_id_table[] = {
{ .name = "rpmsg-micfil-channel" },
{ },
};
+MODULE_DEVICE_TABLE(rpmsg, imx_audio_rpmsg_id_table);
static struct rpmsg_driver imx_audio_rpmsg_driver = {
.drv.name = "imx_audio_rpmsg",
@@ -126,5 +141,5 @@ module_rpmsg_driver(imx_audio_rpmsg_driver);
MODULE_DESCRIPTION("Freescale SoC Audio RPMSG interface");
MODULE_AUTHOR("Shengjiu Wang <shengjiu.wang@nxp.com>");
-MODULE_ALIAS("platform:imx_audio_rpmsg");
+MODULE_ALIAS("rpmsg:imx_audio_rpmsg");
MODULE_LICENSE("GPL v2");
diff --git a/sound/soc/fsl/imx-pcm-rpmsg.c b/sound/soc/fsl/imx-pcm-rpmsg.c
index fb9244c1e9c5..b84d1dfddba2 100644
--- a/sound/soc/fsl/imx-pcm-rpmsg.c
+++ b/sound/soc/fsl/imx-pcm-rpmsg.c
@@ -732,9 +732,6 @@ static int imx_rpmsg_pcm_probe(struct platform_device *pdev)
goto fail;
}
- /* platform component name is used by machine driver to link with */
- component->name = info->rpdev->id.name;
-
#ifdef CONFIG_DEBUG_FS
component->debugfs_prefix = "rpmsg";
#endif
@@ -822,9 +819,17 @@ static const struct dev_pm_ops imx_rpmsg_pcm_pm_ops = {
imx_rpmsg_pcm_resume)
};
+static const struct platform_device_id imx_rpmsg_pcm_id_table[] = {
+ { .name = "rpmsg-audio-channel" },
+ { .name = "rpmsg-micfil-channel" },
+ { },
+};
+MODULE_DEVICE_TABLE(platform, imx_rpmsg_pcm_id_table);
+
static struct platform_driver imx_pcm_rpmsg_driver = {
.probe = imx_rpmsg_pcm_probe,
.remove_new = imx_rpmsg_pcm_remove,
+ .id_table = imx_rpmsg_pcm_id_table,
.driver = {
.name = IMX_PCM_DRV_NAME,
.pm = &imx_rpmsg_pcm_pm_ops,
diff --git a/sound/soc/fsl/imx-rpmsg.c b/sound/soc/fsl/imx-rpmsg.c
index e5bd63dab10c..0f1ad7ad7d27 100644
--- a/sound/soc/fsl/imx-rpmsg.c
+++ b/sound/soc/fsl/imx-rpmsg.c
@@ -108,10 +108,8 @@ static int imx_rpmsg_late_probe(struct snd_soc_card *card)
static int imx_rpmsg_probe(struct platform_device *pdev)
{
struct snd_soc_dai_link_component *dlc;
- struct device *dev = pdev->dev.parent;
- /* rpmsg_pdev is the platform device for the rpmsg node that probed us */
- struct platform_device *rpmsg_pdev = to_platform_device(dev);
- struct device_node *np = rpmsg_pdev->dev.of_node;
+ struct snd_soc_dai *cpu_dai;
+ struct device_node *np = NULL;
struct of_phandle_args args;
const char *platform_name;
struct imx_rpmsg *data;
@@ -127,10 +125,6 @@ static int imx_rpmsg_probe(struct platform_device *pdev)
goto fail;
}
- ret = of_reserved_mem_device_init_by_idx(&pdev->dev, np, 0);
- if (ret)
- dev_warn(&pdev->dev, "no reserved DMA memory\n");
-
data->dai.cpus = &dlc[0];
data->dai.num_cpus = 1;
data->dai.platforms = &dlc[1];
@@ -152,6 +146,23 @@ static int imx_rpmsg_probe(struct platform_device *pdev)
*/
data->dai.ignore_pmdown_time = 1;
+ data->dai.cpus->dai_name = pdev->dev.platform_data;
+ cpu_dai = snd_soc_find_dai(data->dai.cpus);
+ if (!cpu_dai) {
+ ret = -EPROBE_DEFER;
+ goto fail;
+ }
+ np = cpu_dai->dev->of_node;
+ if (!np) {
+ dev_err(&pdev->dev, "failed to parse CPU DAI device node\n");
+ ret = -ENODEV;
+ goto fail;
+ }
+
+ ret = of_reserved_mem_device_init_by_idx(&pdev->dev, np, 0);
+ if (ret)
+ dev_warn(&pdev->dev, "no reserved DMA memory\n");
+
/* Optional codec node */
ret = of_parse_phandle_with_fixed_args(np, "audio-codec", 0, 0, &args);
if (ret) {
@@ -170,7 +181,6 @@ static int imx_rpmsg_probe(struct platform_device *pdev)
data->sysclk = clk_get_rate(clk);
}
- data->dai.cpus->dai_name = dev_name(&rpmsg_pdev->dev);
if (!of_property_read_string(np, "fsl,rpmsg-channel-name", &platform_name))
data->dai.platforms->name = platform_name;
else