Skip to content

Commit 21a3e58

Browse files
committed
ipc: ipc4: extract pipeline ID detection into a function
The SOF_IPC4_GLB_SET_PIPELINE_STATE IPC can apply to one or to multiple pipelines. Extract pipeline ID detection into a function to be re-used with userspace IPC processing. Signed-off-by: Guennadi Liakhovetski <guennadi.liakhovetski@linux.intel.com>
1 parent 07b2acd commit 21a3e58

1 file changed

Lines changed: 44 additions & 25 deletions

File tree

src/ipc/ipc4/handler-user.c

Lines changed: 44 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -423,6 +423,44 @@ __cold const struct ipc4_pipeline_set_state_data *ipc4_get_pipeline_data_wrapper
423423
return ipc4_get_pipeline_data();
424424
}
425425

426+
static int ipc4_pipeline_id_get(struct ipc4_message_request *ipc4,
427+
struct ipc4_pipeline_set_state *state,
428+
const uint32_t **ppl_id, unsigned int *ppl_count)
429+
{
430+
if (!state->extension.r.multi_ppl) {
431+
if (ppl_count)
432+
*ppl_count = 1;
433+
if (ppl_id)
434+
*ppl_id = NULL;
435+
return state->primary.r.ppl_id;
436+
}
437+
438+
const struct ipc4_pipeline_set_state_data *ppl_data = ipc4_get_pipeline_data();
439+
unsigned int cnt = ppl_data->pipelines_count;
440+
441+
/*
442+
* pipelines_count is read straight from the host-provided
443+
* mailbox payload, so cap it at what the mailbox can
444+
* physically hold. Anything larger means the host promised
445+
* more ppl_id[] entries than fit in MAILBOX_HOSTBOX, and
446+
* dereferencing the flex array would read out of bounds.
447+
*/
448+
if (cnt > (MAILBOX_HOSTBOX_SIZE - sizeof(struct ipc4_pipeline_set_state_data)) /
449+
sizeof(uint32_t)) {
450+
ipc_cmd_err(&ipc_tr, "ipc: pipelines_count %u exceeds mailbox bound",
451+
cnt);
452+
return -EINVAL;
453+
}
454+
dcache_invalidate_region((__sparse_force void __sparse_cache *)ppl_data->ppl_id,
455+
sizeof(int) * cnt);
456+
if (ppl_count)
457+
*ppl_count = cnt;
458+
if (ppl_id)
459+
*ppl_id = ppl_data->ppl_id;
460+
461+
return ppl_data->ppl_id[0];
462+
}
463+
426464
/**
427465
* \brief Process SET_PIPELINE_STATE IPC4 message (prepare + trigger phases).
428466
* @param[in] ipc4 IPC4 message request.
@@ -435,7 +473,7 @@ int ipc4_set_pipeline_state(struct ipc4_message_request *ipc4)
435473
struct ipc_comp_dev *ppl_icd;
436474
struct ipc *ipc = ipc_get();
437475
uint32_t cmd, ppl_count;
438-
uint32_t id = 0;
476+
int id;
439477
const uint32_t *ppl_id;
440478
bool use_idc = false;
441479
uint32_t idx;
@@ -447,31 +485,12 @@ int ipc4_set_pipeline_state(struct ipc4_message_request *ipc4)
447485
cmd = state.primary.r.ppl_state;
448486
ppl_data = ipc4_get_pipeline_data();
449487

450-
if (state.extension.r.multi_ppl) {
451-
ppl_count = ppl_data->pipelines_count;
452-
/*
453-
* pipelines_count is read straight from the host-provided
454-
* mailbox payload, so cap it at what the mailbox can
455-
* physically hold. Anything larger means the host promised
456-
* more ppl_id[] entries than fit in MAILBOX_HOSTBOX, and
457-
* dereferencing the flex array would read out of bounds.
458-
*/
459-
if (ppl_count > (MAILBOX_HOSTBOX_SIZE -
460-
sizeof(struct ipc4_pipeline_set_state_data)) /
461-
sizeof(uint32_t)) {
462-
ipc_cmd_err(&ipc_tr,
463-
"ipc: pipelines_count %u exceeds mailbox bound",
464-
ppl_count);
465-
return IPC4_ERROR_INVALID_PARAM;
466-
}
467-
ppl_id = ppl_data->ppl_id;
468-
dcache_invalidate_region((__sparse_force void __sparse_cache *)ppl_id,
469-
sizeof(int) * ppl_count);
470-
} else {
471-
ppl_count = 1;
472-
id = state.primary.r.ppl_id;
488+
id = ipc4_pipeline_id_get(ipc4, &state, &ppl_id, &ppl_count);
489+
if (id < 0)
490+
return IPC4_ERROR_INVALID_PARAM;
491+
492+
if (ppl_count == 1)
473493
ppl_id = &id;
474-
}
475494

476495
for (i = 0; i < ppl_count; i++) {
477496
ppl_icd = ipc_get_comp_by_ppl_id(ipc, COMP_TYPE_PIPELINE,

0 commit comments

Comments
 (0)