Skip to content

Commit 5c3c095

Browse files
author
Jyri Sarha
committed
ipc4: Handler: Add ipc4_create_pipeline_payload_decode() and call it
Add ipc4_create_pipeline_payload_decode() and call it if struct ipc4_pipeline_create's extension.r.payload bit is set. The function decodes the message payload, logs the contents, but does not store the information anywhere. Signed-off-by: Jyri Sarha <jyri.sarha@linux.intel.com>
1 parent 40e0638 commit 5c3c095

File tree

1 file changed

+97
-0
lines changed

1 file changed

+97
-0
lines changed

src/ipc/ipc4/helper.c

Lines changed: 97 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -229,6 +229,76 @@ struct ipc_comp_dev *ipc_get_comp_by_ppl_id(struct ipc *ipc, uint16_t type,
229229
return NULL;
230230
}
231231

232+
/*
233+
* This function currently only decodes the payload and prints out
234+
* data it finds, but it does not store it anywhere.
235+
*/
236+
__cold static int ipc4_create_pipeline_payload_decode(char *data)
237+
{
238+
const struct ipc4_pipeline_ext_payload *hdr =
239+
(struct ipc4_pipeline_ext_payload *)data;
240+
const struct ipc4_pipeline_ext_object *obj;
241+
size_t size = hdr->payload_words * sizeof(uint32_t);
242+
bool last_object = !hdr->data_obj_array;
243+
244+
if (hdr->payload_words * sizeof(uint32_t) < sizeof(*hdr)) {
245+
tr_err(&ipc_tr, "Payload size too small: %u : %#x", hdr->payload_words,
246+
*((uint32_t *)hdr));
247+
return -EINVAL;
248+
}
249+
250+
tr_info(&ipc_tr, "payload size %u array %u: %#x", hdr->payload_words, hdr->data_obj_array,
251+
*((uint32_t *)hdr));
252+
253+
obj = (const struct ipc4_pipeline_ext_object *)(hdr + 1);
254+
while (!last_object) {
255+
const struct ipc4_pipeline_ext_object *next_obj;
256+
257+
/* Check if there is space for the object header */
258+
if ((char *)(obj + 1) - data > size) {
259+
tr_err(&ipc_tr, "obj header overflow, %u > %u",
260+
(char *)(obj + 1) - data, size);
261+
return -EINVAL;
262+
}
263+
264+
/* Calculate would be next object position and check if current object fits */
265+
next_obj = (const struct ipc4_pipeline_ext_object *)
266+
(((uint32_t *)(obj + 1)) + obj->object_words);
267+
if ((char *)next_obj - data > size) {
268+
tr_err(&ipc_tr, "object size overflow, %u > %u",
269+
(char *)obj - data, size);
270+
return -EINVAL;
271+
}
272+
273+
switch (obj->object_id) {
274+
case IPC4_GLB_PIPE_EXT_OBJ_ID_MEM_DATA:
275+
{
276+
/* Get mem_data struct that follows the obj struct */
277+
const struct ipc4_pipeline_ext_obj_mem_data *mem_data =
278+
(const struct ipc4_pipeline_ext_obj_mem_data *)(obj + 1);
279+
280+
if (obj->object_words * sizeof(uint32_t) < sizeof(*mem_data)) {
281+
tr_err(&ipc_tr, "mem_data object does not fit %u < %u",
282+
obj->object_words * sizeof(uint32_t), sizeof(*mem_data));
283+
return -EINVAL;
284+
}
285+
tr_info(&ipc_tr, "init_ext_obj_mem_data domain %u stack %u heap %u",
286+
mem_data->domain_id, mem_data->stack_bytes, mem_data->heap_bytes);
287+
break;
288+
}
289+
default:
290+
tr_info(&ipc_tr, "Unknown ext init object id %u of %u words",
291+
obj->object_id, obj->object_words);
292+
}
293+
/* Read the last object flag from obj header */
294+
last_object = obj->last_object;
295+
/* Move to next object */
296+
obj = next_obj;
297+
}
298+
299+
return 0;
300+
}
301+
232302
__cold static int ipc4_create_pipeline(struct ipc4_pipeline_create *pipe_desc)
233303
{
234304
struct ipc_comp_dev *ipc_pipe;
@@ -280,6 +350,23 @@ __cold static int ipc4_create_pipeline(struct ipc4_pipeline_create *pipe_desc)
280350
return IPC4_SUCCESS;
281351
}
282352

353+
#if CONFIG_LIBRARY
354+
static inline char *ipc4_get_pipe_create_data(void)
355+
{
356+
struct ipc *ipc = ipc_get();
357+
char *data = (char *)ipc->comp_data + sizeof(struct ipc4_pipeline_create);
358+
359+
return data;
360+
}
361+
#else
362+
__cold static inline char *ipc4_get_pipe_create_data(void)
363+
{
364+
assert_can_be_cold();
365+
366+
return (char *)MAILBOX_HOSTBOX_BASE;
367+
}
368+
#endif
369+
283370
/* Only called from ipc4_new_pipeline(), which is __cold */
284371
__cold int ipc_pipeline_new(struct ipc *ipc, ipc_pipe_new *_pipe_desc)
285372
{
@@ -293,6 +380,16 @@ __cold int ipc_pipeline_new(struct ipc *ipc, ipc_pipe_new *_pipe_desc)
293380
if (!cpu_is_me(pipe_desc->extension.r.core_id))
294381
return ipc4_process_on_core(pipe_desc->extension.r.core_id, false);
295382

383+
if (pipe_desc->extension.r.payload) {
384+
char *data;
385+
386+
dcache_invalidate_region((__sparse_force void __sparse_cache *)MAILBOX_HOSTBOX_BASE,
387+
MAILBOX_HOSTBOX_SIZE);
388+
data = ipc4_get_pipe_create_data();
389+
390+
ipc4_create_pipeline_payload_decode(data);
391+
}
392+
296393
return ipc4_create_pipeline(pipe_desc);
297394
}
298395

0 commit comments

Comments
 (0)