From: Peter Ujfalusi <peter.ujfalusi@linux.intel.com>
To: lgirdwood@gmail.com, broonie@kernel.org
Cc: alsa-devel@alsa-project.org, kai.vehmanen@linux.intel.com,
pierre-louis.bossart@linux.intel.com, rander.wang@intel.com,
ranjani.sridharan@linux.intel.com,
yung-chuan.liao@linux.intel.com
Subject: [PATCH 06/11] ASoC: SOF: sof-audio: Extend the optionality of IPC ops to IPC as well
Date: Wed, 21 Dec 2022 12:23:23 +0200 [thread overview]
Message-ID: <20221221102328.9635-7-peter.ujfalusi@linux.intel.com> (raw)
In-Reply-To: <20221221102328.9635-1-peter.ujfalusi@linux.intel.com>
The IPC ops are optional, but they require that the ops struct is to be
allocated with all callbacks set to NULL.
Update the code to extend the optionality to:
sdev->ipc == NULL
sdev->ipc->ops == NULL
sdev->ipc->ops->[ops_group] == NULL
sdev->ipc->ops->[pcmops_group]->ops == NULL (treated optional currently)
Signed-off-by: Peter Ujfalusi <peter.ujfalusi@linux.intel.com>
Reviewed-by: Pierre-Louis Bossart <pierre-louis.bossart@linux.intel.com>
Reviewed-by: Ranjani Sridharan <ranjani.sridharan@linux.intel.com>
Reviewed-by: Bard Liao <yung-chuan.liao@linux.intel.com>
Reviewed-by: Rander Wang <rander.wang@intel.com>
---
sound/soc/sof/sof-audio.c | 51 +++++++++++++++++++++------------------
1 file changed, 28 insertions(+), 23 deletions(-)
diff --git a/sound/soc/sof/sof-audio.c b/sound/soc/sof/sof-audio.c
index 2c7d942427c1..e1ab8380e7d8 100644
--- a/sound/soc/sof/sof-audio.c
+++ b/sound/soc/sof/sof-audio.c
@@ -16,12 +16,12 @@
static void sof_reset_route_setup_status(struct snd_sof_dev *sdev, struct snd_sof_widget *widget)
{
- const struct sof_ipc_tplg_ops *tplg_ops = sdev->ipc->ops->tplg;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
struct snd_sof_route *sroute;
list_for_each_entry(sroute, &sdev->route_list, list)
if (sroute->src_widget == widget || sroute->sink_widget == widget) {
- if (sroute->setup && tplg_ops->route_free)
+ if (sroute->setup && tplg_ops && tplg_ops->route_free)
tplg_ops->route_free(sdev, sroute);
sroute->setup = false;
@@ -30,7 +30,7 @@ static void sof_reset_route_setup_status(struct snd_sof_dev *sdev, struct snd_so
int sof_widget_free(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
{
- const struct sof_ipc_tplg_ops *tplg_ops = sdev->ipc->ops->tplg;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
int err = 0;
int ret;
@@ -47,7 +47,7 @@ int sof_widget_free(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
sof_reset_route_setup_status(sdev, swidget);
/* continue to disable core even if IPC fails */
- if (tplg_ops->widget_free)
+ if (tplg_ops && tplg_ops->widget_free)
err = tplg_ops->widget_free(sdev, swidget);
/*
@@ -82,7 +82,7 @@ EXPORT_SYMBOL(sof_widget_free);
int sof_widget_setup(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
{
- const struct sof_ipc_tplg_ops *tplg_ops = sdev->ipc->ops->tplg;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
int ret;
/* skip if there is no private data */
@@ -124,7 +124,7 @@ int sof_widget_setup(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
}
/* setup widget in the DSP */
- if (tplg_ops->widget_setup) {
+ if (tplg_ops && tplg_ops->widget_setup) {
ret = tplg_ops->widget_setup(sdev, swidget);
if (ret < 0)
goto core_put;
@@ -134,7 +134,7 @@ int sof_widget_setup(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
if (WIDGET_IS_DAI(swidget->id)) {
unsigned int flags = SOF_DAI_CONFIG_FLAGS_NONE;
- if (tplg_ops->dai_config) {
+ if (tplg_ops && tplg_ops->dai_config) {
ret = tplg_ops->dai_config(sdev, swidget, flags, NULL);
if (ret < 0)
goto widget_free;
@@ -142,7 +142,7 @@ int sof_widget_setup(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
}
/* restore kcontrols for widget */
- if (tplg_ops->control->widget_kcontrol_setup) {
+ if (tplg_ops && tplg_ops->control && tplg_ops->control->widget_kcontrol_setup) {
ret = tplg_ops->control->widget_kcontrol_setup(sdev, swidget);
if (ret < 0)
goto widget_free;
@@ -169,7 +169,7 @@ EXPORT_SYMBOL(sof_widget_setup);
int sof_route_setup(struct snd_sof_dev *sdev, struct snd_soc_dapm_widget *wsource,
struct snd_soc_dapm_widget *wsink)
{
- const struct sof_ipc_tplg_ops *ipc_tplg_ops = sdev->ipc->ops->tplg;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
struct snd_sof_widget *src_widget = wsource->dobj.private;
struct snd_sof_widget *sink_widget = wsink->dobj.private;
struct snd_sof_route *sroute;
@@ -211,8 +211,8 @@ int sof_route_setup(struct snd_sof_dev *sdev, struct snd_soc_dapm_widget *wsourc
if (sroute->setup)
return 0;
- if (ipc_tplg_ops->route_setup) {
- int ret = ipc_tplg_ops->route_setup(sdev, sroute);
+ if (tplg_ops && tplg_ops->route_setup) {
+ int ret = tplg_ops->route_setup(sdev, sroute);
if (ret < 0)
return ret;
@@ -268,16 +268,17 @@ static int sof_setup_pipeline_connections(struct snd_sof_dev *sdev,
static void
sof_unprepare_widgets_in_path(struct snd_sof_dev *sdev, struct snd_soc_dapm_widget *widget)
{
- const struct sof_ipc_tplg_ops *ipc_tplg_ops = sdev->ipc->ops->tplg;
- const struct sof_ipc_tplg_widget_ops *widget_ops = ipc_tplg_ops->widget;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
struct snd_sof_widget *swidget = widget->dobj.private;
+ const struct sof_ipc_tplg_widget_ops *widget_ops;
struct snd_soc_dapm_path *p;
/* return if the widget is in use or if it is already unprepared */
if (!swidget->prepared || swidget->use_count > 1)
return;
- if (widget_ops[widget->id].ipc_unprepare)
+ widget_ops = tplg_ops ? tplg_ops->widget : NULL;
+ if (widget_ops && widget_ops[widget->id].ipc_unprepare)
/* unprepare the source widget */
widget_ops[widget->id].ipc_unprepare(swidget);
@@ -299,12 +300,16 @@ sof_prepare_widgets_in_path(struct snd_sof_dev *sdev, struct snd_soc_dapm_widget
struct snd_sof_platform_stream_params *platform_params,
struct snd_pcm_hw_params *pipeline_params, int dir)
{
- const struct sof_ipc_tplg_ops *ipc_tplg_ops = sdev->ipc->ops->tplg;
- const struct sof_ipc_tplg_widget_ops *widget_ops = ipc_tplg_ops->widget;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
struct snd_sof_widget *swidget = widget->dobj.private;
+ const struct sof_ipc_tplg_widget_ops *widget_ops;
struct snd_soc_dapm_path *p;
int ret;
+ widget_ops = tplg_ops ? tplg_ops->widget : NULL;
+ if (!widget_ops)
+ return 0;
+
if (!widget_ops[widget->id].ipc_prepare || swidget->prepared)
goto sink_prepare;
@@ -485,7 +490,7 @@ int sof_widget_list_setup(struct snd_sof_dev *sdev, struct snd_sof_pcm *spcm,
struct snd_sof_platform_stream_params *platform_params,
int dir)
{
- const struct sof_ipc_tplg_ops *ipc_tplg_ops = sdev->ipc->ops->tplg;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
struct snd_soc_dapm_widget_list *list = spcm->stream[dir].list;
struct snd_soc_dapm_widget *widget;
int i, ret;
@@ -539,8 +544,8 @@ int sof_widget_list_setup(struct snd_sof_dev *sdev, struct snd_sof_pcm *spcm,
if (pipe_widget->complete)
continue;
- if (ipc_tplg_ops->pipeline_complete) {
- pipe_widget->complete = ipc_tplg_ops->pipeline_complete(sdev, pipe_widget);
+ if (tplg_ops && tplg_ops->pipeline_complete) {
+ pipe_widget->complete = tplg_ops->pipeline_complete(sdev, pipe_widget);
if (pipe_widget->complete < 0) {
ret = pipe_widget->complete;
goto widget_free;
@@ -628,11 +633,11 @@ bool snd_sof_stream_suspend_ignored(struct snd_sof_dev *sdev)
int sof_pcm_stream_free(struct snd_sof_dev *sdev, struct snd_pcm_substream *substream,
struct snd_sof_pcm *spcm, int dir, bool free_widget_list)
{
- const struct sof_ipc_pcm_ops *pcm_ops = sdev->ipc->ops->pcm;
+ const struct sof_ipc_pcm_ops *pcm_ops = sof_ipc_get_ops(sdev, pcm);
int ret;
/* Send PCM_FREE IPC to reset pipeline */
- if (pcm_ops->hw_free && spcm->prepared[substream->stream]) {
+ if (pcm_ops && pcm_ops->hw_free && spcm->prepared[substream->stream]) {
ret = pcm_ops->hw_free(sdev->component, substream);
if (ret < 0)
return ret;
@@ -762,13 +767,13 @@ static int sof_dai_get_clk(struct snd_soc_pcm_runtime *rtd, int clk_type)
struct snd_sof_dai *dai =
snd_sof_find_dai(component, (char *)rtd->dai_link->name);
struct snd_sof_dev *sdev = snd_soc_component_get_drvdata(component);
- const struct sof_ipc_tplg_ops *tplg_ops = sdev->ipc->ops->tplg;
+ const struct sof_ipc_tplg_ops *tplg_ops = sof_ipc_get_ops(sdev, tplg);
/* use the tplg configured mclk if existed */
if (!dai)
return 0;
- if (tplg_ops->dai_get_clk)
+ if (tplg_ops && tplg_ops->dai_get_clk)
return tplg_ops->dai_get_clk(sdev, dai, clk_type);
return 0;
--
2.39.0
next prev parent reply other threads:[~2022-12-21 10:26 UTC|newest]
Thread overview: 13+ messages / expand[flat|nested] mbox.gz Atom feed top
2022-12-21 10:23 [PATCH 00/11] ASoC: SOF: Extend the IPC ops optionality Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 01/11] ASoC: SOF: sof-audio: Treat tplg_ops->route_setup() as optional Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 02/11] ASoC: SOF: sof-audio: Update documentation for sof_ipc_tplg_ops Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 03/11] ASoC: SOF: Add helper macro to be used to get an IPC ops Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 04/11] ASoC: SOF: pcm: Extend the optionality of IPC ops to IPC as well Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 05/11] ASoC: SOF: control: " Peter Ujfalusi
2022-12-21 10:23 ` Peter Ujfalusi [this message]
2022-12-21 10:23 ` [PATCH 07/11] ASoC: SOF: topology: " Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 08/11] ASoC: SOF: pm: " Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 09/11] ASoC: SOF: sof-priv: Mark fw_tracing ops optional in documentation Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 10/11] ASoC: SOF: trace: Use sof_ipc_get_ops() in sof_fw_trace_init Peter Ujfalusi
2022-12-21 10:23 ` [PATCH 11/11] ASoC: SOF: trace: No need to check for op pointer in sof_fw_trace_free() Peter Ujfalusi
2022-12-27 11:57 ` [PATCH 00/11] ASoC: SOF: Extend the IPC ops optionality Mark Brown
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20221221102328.9635-7-peter.ujfalusi@linux.intel.com \
--to=peter.ujfalusi@linux.intel.com \
--cc=alsa-devel@alsa-project.org \
--cc=broonie@kernel.org \
--cc=kai.vehmanen@linux.intel.com \
--cc=lgirdwood@gmail.com \
--cc=pierre-louis.bossart@linux.intel.com \
--cc=rander.wang@intel.com \
--cc=ranjani.sridharan@linux.intel.com \
--cc=yung-chuan.liao@linux.intel.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox