// SPDX-License-Identifier: BSD-2-Clause /* * Copyright (c) 2026, Linutronix GmbH */ #include #include #include "asan.h" #include "sys.h" static void init_run_constructors(void) { const vaddr_t *ctor = NULL; for (ctor = &__init_array_start; ctor < &__init_array_end; ctor++) ((void (*)(void))(*ctor))(); } static int asan_ldelf_map_stack(size_t size) { vaddr_t stack_top = (vaddr_t)&stack_top; vaddr_t stack_base = 0; size = ROUNDUP(size, SMALL_PAGE_SIZE); stack_top = ROUNDUP(stack_top, SMALL_PAGE_SIZE); stack_base = stack_top - size; return asan_user_map_shadow((void *)stack_base, (void *)stack_top, ASAN_REG_STACK); } TEE_Result asan_init_ldelf(void) { vaddr_t req = (vaddr_t)GET_ASAN_INFO(); TEE_Result rc = TEE_SUCCESS; vaddr_t tmp = req; /* Map global ASan info */ rc = sys_map_zi(sizeof(struct asan_global_info), 0, &tmp, 0, 0); if (rc == TEE_SUCCESS && req == tmp) { /* Map shadow stack for ldelf */ rc = asan_ldelf_map_stack(LDELF_STACK_SIZE); if (rc) { EMSG("failed to map ldelf shadow stack"); panic(); } /* Map shadow memory for ldelf binary sections */ rc = asan_user_map_shadow((void *)__text_start, (void *)ROUNDUP((vaddr_t)__end, SMALL_PAGE_SIZE), ASAN_REG_ELF); if (rc) { EMSG("failed to map ldelf shadow elf sections"); panic(); } /* Register global ASan constructors */ init_run_constructors(); } else { rc = TEE_ERROR_GENERIC; } return rc; }