diff options
Diffstat (limited to 'compiler-rt/lib/crt/crtbegin.c')
-rw-r--r-- | compiler-rt/lib/crt/crtbegin.c | 48 |
1 files changed, 35 insertions, 13 deletions
diff --git a/compiler-rt/lib/crt/crtbegin.c b/compiler-rt/lib/crt/crtbegin.c index 2450ce54e31b..24bea1a2c3a7 100644 --- a/compiler-rt/lib/crt/crtbegin.c +++ b/compiler-rt/lib/crt/crtbegin.c @@ -10,11 +10,13 @@ __attribute__((visibility("hidden"))) void *__dso_handle = &__dso_handle; +#ifdef EH_USE_FRAME_REGISTRY __extension__ static void *__EH_FRAME_LIST__[] __attribute__((section(".eh_frame"), aligned(sizeof(void *)))) = {}; extern void __register_frame_info(const void *, void *) __attribute__((weak)); extern void *__deregister_frame_info(const void *) __attribute__((weak)); +#endif #ifndef CRT_HAS_INITFINI_ARRAY typedef void (*fp)(void); @@ -32,10 +34,11 @@ static void __attribute__((used)) __do_init() { return; __initialized = 1; +#ifdef EH_USE_FRAME_REGISTRY static struct { void *p[8]; } __object; if (__register_frame_info) __register_frame_info(__EH_FRAME_LIST__, &__object); - +#endif #ifndef CRT_HAS_INITFINI_ARRAY const size_t n = __CTOR_LIST_END__ - __CTOR_LIST__ - 1; for (size_t i = n; i >= 1; i--) __CTOR_LIST__[i](); @@ -45,17 +48,26 @@ static void __attribute__((used)) __do_init() { #ifdef CRT_HAS_INITFINI_ARRAY __attribute__((section(".init_array"), used)) static void (*__init)(void) = __do_init; -#else // CRT_HAS_INITFINI_ARRAY -#if defined(__i386__) || defined(__x86_64__) +#elif defined(__i386__) || defined(__x86_64__) __asm__(".pushsection .init,\"ax\",@progbits\n\t" "call " __USER_LABEL_PREFIX__ "__do_init\n\t" ".popsection"); -#elif defined(__arm__) +#elif defined(__arm__) || defined(__aarch64__) __asm__(".pushsection .init,\"ax\",%progbits\n\t" "bl " __USER_LABEL_PREFIX__ "__do_init\n\t" ".popsection"); -#endif // CRT_HAS_INITFINI_ARRAY -#endif +#elif defined(__powerpc__) || defined(__powerpc64__) +__asm__(".pushsection .init,\"ax\",@progbits\n\t" + "bl " __USER_LABEL_PREFIX__ "__do_init\n\t" + "nop\n\t" + ".popsection"); +#elif defined(__sparc__) +__asm__(".pushsection .init,\"ax\",@progbits\n\t" + "call " __USER_LABEL_PREFIX__ "__do_init\n\t" + ".popsection"); +#else +#error "crtbegin without .init_fini array unimplemented for this architecture" +#endif // CRT_HAS_INITFINI_ARRAY #ifndef CRT_HAS_INITFINI_ARRAY static fp __DTOR_LIST__[] @@ -73,25 +85,35 @@ static void __attribute__((used)) __do_fini() { __cxa_finalize(__dso_handle); #ifndef CRT_HAS_INITFINI_ARRAY - if (__deregister_frame_info) - __deregister_frame_info(__EH_FRAME_LIST__); - const size_t n = __DTOR_LIST_END__ - __DTOR_LIST__ - 1; for (size_t i = 1; i <= n; i++) __DTOR_LIST__[i](); #endif +#ifdef EH_USE_FRAME_REGISTRY + if (__deregister_frame_info) + __deregister_frame_info(__EH_FRAME_LIST__); +#endif } #ifdef CRT_HAS_INITFINI_ARRAY __attribute__((section(".fini_array"), used)) static void (*__fini)(void) = __do_fini; -#else // CRT_HAS_INITFINI_ARRAY -#if defined(__i386__) || defined(__x86_64__) +#elif defined(__i386__) || defined(__x86_64__) __asm__(".pushsection .fini,\"ax\",@progbits\n\t" "call " __USER_LABEL_PREFIX__ "__do_fini\n\t" ".popsection"); -#elif defined(__arm__) +#elif defined(__arm__) || defined(__aarch64__) __asm__(".pushsection .fini,\"ax\",%progbits\n\t" "bl " __USER_LABEL_PREFIX__ "__do_fini\n\t" ".popsection"); -#endif +#elif defined(__powerpc__) || defined(__powerpc64__) +__asm__(".pushsection .fini,\"ax\",@progbits\n\t" + "bl " __USER_LABEL_PREFIX__ "__do_fini\n\t" + "nop\n\t" + ".popsection"); +#elif defined(__sparc__) +__asm__(".pushsection .fini,\"ax\",@progbits\n\t" + "call " __USER_LABEL_PREFIX__ "__do_fini\n\t" + ".popsection"); +#else +#error "crtbegin without .init_fini array unimplemented for this architecture" #endif // CRT_HAS_INIT_FINI_ARRAY |