Skip to content

Commit 53f5236

Browse files
lyakhlgirdwood
authored andcommitted
llext: add support for adding LLEXT memory to a memory domain
Add functions for adding LLEXT partitions to a memory domain for user-space modules. Signed-off-by: Guennadi Liakhovetski <guennadi.liakhovetski@linux.intel.com>
1 parent dbf8a4d commit 53f5236

2 files changed

Lines changed: 65 additions & 0 deletions

File tree

src/include/sof/llext_manager.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
struct comp_dev;
1616
struct comp_driver;
1717
struct comp_ipc_config;
18+
struct k_mem_domain;
1819

1920
static inline bool module_is_llext(const struct sof_man_module *mod)
2021
{
@@ -29,12 +30,15 @@ int llext_manager_free_module(const uint32_t component_id);
2930

3031
int llext_manager_add_library(uint32_t module_id);
3132

33+
int llext_manager_add_domain(const uint32_t component_id, struct k_mem_domain *domain);
34+
3235
bool comp_is_llext(struct comp_dev *comp);
3336
#else
3437
#define module_is_llext(mod) false
3538
#define llext_manager_allocate_module(ipc_config, ipc_specific_config) 0
3639
#define llext_manager_free_module(component_id) 0
3740
#define llext_manager_add_library(module_id) 0
41+
#define llext_manager_add_domain(component_id, domain) 0
3842
#define comp_is_llext(comp) false
3943
#endif
4044

src/library_manager/llext_manager.c

Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@
2525
#include <sof/audio/module_adapter/module/modules.h>
2626

2727
#include <zephyr/cache.h>
28+
#include <zephyr/app_memory/mem_domain.h>
2829
#include <zephyr/drivers/mm/system_mm.h>
2930
#include <zephyr/llext/buf_loader.h>
3031
#include <zephyr/llext/loader.h>
@@ -716,6 +717,66 @@ uintptr_t llext_manager_allocate_module(const struct comp_ipc_config *ipc_config
716717
return mod_manifest->module.entry_point;
717718
}
718719

720+
#ifdef CONFIG_USERSPACE
721+
static int llext_manager_add_partition(struct k_mem_domain *domain,
722+
uintptr_t addr, size_t size,
723+
k_mem_partition_attr_t attr)
724+
{
725+
size_t pre_pad_size = addr & (PAGE_SZ - 1);
726+
struct k_mem_partition part = {
727+
.start = addr - pre_pad_size,
728+
.size = ALIGN_UP(pre_pad_size + size, PAGE_SZ),
729+
.attr = attr,
730+
};
731+
732+
tr_dbg(&lib_manager_tr, "add %#zx @ %lx partition", part.size, part.start);
733+
return k_mem_domain_add_partition(domain, &part);
734+
}
735+
736+
int llext_manager_add_domain(const uint32_t component_id, struct k_mem_domain *domain)
737+
{
738+
const uint32_t module_id = IPC4_MOD_ID(component_id);
739+
struct lib_manager_mod_ctx *ctx = lib_manager_get_mod_ctx(module_id);
740+
const uint32_t entry_index = LIB_MANAGER_GET_MODULE_INDEX(module_id);
741+
const unsigned int mod_idx = llext_manager_mod_find(ctx, entry_index);
742+
struct lib_manager_module *mctx = ctx->mod + mod_idx;
743+
int ret;
744+
745+
/* Executable code (.text) */
746+
uintptr_t va_base_text = mctx->segment[LIB_MANAGER_TEXT].addr;
747+
size_t text_size = mctx->segment[LIB_MANAGER_TEXT].size;
748+
749+
/* Read-only data (.rodata and others) */
750+
uintptr_t va_base_rodata = mctx->segment[LIB_MANAGER_RODATA].addr;
751+
size_t rodata_size = mctx->segment[LIB_MANAGER_RODATA].size;
752+
753+
/* Writable data (.data, .bss and others) */
754+
uintptr_t va_base_data = mctx->segment[LIB_MANAGER_DATA].addr;
755+
size_t data_size = mctx->segment[LIB_MANAGER_DATA].size;
756+
757+
ret = llext_manager_add_partition(domain, va_base_text, text_size,
758+
K_MEM_PARTITION_P_RX_U_RX);
759+
if (ret < 0)
760+
return ret;
761+
762+
if (rodata_size) {
763+
ret = llext_manager_add_partition(domain, va_base_rodata, rodata_size,
764+
K_MEM_PARTITION_P_RO_U_RO);
765+
if (ret < 0)
766+
return ret;
767+
}
768+
769+
if (data_size) {
770+
ret = llext_manager_add_partition(domain, va_base_data, data_size,
771+
K_MEM_PARTITION_P_RW_U_RW);
772+
if (ret < 0)
773+
return ret;
774+
}
775+
776+
return 0;
777+
}
778+
#endif
779+
719780
int llext_manager_free_module(const uint32_t component_id)
720781
{
721782
const uint32_t module_id = IPC4_MOD_ID(component_id);

0 commit comments

Comments
 (0)