Skip to content

Commit e8353e2

Browse files
softwareckiabonislawski
authored andcommitted
ptl: mmu: Enable module data processing in userspace
Introduce support for loading userspace modules. Allow the DP thread to process audio data in userspace. Signed-off-by: Jaroslaw Stelter <Jaroslaw.Stelter@intel.com> Signed-off-by: Adrian Warecki <adrian.warecki@intel.com>
1 parent 9494177 commit e8353e2

File tree

2 files changed

+62
-21
lines changed

2 files changed

+62
-21
lines changed

src/audio/module_adapter/module/modules.c

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77

88
#include <sof/audio/module_adapter/module/generic.h>
99
#include <sof/audio/module_adapter/module/modules.h>
10+
#include <rtos/userspace_helper.h>
1011
#include <utilities/array.h>
1112
#include <iadk_module_adapter.h>
1213
#include <sof/lib_manager.h>
@@ -201,7 +202,7 @@ static int modules_reset(struct processing_module *mod)
201202
}
202203

203204
/* Processing Module Adapter API*/
204-
const struct module_interface processing_module_adapter_interface = {
205+
APP_TASK_DATA const struct module_interface processing_module_adapter_interface = {
205206
.init = modules_init,
206207
.prepare = modules_prepare,
207208
.process = modules_process,

src/library_manager/lib_manager.c

Lines changed: 60 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,8 @@
33
// Copyright(c) 2022 Intel Corporation. All rights reserved.
44
//
55
// Author: Jaroslaw Stelter <jaroslaw.stelter@intel.com>
6-
// Pawel Dobrowolski<pawelx.dobrowolski@intel.com>
6+
// Pawel Dobrowolski <pawelx.dobrowolski@intel.com>
7+
// Adrian Warecki <adrian.warecki@intel.com>
78

89
/*
910
* Dynamic module loading functions.
@@ -18,11 +19,13 @@
1819
#include <rtos/clk.h>
1920
#include <rtos/sof.h>
2021
#include <rtos/spinlock.h>
22+
#include <rtos/userspace_helper.h>
2123
#include <sof/lib/cpu-clk-manager.h>
2224
#include <sof/lib_manager.h>
2325
#include <sof/llext_manager.h>
2426
#include <sof/audio/module_adapter/module/generic.h>
2527
#include <sof/audio/module_adapter/module/modules.h>
28+
#include <sof/audio/module_adapter/library/userspace_proxy.h>
2629
#include <utilities/array.h>
2730
#include <system_agent.h>
2831
#include <native_system_agent.h>
@@ -492,14 +495,19 @@ const struct sof_man_module *lib_manager_get_module_manifest(const uint32_t modu
492495
* \param[in] module_entry_point - Entry point address of the module.
493496
* \param[in] agent - Function pointer to the system agent start function.
494497
* \param[out] agent_interface - Pointer to store the module interface returned by the system agent.
498+
* \param[out] userspace - Pointer to store the userspace module proxy context.
499+
* \param[out] ops - Pointer to store pointer to the module interface structure.
495500
*
496501
* \return Error code returned by the system agent, 0 on success.
497502
*/
498503
static int lib_manager_start_agent(const struct comp_driver *drv, const uint32_t component_id,
504+
const struct sof_man_module *mod_manifest,
499505
const struct ipc_config_process *args,
500506
const uintptr_t module_entry_point,
501507
const system_agent_start_fn agent,
502-
const void **agent_interface)
508+
const void **agent_interface,
509+
struct userspace_context **userspace,
510+
const struct module_interface **ops)
503511
{
504512
struct system_agent_params agent_params;
505513
byte_array_t mod_cfg;
@@ -516,6 +524,17 @@ static int lib_manager_start_agent(const struct comp_driver *drv, const uint32_t
516524
agent_params.log_handle = (uint32_t)drv->tctx;
517525
agent_params.mod_cfg = &mod_cfg;
518526

527+
#if CONFIG_SOF_USERSPACE_PROXY
528+
/* If drv->user_heap is allocated, it means the module is userspace. */
529+
if (drv->user_heap) {
530+
ret = userspace_proxy_create(userspace, drv, mod_manifest, agent, &agent_params,
531+
agent_interface, ops);
532+
if (ret)
533+
tr_err(&lib_manager_tr, "userspace_proxy_create failed! %d", ret);
534+
return ret;
535+
}
536+
#endif /* CONFIG_SOF_USERSPACE_PROXY */
537+
519538
ret = agent(&agent_params, agent_interface);
520539
if (ret)
521540
tr_err(&lib_manager_tr, "System agent start failed %d!", ret);
@@ -584,14 +603,22 @@ static struct comp_dev *lib_manager_module_create(const struct comp_driver *drv,
584603
const struct sof_man_fw_desc *const desc = lib_manager_get_library_manifest(config->id);
585604
const struct ipc_config_process *args = (const struct ipc_config_process *)spec;
586605
const uint32_t entry_index = LIB_MANAGER_GET_MODULE_INDEX(config->id);
587-
const struct module_interface *ops = NULL;
606+
struct userspace_context *userspace = NULL;
607+
const struct module_interface *ops;
588608
const struct sof_man_module *mod;
589609
system_agent_start_fn agent;
590610
void *adapter_priv = NULL;
591611
const void **agent_iface;
592612
struct comp_dev *dev;
593613
int ret;
594614

615+
#ifdef CONFIG_SOF_USERSPACE_PROXY
616+
if (drv->user_heap && config->proc_domain != COMP_PROCESSING_DOMAIN_DP) {
617+
tr_err(&lib_manager_tr, "Userspace supports only DP modules.");
618+
return NULL;
619+
}
620+
#endif
621+
595622
tr_dbg(&lib_manager_tr, "start");
596623
if (!desc) {
597624
tr_err(&lib_manager_tr, "Error: Couldn't find loadable module with id %u.",
@@ -623,35 +650,39 @@ static struct comp_dev *lib_manager_module_create(const struct comp_driver *drv,
623650
agent = &native_system_agent_start;
624651
agent_iface = (const void **)&ops;
625652
break;
653+
#if CONFIG_INTEL_MODULES
626654
case MOD_TYPE_IADK:
627655
agent = &system_agent_start;
628-
/* processing_module_adapter_interface is already assigned to drv->adapter_ops by
629-
* the lib_manager_prepare_module_adapter function.
630-
*/
656+
ops = &processing_module_adapter_interface;
631657
agent_iface = (const void **)&adapter_priv;
632658
break;
659+
#endif
633660
case MOD_TYPE_INVALID:
634661
goto err;
635662
}
636663

637664
/* At this point module resources are allocated and it is moved to L2 memory. */
638665
if (agent) {
639-
ret = lib_manager_start_agent(drv, config->id, args, module_entry_point, agent,
640-
agent_iface);
666+
ret = lib_manager_start_agent(drv, config->id, mod, args, module_entry_point, agent,
667+
agent_iface, &userspace, &ops);
641668
if (ret)
642669
goto err;
643670
}
644671

645-
if (ops && comp_set_adapter_ops(drv, ops) < 0)
672+
if (comp_set_adapter_ops(drv, ops) < 0)
646673
goto err;
647674

648-
dev = module_adapter_new_ext(drv, config, spec, adapter_priv, NULL);
675+
dev = module_adapter_new_ext(drv, config, spec, adapter_priv, userspace);
649676
if (!dev)
650677
goto err;
651678

652679
return dev;
653680

654681
err:
682+
#if CONFIG_SOF_USERSPACE_PROXY
683+
if (userspace)
684+
userspace_proxy_destroy(drv, userspace);
685+
#endif /* CONFIG_SOF_USERSPACE_PROXY */
655686
lib_manager_free_module(config->id);
656687
return NULL;
657688
}
@@ -698,18 +729,16 @@ static void lib_manager_prepare_module_adapter(struct comp_driver *drv, const st
698729
drv->ops.dai_ts_start = module_adapter_ts_start_op;
699730
drv->ops.dai_ts_stop = module_adapter_ts_stop_op;
700731
drv->ops.dai_ts_get = module_adapter_ts_get_op;
701-
#if CONFIG_INTEL_MODULES
702-
drv->adapter_ops = &processing_module_adapter_interface;
703-
#endif
704732
}
705733

706734
int lib_manager_register_module(const uint32_t component_id)
707735
{
708-
struct comp_driver_info *new_drv_info;
709-
struct comp_driver *drv = NULL;
710736
const struct sof_man_module *mod = lib_manager_get_module_manifest(component_id);
711737
const struct sof_uuid *uid = (struct sof_uuid *)&mod->uuid;
712-
int ret;
738+
struct comp_driver_info *new_drv_info;
739+
struct sys_heap *drv_heap = NULL;
740+
struct comp_driver *drv = NULL;
741+
int ret = -ENOMEM;
713742

714743
if (!mod) {
715744
tr_err(&lib_manager_tr, "Error: Couldn't find loadable module with id %u.",
@@ -726,13 +755,23 @@ int lib_manager_register_module(const uint32_t component_id)
726755
return -ENOMEM;
727756
}
728757

729-
drv = rzalloc(SOF_MEM_FLAG_KERNEL | SOF_MEM_FLAG_COHERENT,
730-
sizeof(struct comp_driver));
758+
#if CONFIG_SOF_USERSPACE_USE_DRIVER_HEAP
759+
if (mod->type.user_mode) {
760+
drv_heap = module_driver_heap_init();
761+
if (!drv_heap) {
762+
tr_err(&lib_manager_tr, "failed to allocate driver heap!");
763+
goto cleanup;
764+
}
765+
}
766+
#endif /* CONFIG_SOF_USERSPACE_USE_DRIVER_HEAP */
767+
768+
drv = module_driver_heap_rmalloc(drv_heap, SOF_MEM_FLAG_KERNEL | SOF_MEM_FLAG_COHERENT,
769+
sizeof(struct comp_driver));
731770
if (!drv) {
732771
tr_err(&lib_manager_tr, "failed to allocate comp_driver");
733-
ret = -ENOMEM;
734772
goto cleanup;
735773
}
774+
drv->user_heap = drv_heap;
736775

737776
lib_manager_prepare_module_adapter(drv, uid);
738777

@@ -745,8 +784,9 @@ int lib_manager_register_module(const uint32_t component_id)
745784

746785
cleanup:
747786
if (ret < 0) {
748-
rfree(drv);
749787
rfree(new_drv_info);
788+
module_driver_heap_free(drv_heap, drv);
789+
module_driver_heap_remove(drv_heap);
750790
}
751791

752792
return ret;

0 commit comments

Comments
 (0)