diff --git a/app/boards/intel_adsp_ace30_ptl.conf b/app/boards/intel_adsp_ace30_ptl.conf index e1fcabd91fa4..2468f5cebf32 100644 --- a/app/boards/intel_adsp_ace30_ptl.conf +++ b/app/boards/intel_adsp_ace30_ptl.conf @@ -42,6 +42,7 @@ CONFIG_LIBRARY_MANAGER=y CONFIG_LIBRARY_BASE_ADDRESS=0xa0688000 CONFIG_LIBRARY_BUILD_LIB=y CONFIG_LIBRARY_DEFAULT_MODULAR=y +CONFIG_COLD_STORE_EXECUTE_DRAM=y # SOF / logging CONFIG_SOF_LOG_LEVEL_INF=y diff --git a/src/include/sof/ipc/topology.h b/src/include/sof/ipc/topology.h index 3503c7a407d8..5605c6ef9837 100644 --- a/src/include/sof/ipc/topology.h +++ b/src/include/sof/ipc/topology.h @@ -49,6 +49,8 @@ typedef uint32_t ipc_comp; struct ipc_comp_dev; const struct comp_driver *ipc4_get_comp_drv(uint32_t module_id); struct comp_dev *ipc4_get_comp_dev(uint32_t comp_id); +int ipc4_add_comp_dev(struct comp_dev *dev); +const struct comp_driver *ipc4_get_drv(const void *uuid); int ipc4_chain_manager_create(struct ipc4_chain_dma *cdma); int ipc4_chain_dma_state(struct comp_dev *dev, struct ipc4_chain_dma *cdma); int ipc4_create_chain_dma(struct ipc *ipc, struct ipc4_chain_dma *cdma); diff --git a/src/ipc/ipc-common.c b/src/ipc/ipc-common.c index 3c81064cb7cd..8f72ac1ba91b 100644 --- a/src/ipc/ipc-common.c +++ b/src/ipc/ipc-common.c @@ -20,7 +20,6 @@ #include #include #include -#include #include #include #include @@ -189,14 +188,12 @@ static void schedule_ipc_worker(void) #endif } -__cold void ipc_msg_send_direct(struct ipc_msg *msg, void *data) +void ipc_msg_send_direct(struct ipc_msg *msg, void *data) { struct ipc *ipc = ipc_get(); k_spinlock_key_t key; int ret; - assert_can_be_cold(); - key = k_spin_lock(&ipc->lock); /* copy mailbox data to message if not already copied */ @@ -283,10 +280,8 @@ void ipc_schedule_process(struct ipc *ipc) #endif } -__cold int ipc_init(struct sof *sof) +int ipc_init(struct sof *sof) { - assert_can_be_cold(); - tr_dbg(&ipc_tr, "ipc_init()"); /* init ipc data */ diff --git a/src/ipc/ipc-helper.c b/src/ipc/ipc-helper.c index 65910767d95e..1d1b651d1c49 100644 --- a/src/ipc/ipc-helper.c +++ b/src/ipc/ipc-helper.c @@ -21,7 +21,6 @@ #include #include #include -#include #include #include #include @@ -38,10 +37,8 @@ LOG_MODULE_DECLARE(ipc, CONFIG_SOF_LOG_LEVEL); -__cold static bool valid_ipc_buffer_desc(const struct sof_ipc_buffer *desc) +static bool valid_ipc_buffer_desc(const struct sof_ipc_buffer *desc) { - assert_can_be_cold(); - if (desc->caps >= SOF_MEM_CAPS_LOWEST_INVALID) return false; @@ -50,12 +47,10 @@ __cold static bool valid_ipc_buffer_desc(const struct sof_ipc_buffer *desc) } /* create a new component in the pipeline */ -__cold struct comp_buffer *buffer_new(const struct sof_ipc_buffer *desc, bool is_shared) +struct comp_buffer *buffer_new(const struct sof_ipc_buffer *desc, bool is_shared) { struct comp_buffer *buffer; - assert_can_be_cold(); - tr_info(&buffer_tr, "buffer new size 0x%x id %d.%d flags 0x%x", desc->size, desc->comp.pipeline_id, desc->comp.id, desc->flags); @@ -80,7 +75,6 @@ __cold struct comp_buffer *buffer_new(const struct sof_ipc_buffer *desc, bool is return buffer; } -/* Called from multiple locations, including ipc_get_comp_by_ppl_id(), so cannot be cold */ int32_t ipc_comp_pipe_id(const struct ipc_comp_dev *icd) { switch (icd->type) { @@ -183,11 +177,9 @@ int comp_verify_params(struct comp_dev *dev, uint32_t flag, } EXPORT_SYMBOL(comp_verify_params); -__cold int comp_buffer_connect(struct comp_dev *comp, uint32_t comp_core, - struct comp_buffer *buffer, uint32_t dir) +int comp_buffer_connect(struct comp_dev *comp, uint32_t comp_core, + struct comp_buffer *buffer, uint32_t dir) { - assert_can_be_cold(); - /* check if it's a connection between cores */ if (buffer->core != comp_core) { #if CONFIG_INCOHERENT @@ -266,15 +258,13 @@ int ipc_pipeline_complete(struct ipc *ipc, uint32_t comp_id) ipc_ppl_sink->cd); } -__cold int ipc_comp_free(struct ipc *ipc, uint32_t comp_id) +int ipc_comp_free(struct ipc *ipc, uint32_t comp_id) { struct ipc_comp_dev *icd; struct comp_buffer *buffer; struct comp_buffer *safe; uint32_t flags; - assert_can_be_cold(); - /* check whether component exists */ icd = ipc_get_comp_by_id(ipc, comp_id); if (!icd) { diff --git a/src/ipc/ipc4/handler.c b/src/ipc/ipc4/handler.c index dbffb96e415d..65056289e71d 100644 --- a/src/ipc/ipc4/handler.c +++ b/src/ipc/ipc4/handler.c @@ -21,7 +21,6 @@ #include #include #include -#include #include #include #include @@ -132,22 +131,18 @@ static inline const struct ipc4_pipeline_set_state_data *ipc4_get_pipeline_data( /* * Global IPC Operations. */ -__cold static int ipc4_new_pipeline(struct ipc4_message_request *ipc4) +static int ipc4_new_pipeline(struct ipc4_message_request *ipc4) { struct ipc *ipc = ipc_get(); - assert_can_be_cold(); - return ipc_pipeline_new(ipc, (ipc_pipe_new *)ipc4); } -__cold static int ipc4_delete_pipeline(struct ipc4_message_request *ipc4) +static int ipc4_delete_pipeline(struct ipc4_message_request *ipc4) { struct ipc4_pipeline_delete *pipe; struct ipc *ipc = ipc_get(); - assert_can_be_cold(); - pipe = (struct ipc4_pipeline_delete *)ipc4; tr_dbg(&ipc_tr, "ipc4 delete pipeline %x:", (uint32_t)pipe->primary.r.instance_id); @@ -234,13 +229,11 @@ static int ipc4_pcm_params(struct ipc_comp_dev *pcm_dev) return err; } -__cold static bool is_any_ppl_active(void) +static bool is_any_ppl_active(void) { struct ipc_comp_dev *icd; struct list_item *clist; - assert_can_be_cold(); - list_for_item(clist, &ipc_get()->comp_list) { icd = container_of(clist, struct ipc_comp_dev, list); if (icd->type != COMP_TYPE_PIPELINE) @@ -569,14 +562,15 @@ static int ipc_wait_for_compound_msg(void) } #endif -__cold const struct ipc4_pipeline_set_state_data *ipc4_get_pipeline_data_wrapper(void) +const struct ipc4_pipeline_set_state_data *ipc4_get_pipeline_data_wrapper(void) { - assert_can_be_cold(); + const struct ipc4_pipeline_set_state_data *ppl_data; - return ipc4_get_pipeline_data(); + ppl_data = ipc4_get_pipeline_data(); + + return ppl_data; } -/* Entry point for ipc4_pipeline_trigger(), therefore cannot be cold */ static int ipc4_set_pipeline_state(struct ipc4_message_request *ipc4) { const struct ipc4_pipeline_set_state_data *ppl_data; @@ -706,13 +700,11 @@ static int ipc4_set_pipeline_state(struct ipc4_message_request *ipc4) } #if CONFIG_LIBRARY_MANAGER -__cold static int ipc4_load_library(struct ipc4_message_request *ipc4) +static int ipc4_load_library(struct ipc4_message_request *ipc4) { struct ipc4_module_load_library library; int ret; - assert_can_be_cold(); - library.header.dat = ipc4->primary.dat; ret = lib_manager_load_library(library.header.r.dma_id, library.header.r.lib_id, @@ -724,10 +716,8 @@ __cold static int ipc4_load_library(struct ipc4_message_request *ipc4) } #endif -__cold static int ipc4_process_chain_dma(struct ipc4_message_request *ipc4) +static int ipc4_process_chain_dma(struct ipc4_message_request *ipc4) { - assert_can_be_cold(); - #if CONFIG_COMP_CHAIN_DMA struct ipc_comp_dev *cdma_comp; struct ipc *ipc = ipc_get(); @@ -781,10 +771,8 @@ __cold static int ipc4_process_chain_dma(struct ipc4_message_request *ipc4) #endif } -__cold static int ipc4_process_ipcgtw_cmd(struct ipc4_message_request *ipc4) +static int ipc4_process_ipcgtw_cmd(struct ipc4_message_request *ipc4) { - assert_can_be_cold(); - #if CONFIG_IPC4_GATEWAY struct ipc *ipc = ipc_get(); uint32_t reply_size = 0; @@ -892,15 +880,14 @@ __cold static int ipc4_init_module_instance(struct ipc4_message_request *ipc4) { struct ipc4_module_init_instance module_init; struct comp_dev *dev; - - assert_can_be_cold(); - /* we only need the common header here, all we have from the IPC */ int ret = memcpy_s(&module_init, sizeof(module_init), ipc4, sizeof(*ipc4)); if (ret < 0) return IPC4_FAILURE; + assert_can_be_cold(); + tr_dbg(&ipc_tr, "ipc4_init_module_instance %x : %x", (uint32_t)module_init.primary.r.module_id, @@ -921,13 +908,10 @@ __cold static int ipc4_init_module_instance(struct ipc4_message_request *ipc4) return 0; } -__cold static int ipc4_bind_module_instance(struct ipc4_message_request *ipc4) +static int ipc4_bind_module_instance(struct ipc4_message_request *ipc4) { struct ipc4_module_bind_unbind bu; struct ipc *ipc = ipc_get(); - - assert_can_be_cold(); - int ret = memcpy_s(&bu, sizeof(bu), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -940,13 +924,10 @@ __cold static int ipc4_bind_module_instance(struct ipc4_message_request *ipc4) return ipc_comp_connect(ipc, (ipc_pipe_comp_connect *)&bu); } -__cold static int ipc4_unbind_module_instance(struct ipc4_message_request *ipc4) +static int ipc4_unbind_module_instance(struct ipc4_message_request *ipc4) { struct ipc4_module_bind_unbind bu; struct ipc *ipc = ipc_get(); - - assert_can_be_cold(); - int ret = memcpy_s(&bu, sizeof(bu), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -959,7 +940,7 @@ __cold static int ipc4_unbind_module_instance(struct ipc4_message_request *ipc4) return ipc_comp_disconnect(ipc, (ipc_pipe_comp_connect *)&bu); } -__cold static int ipc4_get_vendor_config_module_instance(struct comp_dev *dev, +static int ipc4_get_vendor_config_module_instance(struct comp_dev *dev, const struct comp_driver *drv, bool init_block, bool final_block, @@ -971,8 +952,6 @@ __cold static int ipc4_get_vendor_config_module_instance(struct comp_dev *dev, int ret; struct ipc4_vendor_error *error; - assert_can_be_cold(); - if (init_block && final_block) { /* we use data_off_size as in/out, * save value to new variable so it can be used as out size @@ -1054,7 +1033,7 @@ __cold static int ipc4_get_vendor_config_module_instance(struct comp_dev *dev, return IPC4_SUCCESS; } -__cold static int ipc4_get_large_config_module_instance(struct ipc4_message_request *ipc4) +static int ipc4_get_large_config_module_instance(struct ipc4_message_request *ipc4) { struct ipc4_module_large_config_reply reply; struct ipc4_module_large_config config; @@ -1062,9 +1041,6 @@ __cold static int ipc4_get_large_config_module_instance(struct ipc4_message_requ const struct comp_driver *drv; struct comp_dev *dev = NULL; uint32_t data_offset; - - assert_can_be_cold(); - int ret = memcpy_s(&config, sizeof(config), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -1149,7 +1125,7 @@ __cold static int ipc4_get_large_config_module_instance(struct ipc4_message_requ return ret; } -__cold static int ipc4_set_vendor_config_module_instance(struct comp_dev *dev, +static int ipc4_set_vendor_config_module_instance(struct comp_dev *dev, const struct comp_driver *drv, uint32_t module_id, uint32_t instance_id, @@ -1160,8 +1136,6 @@ __cold static int ipc4_set_vendor_config_module_instance(struct comp_dev *dev, { int ret; - assert_can_be_cold(); - /* Old FW comment: bursted configs */ if (init_block && final_block) { const struct sof_tlv *tlv = (struct sof_tlv *)data; @@ -1214,14 +1188,11 @@ __cold static int ipc4_set_vendor_config_module_instance(struct comp_dev *dev, data_off_size, data); } -__cold static int ipc4_set_large_config_module_instance(struct ipc4_message_request *ipc4) +static int ipc4_set_large_config_module_instance(struct ipc4_message_request *ipc4) { struct ipc4_module_large_config config; struct comp_dev *dev = NULL; const struct comp_driver *drv; - - assert_can_be_cold(); - int ret = memcpy_s(&config, sizeof(config), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -1285,14 +1256,11 @@ __cold static int ipc4_set_large_config_module_instance(struct ipc4_message_requ return ret; } -__cold static int ipc4_delete_module_instance(struct ipc4_message_request *ipc4) +static int ipc4_delete_module_instance(struct ipc4_message_request *ipc4) { struct ipc4_module_delete_instance module; struct ipc *ipc = ipc_get(); uint32_t comp_id; - - assert_can_be_cold(); - int ret = memcpy_s(&module, sizeof(module), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -1314,13 +1282,10 @@ __cold static int ipc4_delete_module_instance(struct ipc4_message_request *ipc4) } /* disable power gating on core 0 */ -__cold static int ipc4_module_process_d0ix(struct ipc4_message_request *ipc4) +static int ipc4_module_process_d0ix(struct ipc4_message_request *ipc4) { struct ipc4_module_set_d0ix d0ix; uint32_t module_id, instance_id; - - assert_can_be_cold(); - int ret = memcpy_s(&d0ix, sizeof(d0ix), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -1346,15 +1311,12 @@ __cold static int ipc4_module_process_d0ix(struct ipc4_message_request *ipc4) } /* enable/disable cores according to the state mask */ -__cold static int ipc4_module_process_dx(struct ipc4_message_request *ipc4) +static int ipc4_module_process_dx(struct ipc4_message_request *ipc4) { struct ipc4_module_set_dx dx; struct ipc4_dx_state_info dx_info; uint32_t module_id, instance_id; uint32_t core_id; - - assert_can_be_cold(); - int ret = memcpy_s(&dx, sizeof(dx), ipc4, sizeof(*ipc4)); if (ret < 0) @@ -1440,13 +1402,11 @@ __cold static int ipc4_module_process_dx(struct ipc4_message_request *ipc4) return IPC4_SUCCESS; } -__cold static int ipc4_process_module_message(struct ipc4_message_request *ipc4) +static int ipc4_process_module_message(struct ipc4_message_request *ipc4) { uint32_t type; int ret; - assert_can_be_cold(); - type = ipc4->primary.r.type; switch (type) { @@ -1491,12 +1451,9 @@ __cold static int ipc4_process_module_message(struct ipc4_message_request *ipc4) return ret; } -__cold struct ipc_cmd_hdr *mailbox_validate(void) +struct ipc_cmd_hdr *mailbox_validate(void) { struct ipc_cmd_hdr *hdr = ipc_get()->comp_data; - - assert_can_be_cold(); - return hdr; } @@ -1522,22 +1479,18 @@ struct ipc_cmd_hdr *ipc_prepare_to_send(const struct ipc_msg *msg) return &msg_data.msg_out; } -__cold void ipc_boot_complete_msg(struct ipc_cmd_hdr *header, uint32_t data) +void ipc_boot_complete_msg(struct ipc_cmd_hdr *header, uint32_t data) { - assert_can_be_cold(); - header->pri = SOF_IPC4_FW_READY; header->ext = 0; } #if defined(CONFIG_PM_DEVICE) && defined(CONFIG_INTEL_ADSP_IPC) -__cold void ipc_send_failed_power_transition_response(void) +void ipc_send_failed_power_transition_response(void) { struct ipc4_message_request *request = ipc_from_hdr(&msg_data.msg_in); struct ipc4_message_reply response; - assert_can_be_cold(); - response.primary.r.status = IPC4_POWER_TRANSITION_FAILED; response.primary.r.rsp = SOF_IPC4_MESSAGE_DIR_MSG_REPLY; response.primary.r.msg_tgt = request->primary.r.msg_tgt; @@ -1550,10 +1503,8 @@ __cold void ipc_send_failed_power_transition_response(void) } #endif /* defined(CONFIG_PM_DEVICE) && defined(CONFIG_INTEL_ADSP_IPC) */ -__cold void ipc_send_panic_notification(void) +void ipc_send_panic_notification(void) { - assert_can_be_cold(); - msg_notify.header = SOF_IPC4_NOTIF_HEADER(SOF_IPC4_EXCEPTION_CAUGHT); msg_notify.extension = cpu_get_id(); msg_notify.tx_size = 0; @@ -1579,7 +1530,6 @@ static bool is_notification_queued(struct ipc_msg *msg) return queued; } -/* Called from ipc_send_buffer_status_notify(), which is currently "hot" */ void ipc_send_buffer_status_notify(void) { /* a single msg_notify object is used */ diff --git a/src/ipc/ipc4/helper.c b/src/ipc/ipc4/helper.c index f727d212f179..10a871259b49 100644 --- a/src/ipc/ipc4/helper.c +++ b/src/ipc/ipc4/helper.c @@ -20,7 +20,6 @@ #include #include #include -#include #include #include #include @@ -61,9 +60,6 @@ LOG_MODULE_DECLARE(ipc, CONFIG_SOF_LOG_LEVEL); extern struct tr_ctx comp_tr; -static const struct comp_driver *ipc4_get_drv(const void *uuid); -static int ipc4_add_comp_dev(struct comp_dev *dev); - void ipc_build_stream_posn(struct sof_ipc_stream_posn *posn, uint32_t type, uint32_t id) { @@ -100,15 +96,12 @@ static const struct comp_driver *ipc4_library_get_comp_drv(char *data) return ipc4_get_drv(data); } #else -__cold static inline char *ipc4_get_comp_new_data(void) +static inline char *ipc4_get_comp_new_data(void) { - assert_can_be_cold(); - return (char *)MAILBOX_HOSTBOX_BASE; } #endif -/* Only called from ipc4_init_module_instance(), which is __cold */ __cold struct comp_dev *comp_new_ipc4(struct ipc4_module_init_instance *module_init) { struct comp_ipc_config ipc_config; @@ -199,7 +192,6 @@ __cold struct comp_dev *comp_new_ipc4(struct ipc4_module_init_instance *module_i return dev; } -/* Called from ipc4_set_pipeline_state(), so cannot be cold */ struct ipc_comp_dev *ipc_get_comp_by_ppl_id(struct ipc *ipc, uint16_t type, uint32_t ppl_id, uint32_t ignore_remote) @@ -228,14 +220,12 @@ struct ipc_comp_dev *ipc_get_comp_by_ppl_id(struct ipc *ipc, uint16_t type, return NULL; } -__cold static int ipc4_create_pipeline(struct ipc4_pipeline_create *pipe_desc) +static int ipc4_create_pipeline(struct ipc4_pipeline_create *pipe_desc) { struct ipc_comp_dev *ipc_pipe; struct pipeline *pipe; struct ipc *ipc = ipc_get(); - assert_can_be_cold(); - /* check whether pipeline id is already taken or in use */ ipc_pipe = ipc_get_pipeline_by_id(ipc, pipe_desc->primary.r.instance_id); if (ipc_pipe) { @@ -279,13 +269,10 @@ __cold static int ipc4_create_pipeline(struct ipc4_pipeline_create *pipe_desc) return IPC4_SUCCESS; } -/* Only called from ipc4_new_pipeline(), which is __cold */ -__cold int ipc_pipeline_new(struct ipc *ipc, ipc_pipe_new *_pipe_desc) +int ipc_pipeline_new(struct ipc *ipc, ipc_pipe_new *_pipe_desc) { struct ipc4_pipeline_create *pipe_desc = ipc_from_pipe_new(_pipe_desc); - assert_can_be_cold(); - tr_dbg(&ipc_tr, "ipc: pipeline id = %u", (uint32_t)pipe_desc->primary.r.instance_id); /* pass IPC to target core */ @@ -295,24 +282,20 @@ __cold int ipc_pipeline_new(struct ipc *ipc, ipc_pipe_new *_pipe_desc) return ipc4_create_pipeline(pipe_desc); } -__cold static inline int ipc_comp_free_remote(struct comp_dev *dev) +static inline int ipc_comp_free_remote(struct comp_dev *dev) { struct idc_msg msg = { IDC_MSG_FREE, IDC_MSG_FREE_EXT(dev->ipc_config.id), dev->ipc_config.core,}; - assert_can_be_cold(); - return idc_send_msg(&msg, IDC_BLOCKING); } -__cold static int ipc_pipeline_module_free(uint32_t pipeline_id) +static int ipc_pipeline_module_free(uint32_t pipeline_id) { struct ipc *ipc = ipc_get(); struct ipc_comp_dev *icd; int ret; - assert_can_be_cold(); - icd = ipc_get_comp_by_ppl_id(ipc, COMP_TYPE_COMPONENT, pipeline_id, IPC_COMP_ALL); while (icd) { struct comp_buffer *buffer; @@ -351,14 +334,11 @@ __cold static int ipc_pipeline_module_free(uint32_t pipeline_id) return IPC4_SUCCESS; } -/* Only called from ipc4_delete_pipeline(), which is __cold */ -__cold int ipc_pipeline_free(struct ipc *ipc, uint32_t comp_id) +int ipc_pipeline_free(struct ipc *ipc, uint32_t comp_id) { struct ipc_comp_dev *ipc_pipe; int ret; - assert_can_be_cold(); - /* check whether pipeline exists */ ipc_pipe = ipc_get_pipeline_by_id(ipc, comp_id); if (!ipc_pipe) @@ -388,14 +368,12 @@ __cold int ipc_pipeline_free(struct ipc *ipc, uint32_t comp_id) return IPC4_SUCCESS; } -__cold static struct comp_buffer *ipc4_create_buffer(struct comp_dev *src, bool is_shared, - uint32_t buf_size, uint32_t src_queue, - uint32_t dst_queue) +static struct comp_buffer *ipc4_create_buffer(struct comp_dev *src, bool is_shared, + uint32_t buf_size, uint32_t src_queue, + uint32_t dst_queue) { struct sof_ipc_buffer ipc_buf; - assert_can_be_cold(); - memset(&ipc_buf, 0, sizeof(ipc_buf)); ipc_buf.size = buf_size; ipc_buf.comp.id = IPC4_COMP_ID(src_queue, dst_queue); @@ -472,8 +450,7 @@ static int ll_wait_finished_on_core(struct comp_dev *dev) #endif -/* Only called from ipc4_bind_module_instance(), which is __cold */ -__cold int ipc_comp_connect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) +int ipc_comp_connect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) { struct ipc4_module_bind_unbind *bu; struct comp_buffer *buffer; @@ -488,8 +465,6 @@ __cold int ipc_comp_connect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) int src_id, sink_id; int ret; - assert_can_be_cold(); - bu = (struct ipc4_module_bind_unbind *)_connect; src_id = IPC4_COMP_ID(bu->primary.r.module_id, bu->primary.r.instance_id); sink_id = IPC4_COMP_ID(bu->extension.r.dst_module_id, bu->extension.r.dst_instance_id); @@ -693,8 +668,7 @@ __cold int ipc_comp_connect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) * during run-time. The only way to change pipeline topology is to delete the whole * pipeline and create it in modified form. */ -/* Only called from ipc4_unbind_module_instance(), which is __cold */ -__cold int ipc_comp_disconnect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) +int ipc_comp_disconnect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) { struct ipc4_module_bind_unbind *bu; struct comp_buffer *buffer = NULL; @@ -705,8 +679,6 @@ __cold int ipc_comp_disconnect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) int ret, ret1; bool cross_core_unbind; - assert_can_be_cold(); - bu = (struct ipc4_module_bind_unbind *)_connect; src_id = IPC4_COMP_ID(bu->primary.r.module_id, bu->primary.r.instance_id); sink_id = IPC4_COMP_ID(bu->extension.r.dst_module_id, bu->extension.r.dst_instance_id); @@ -787,15 +759,12 @@ __cold int ipc_comp_disconnect(struct ipc *ipc, ipc_pipe_comp_connect *_connect) } #if CONFIG_COMP_CHAIN_DMA -/* Only called from ipc4_process_chain_dma(), which is __cold */ -__cold int ipc4_chain_manager_create(struct ipc4_chain_dma *cdma) +int ipc4_chain_manager_create(struct ipc4_chain_dma *cdma) { const struct sof_uuid uuid = SOF_REG_UUID(chain_dma); const struct comp_driver *drv; struct comp_dev *dev; - assert_can_be_cold(); - drv = ipc4_get_drv(&uuid); if (!drv) return -EINVAL; @@ -814,8 +783,7 @@ __cold int ipc4_chain_manager_create(struct ipc4_chain_dma *cdma) return ipc4_add_comp_dev(dev); } -/* Only called from ipc4_process_chain_dma(), which is __cold */ -__cold int ipc4_chain_dma_state(struct comp_dev *dev, struct ipc4_chain_dma *cdma) +int ipc4_chain_dma_state(struct comp_dev *dev, struct ipc4_chain_dma *cdma) { const bool allocate = cdma->primary.r.allocate; const bool enable = cdma->primary.r.enable; @@ -824,8 +792,6 @@ __cold int ipc4_chain_dma_state(struct comp_dev *dev, struct ipc4_chain_dma *cdm struct list_item *clist, *_tmp; int ret; - assert_can_be_cold(); - if (!dev) return -EINVAL; @@ -857,14 +823,12 @@ __cold int ipc4_chain_dma_state(struct comp_dev *dev, struct ipc4_chain_dma *cdm } #endif -__cold static int ipc4_update_comps_direction(struct ipc *ipc, uint32_t ppl_id) +static int ipc4_update_comps_direction(struct ipc *ipc, uint32_t ppl_id) { struct ipc_comp_dev *icd; struct list_item *clist; struct comp_buffer *src_buf; - assert_can_be_cold(); - list_for_item(clist, &ipc->comp_list) { icd = container_of(clist, struct ipc_comp_dev, list); if (icd->type != COMP_TYPE_COMPONENT) @@ -940,7 +904,7 @@ int ipc4_process_on_core(uint32_t core, bool blocking) return IPC4_SUCCESS; } -__cold static const struct comp_driver *ipc4_get_drv(const void *uuid) +const struct comp_driver *ipc4_get_drv(const void *uuid) { const struct sof_uuid *const sof_uuid = (const struct sof_uuid *)uuid; struct comp_driver_list *drivers = comp_drivers_get(); @@ -949,8 +913,6 @@ __cold static const struct comp_driver *ipc4_get_drv(const void *uuid) struct comp_driver_info *info; uint32_t flags; - assert_can_be_cold(); - irq_local_disable(flags); /* search driver list with UUID */ @@ -978,22 +940,13 @@ __cold static const struct comp_driver *ipc4_get_drv(const void *uuid) return drv; } -/* - * Called from - * - ipc4_get_large_config_module_instance() - * - ipc4_set_large_config_module_instance() - * - comp_new_ipc4() - * all of which are __cold - */ -__cold const struct comp_driver *ipc4_get_comp_drv(uint32_t module_id) +const struct comp_driver *ipc4_get_comp_drv(uint32_t module_id) { const struct sof_man_fw_desc *desc = NULL; const struct comp_driver *drv; const struct sof_man_module *mod; uint32_t entry_index; - assert_can_be_cold(); - #ifdef RIMAGE_MANIFEST desc = (const struct sof_man_fw_desc *)IMR_BOOT_LDR_MANIFEST_BASE; #else @@ -1059,13 +1012,11 @@ struct comp_dev *ipc4_get_comp_dev(uint32_t comp_id) } EXPORT_SYMBOL(ipc4_get_comp_dev); -__cold static int ipc4_add_comp_dev(struct comp_dev *dev) +int ipc4_add_comp_dev(struct comp_dev *dev) { struct ipc *ipc = ipc_get(); struct ipc_comp_dev *icd; - assert_can_be_cold(); - /* check id for duplicates */ icd = ipc_get_comp_by_id(ipc, dev->ipc_config.id); if (icd) { diff --git a/src/library_manager/llext_manager.c b/src/library_manager/llext_manager.c index e7f6487740af..dd8866ea784a 100644 --- a/src/library_manager/llext_manager.c +++ b/src/library_manager/llext_manager.c @@ -30,6 +30,7 @@ #include #include #include +#include #include #include @@ -71,6 +72,20 @@ static int llext_manager_align_unmap(void __sparse_cache *vma, size_t size) return sys_mm_drv_unmap_region(aligned_vma, ALIGN_UP(pre_pad_size + size, PAGE_SZ)); } +static void llext_manager_detached_update_flags(void __sparse_cache *vma, + size_t size, uint32_t flags) +{ +#ifdef CONFIG_MMU + size_t pre_pad_size = (uintptr_t)vma & (PAGE_SZ - 1); + void *aligned_vma = (__sparse_force uint8_t *)vma - pre_pad_size; + + /* Use cached virtual address */ + uintptr_t va = POINTER_TO_UINT(sys_cache_cached_ptr_get(aligned_vma)); + + arch_mem_map(aligned_vma, va, ALIGN_UP(pre_pad_size + size, PAGE_SZ), flags); +#endif +} + /* * Map the memory range covered by 'vma' and 'size' as writable, copy all * sections that belong to the specified 'region' and are contained in the @@ -107,8 +122,16 @@ static int llext_manager_load_data_from_storage(const struct llext_loader *ldr, /* skip detached sections (will be outside requested VMA area) */ if ((uintptr_t)shdr->sh_addr < (uintptr_t)vma || - (uintptr_t)shdr->sh_addr >= (uintptr_t)vma + size) + (uintptr_t)shdr->sh_addr >= (uintptr_t)vma + size) { + llext_manager_detached_update_flags((__sparse_cache void *) + ((uint8_t *)region_addr + s_offset), + shdr->sh_size, flags); + if (flags & SYS_MM_MEM_PERM_EXEC) + icache_invalidate_region((__sparse_cache void *) + ((uint8_t *)region_addr + s_offset), + shdr->sh_size); continue; + } ret = memcpy_s((__sparse_force void *)shdr->sh_addr, size - s_offset, (const uint8_t *)region_addr + s_offset, shdr->sh_size); @@ -129,6 +152,39 @@ static int llext_manager_load_data_from_storage(const struct llext_loader *ldr, return ret; } +static void llext_manager_unmap_detached_sections(const struct llext_loader *ldr, + const struct llext *ext, + enum llext_mem region, + void __sparse_cache *vma, + size_t size) +{ +#ifdef CONFIG_MMU + unsigned int i; + const void *region_addr; + + llext_get_region_info(ldr, ext, region, NULL, ®ion_addr, NULL); + + for (i = 0; i < llext_section_count(ext); i++) { + const elf_shdr_t *shdr; + enum llext_mem s_region = LLEXT_MEM_COUNT; + size_t s_offset = 0; + + llext_get_section_info(ldr, ext, i, &shdr, &s_region, &s_offset); + + /* skip sections not in the requested region */ + if (s_region != region) + continue; + + /* unmap detached sections (will be outside requested VMA area) */ + if ((uintptr_t)shdr->sh_addr < (uintptr_t)vma || + (uintptr_t)shdr->sh_addr >= (uintptr_t)vma + size) + llext_manager_detached_update_flags((__sparse_force void *) + ((uint8_t *)region_addr + s_offset), + shdr->sh_size, 0); + } +#endif +} + static int llext_manager_load_module(struct lib_manager_module *mctx) { /* Executable code (.text) */ @@ -216,6 +272,9 @@ static int llext_manager_load_module(struct lib_manager_module *mctx) static int llext_manager_unload_module(struct lib_manager_module *mctx) { + const struct llext_loader *ldr = &mctx->ebl->loader; + const struct llext *ext = mctx->llext; + /* Executable code (.text) */ void __sparse_cache *va_base_text = (void __sparse_cache *) mctx->segment[LIB_MANAGER_TEXT].addr; @@ -232,14 +291,20 @@ static int llext_manager_unload_module(struct lib_manager_module *mctx) size_t data_size = mctx->segment[LIB_MANAGER_DATA].size; int err = 0, ret; + llext_manager_unmap_detached_sections(ldr, ext, LLEXT_MEM_TEXT, + va_base_text, text_size); ret = llext_manager_align_unmap(va_base_text, text_size); if (ret < 0) err = ret; + llext_manager_unmap_detached_sections(ldr, ext, LLEXT_MEM_DATA, + va_base_data, data_size); ret = llext_manager_align_unmap(va_base_data, data_size); if (ret < 0 && !err) err = ret; + llext_manager_unmap_detached_sections(ldr, ext, LLEXT_MEM_RODATA, + va_base_rodata, rodata_size); ret = llext_manager_align_unmap(va_base_rodata, rodata_size); if (ret < 0 && !err) err = ret; diff --git a/zephyr/CMakeLists.txt b/zephyr/CMakeLists.txt index 7a3c92f9ce64..9848e492fcd0 100644 --- a/zephyr/CMakeLists.txt +++ b/zephyr/CMakeLists.txt @@ -162,9 +162,9 @@ zephyr_library_named(modules_sof) # Zephyr C++ code requires 14 or newer standard set_property(TARGET modules_sof PROPERTY CXX_STANDARD 17) -zephyr_include_directories( - include -) +zephyr_include_directories(include) +zephyr_include_directories(${ZEPHYR_BASE}/kernel/include) +zephyr_include_directories(${ZEPHYR_BASE}/arch/${ARCH}/include) # SOC level sources # Files that are commented may not be needed.