diff options
Diffstat (limited to 'elf/soinit.c')
-rw-r--r-- | elf/soinit.c | 69 |
1 files changed, 65 insertions, 4 deletions
diff --git a/elf/soinit.c b/elf/soinit.c index c0a881ef5d..2015ea2d66 100644 --- a/elf/soinit.c +++ b/elf/soinit.c @@ -6,6 +6,10 @@ #include <libc-internal.h> #include <stdlib.h> +#ifdef HAVE_DWARF2_UNWIND_INFO_STATIC +# include <gccframe.h> +#endif + static void (*const __CTOR_LIST__[1]) (void) __attribute__ ((section (".ctors"))) = { (void (*) (void)) -1 }; @@ -20,9 +24,21 @@ run_hooks (void (*const list[]) (void)) (**list) (); } -static const char __EH_FRAME_BEGIN__[] - __attribute__ ((used, section (".eh_frame"))) - = { }; +#ifdef HAVE_DWARF2_UNWIND_INFO +static char __EH_FRAME_BEGIN__[] + __attribute__ ((section (".eh_frame"))) + = { }; +# ifdef HAVE_DWARF2_UNWIND_INFO_STATIC +extern void __register_frame_info (const void *, struct object *); +extern void __register_frame_info_bases (const void *, struct object *, + void *, void *); +extern void __deregister_frame_info (const void *); +extern void __deregister_frame_info_bases (const void *); +# else +extern void __register_frame (const void *); +extern void __deregister_frame (const void *); +# endif +#endif /* This function will be called from _init in init-first.c. */ void @@ -30,17 +46,62 @@ __libc_global_ctors (void) { /* Call constructor functions. */ run_hooks (__CTOR_LIST__); + +#ifdef HAVE_DWARF2_UNWIND_INFO +# ifdef HAVE_DWARF2_UNWIND_INFO_STATIC + { + static struct object ob; +# if defined CRT_GET_RFIB_TEXT || defined CRT_GET_RFIB_DATA + void *tbase, *dbase; + +# ifdef CRT_GET_RFIB_TEXT + CRT_GET_RFIB_TEXT (tbase); +# else + tbase = NULL; +# endif +# ifdef CRT_GET_RFIB_DATA + CRT_GET_RFIB_DATA (dbase); +# else + dbase = NULL; +# endif + __register_frame_info_bases (__EH_FRAME_BEGIN__, &ob, tbase, dbase); +# else + __register_frame_info (__EH_FRAME_BEGIN__, &ob); +# endif + } +# else + __register_frame (__EH_FRAME_BEGIN__); +# endif +#endif } /* This function becomes the DT_FINI termination function for the C library. */ +#ifndef HAVE_INITFINI_ARRAY +void _fini (void) __attribute__ ((section (".fini"))); /* Just for kicks. */ +void +_fini (void) +#else void __libc_fini (void) +#endif { /* Call destructor functions. */ run_hooks (__DTOR_LIST__); +#ifdef HAVE_DWARF2_UNWIND_INFO +# ifdef HAVE_DWARF2_UNWIND_INFO_STATIC +# if defined CRT_GET_RFIB_TEXT || defined CRT_GET_RFIB_DATA + __deregister_frame_info_bases (__EH_FRAME_BEGIN__); +# else + __deregister_frame_info (__EH_FRAME_BEGIN__); +# endif +# else + __deregister_frame (__EH_FRAME_BEGIN__); +# endif +#endif } - +#ifdef HAVE_INITFINI_ARRAY void (*_fini_ptr) (void) __attribute__ ((section (".fini_array"))) = &__libc_fini; +#endif |