blob: 65f8f9cfaf1b19b5165f54548ba5ebc1d2ca3ba2 [file]
/*
* Copyright 2019, Data61, CSIRO (ABN 41 687 119 230)
*
* SPDX-License-Identifier: BSD-2-Clause
*/
#include <stddef.h>
#include <sel4runtime/start.h>
#include <stdint.h>
#include <camkes/init.h>
extern unsigned int _tdata_start[];
extern unsigned int _tdata_end[];
extern unsigned int _tbss_end[];
extern unsigned char bootinfo_frame[] __attribute__((weak));
long sel4_vsyscall(long sysnum, ...);
void camkes_start_control(int thread_id, void *ipc_buffer_ptr)
{
uintptr_t tdata_start = (uintptr_t) &_tdata_start[0];
uintptr_t tdata_end = (uintptr_t) &_tdata_end[0];
uintptr_t tbss_end = (uintptr_t) &_tbss_end[0];
Elf_Phdr tls_header = {
.p_type = PT_TLS,
.p_offset = 0,
.p_vaddr = (Elf_Addr) tdata_start,
.p_paddr = 0,
.p_filesz = tdata_end - tdata_start,
.p_memsz = tbss_end - tdata_start,
.p_align = sizeof(long),
};
struct {
char const *const argv[3];
char const *const envp[2];
auxv_t auxv[7];
} info = {
.argv = {
"camkes",
(char *)(uintptr_t) thread_id,
NULL,
},
.envp = {
"seL4=1",
NULL,
},
.auxv = {
{
.a_type = AT_PHENT,
.a_un.a_val = sizeof(Elf32_Phdr),
}, {
.a_type = AT_PHNUM,
.a_un.a_val = 1,
}, {
.a_type = AT_PHDR,
.a_un.a_ptr = &tls_header,
}, {
.a_type = AT_SYSINFO,
.a_un.a_ptr = &sel4_vsyscall,
}, {
// NB: optionally filled in by rootserver, if not defined
// a_ptr will be null and dropped by parse_auxv
.a_type = AT_SEL4_BOOT_INFO,
.a_un.a_ptr = bootinfo_frame,
}, {
.a_type = AT_SEL4_IPC_BUFFER_PTR,
.a_un.a_ptr = ipc_buffer_ptr,
}, {
// Null terminating entry
.a_type = AT_NULL,
.a_un.a_val = 0
},
},
};
__sel4runtime_start_main(main, ARRAY_LENGTH(info.argv) - 1, info.argv, info.envp, info.auxv);
}