return -EINVAL;
}
+static int sof_ipc3_complete_pipeline(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget)
+{
+ struct sof_ipc_pipe_ready ready;
+ struct sof_ipc_reply reply;
+ int ret;
+
+ dev_dbg(sdev->dev, "tplg: complete pipeline %s id %d\n",
+ swidget->widget->name, swidget->comp_id);
+
+ memset(&ready, 0, sizeof(ready));
+ ready.hdr.size = sizeof(ready);
+ ready.hdr.cmd = SOF_IPC_GLB_TPLG_MSG | SOF_IPC_TPLG_PIPE_COMPLETE;
+ ready.comp_id = swidget->comp_id;
+
+ ret = sof_ipc_tx_message(sdev->ipc, ready.hdr.cmd, &ready, sizeof(ready), &reply,
+ sizeof(reply));
+ if (ret < 0)
+ return ret;
+
+ return 1;
+}
+
/* token list for each topology object */
static enum sof_tokens host_token_list[] = {
SOF_CORE_TOKENS,
.route_setup = sof_ipc3_route_setup,
.control_setup = sof_ipc3_control_setup,
.control_free = sof_ipc3_control_free,
+ .pipeline_complete = sof_ipc3_complete_pipeline,
.token_list = ipc3_token_list,
};
int sof_widget_list_setup(struct snd_sof_dev *sdev, struct snd_sof_pcm *spcm, int dir)
{
+ const struct sof_ipc_tplg_ops *ipc_tplg_ops = sdev->ipc->ops->tplg;
struct snd_soc_dapm_widget_list *list = spcm->stream[dir].list;
struct snd_soc_dapm_widget *widget;
int i, ret, num_widgets;
if (pipe_widget->complete)
continue;
- pipe_widget->complete = snd_sof_complete_pipeline(sdev, pipe_widget);
- if (pipe_widget->complete < 0) {
- ret = pipe_widget->complete;
- goto widget_free;
+ if (ipc_tplg_ops->pipeline_complete) {
+ pipe_widget->complete = ipc_tplg_ops->pipeline_complete(sdev, pipe_widget);
+ if (pipe_widget->complete < 0) {
+ ret = pipe_widget->complete;
+ goto widget_free;
+ }
}
}
return ret;
}
- swidget->complete =
- snd_sof_complete_pipeline(sdev, swidget);
+ if (ipc_tplg_ops->pipeline_complete) {
+ swidget->complete = ipc_tplg_ops->pipeline_complete(sdev, swidget);
+ if (swidget->complete < 0)
+ return swidget->complete;
+ }
break;
default:
break;
* initialized to 0.
* @control_setup: Function pointer for setting up kcontrol IPC-specific data
* @control_free: Function pointer for freeing kcontrol IPC-specific data
+ * @pipeline_complete: Function pointer for pipeline complete IPC
*/
struct sof_ipc_tplg_ops {
const struct sof_ipc_tplg_widget_ops *widget;
const struct sof_token_info *token_list;
int (*control_setup)(struct snd_sof_dev *sdev, struct snd_sof_control *scontrol);
int (*control_free)(struct snd_sof_dev *sdev, struct snd_sof_control *scontrol);
+ int (*pipeline_complete)(struct snd_sof_dev *sdev, struct snd_sof_widget *swidget);
};
/** struct snd_sof_tuple - Tuple info
* be freed by snd_soc_unregister_component,
*/
int snd_sof_load_topology(struct snd_soc_component *scomp, const char *file);
-int snd_sof_complete_pipeline(struct snd_sof_dev *sdev,
- struct snd_sof_widget *swidget);
/*
* Stream IPC
return ret;
}
-int snd_sof_complete_pipeline(struct snd_sof_dev *sdev,
- struct snd_sof_widget *swidget)
-{
- struct sof_ipc_pipe_ready ready;
- struct sof_ipc_reply reply;
- int ret;
-
- dev_dbg(sdev->dev, "tplg: complete pipeline %s id %d\n",
- swidget->widget->name, swidget->comp_id);
-
- memset(&ready, 0, sizeof(ready));
- ready.hdr.size = sizeof(ready);
- ready.hdr.cmd = SOF_IPC_GLB_TPLG_MSG | SOF_IPC_TPLG_PIPE_COMPLETE;
- ready.comp_id = swidget->comp_id;
-
- ret = sof_ipc_tx_message(sdev->ipc,
- ready.hdr.cmd, &ready, sizeof(ready), &reply,
- sizeof(reply));
- if (ret < 0)
- return ret;
- return 1;
-}
-
/**
* sof_set_pipe_widget - Set pipe_widget for a component
* @sdev: pointer to struct snd_sof_dev