Changeset View
Changeset View
Standalone View
Standalone View
lib/csu/arm/crt1_c.c
- This file was moved from lib/csu/arm/crt1.c.
Show First 20 Lines • Show All 43 Lines • ▼ Show 20 Lines | |||||
#include <sys/cdefs.h> | #include <sys/cdefs.h> | ||||
__FBSDID("$FreeBSD$"); | __FBSDID("$FreeBSD$"); | ||||
#include <sys/param.h> | #include <sys/param.h> | ||||
#include <sys/elf_common.h> | #include <sys/elf_common.h> | ||||
#include <stdlib.h> | #include <stdlib.h> | ||||
#include "libc_private.h" | #include "libc_private.h" | ||||
#include "crtbrand.c" | |||||
#include "ignore_init.c" | #include "ignore_init.c" | ||||
struct Struct_Obj_Entry; | struct Struct_Obj_Entry; | ||||
struct ps_strings; | struct ps_strings; | ||||
extern void _start(int, char **, char **, const struct Struct_Obj_Entry *, | extern void _start(int, char **, char **, const struct Struct_Obj_Entry *, | ||||
void (*)(void), struct ps_strings *); | void (*)(void), struct ps_strings *); | ||||
#ifdef GCRT | #ifdef GCRT | ||||
extern void _mcleanup(void); | extern void _mcleanup(void); | ||||
extern void monstartup(void *, void *); | extern void monstartup(void *, void *); | ||||
extern int eprol; | extern int eprol; | ||||
extern int etext; | extern int etext; | ||||
#endif | #endif | ||||
struct ps_strings *__ps_strings; | struct ps_strings *__ps_strings; | ||||
void __start(int, char **, char **, struct ps_strings *, | void __start(int, char **, char **, struct ps_strings *, | ||||
const struct Struct_Obj_Entry *, void (*)(void)); | const struct Struct_Obj_Entry *, void (*)(void)); | ||||
/* The entry function. */ | |||||
__asm(" .text \n" | |||||
" .align 0 \n" | |||||
" .globl _start \n" | |||||
" _start: \n" | |||||
" mov r5, r2 /* cleanup */ \n" | |||||
" mov r4, r1 /* obj_main */ \n" | |||||
" mov r3, r0 /* ps_strings */ \n" | |||||
" /* Get argc, argv, and envp from stack */ \n" | |||||
" ldr r0, [sp, #0x0000] \n" | |||||
" add r1, sp, #0x0004 \n" | |||||
" add r2, r1, r0, lsl #2 \n" | |||||
" add r2, r2, #0x0004 \n" | |||||
" /* Ensure the stack is properly aligned before calling C code. */\n" | |||||
" bic sp, sp, #7 \n" | |||||
" sub sp, sp, #8 \n" | |||||
" str r5, [sp, #4] \n" | |||||
" str r4, [sp, #0] \n" | |||||
"\n" | |||||
" b __start "); | |||||
/* ARGSUSED */ | /* ARGSUSED */ | ||||
void | void | ||||
__start(int argc, char **argv, char **env, struct ps_strings *ps_strings, | __start(int argc, char **argv, char **env, struct ps_strings *ps_strings, | ||||
const struct Struct_Obj_Entry *obj __unused, void (*cleanup)(void)) | const struct Struct_Obj_Entry *obj __unused, void (*cleanup)(void)) | ||||
{ | { | ||||
handle_argv(argc, argv, env); | handle_argv(argc, argv, env); | ||||
if (ps_strings != (struct ps_strings *)0) | if (ps_strings != (struct ps_strings *)0) | ||||
__ps_strings = ps_strings; | __ps_strings = ps_strings; | ||||
if (&_DYNAMIC != NULL) | if (&_DYNAMIC != NULL) | ||||
atexit(cleanup); | atexit(cleanup); | ||||
else | else | ||||
_init_tls(); | _init_tls(); | ||||
#ifdef GCRT | #ifdef GCRT | ||||
atexit(_mcleanup); | atexit(_mcleanup); | ||||
monstartup(&eprol, &etext); | monstartup(&eprol, &etext); | ||||
#endif | #endif | ||||
handle_static_init(argc, argv, env); | handle_static_init(argc, argv, env); | ||||
exit(main(argc, argv, env)); | exit(main(argc, argv, env)); | ||||
} | } | ||||
static const struct { | |||||
int32_t namesz; | |||||
int32_t descsz; | |||||
int32_t type; | |||||
char name[sizeof(NOTE_FREEBSD_VENDOR)]; | |||||
char desc[sizeof(MACHINE_ARCH)]; | |||||
} archtag __attribute__ ((section (NOTE_SECTION), aligned(4))) __used = { | |||||
.namesz = sizeof(NOTE_FREEBSD_VENDOR), | |||||
.descsz = sizeof(MACHINE_ARCH), | |||||
.type = NT_FREEBSD_ARCH_TAG, | |||||
.name = NOTE_FREEBSD_VENDOR, | |||||
.desc = MACHINE_ARCH | |||||
}; | |||||
#ifdef GCRT | #ifdef GCRT | ||||
__asm__(".text"); | __asm__(".text"); | ||||
__asm__("eprol:"); | __asm__("eprol:"); | ||||
__asm__(".previous"); | __asm__(".previous"); | ||||
#endif | #endif |