This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

PATCH: Use .init_array/.fini_array sections if available


.init_array/.fini_array is preferred over .init/.fini on Linux. Also
Linux calls functions pointers in .init_array like main (). This patch
uses .init_array/.fini_array if they are available. I tested it on
Linux/ia32, Linux/x86_64 and Linux/ia64. There are no regressions.


H.J.
---
2005-02-09  H.J. Lu  <hongjiu.lu@intel.com>

	* config/linux.h (INIT_ARRAY_LIKE_MAIN): Defined.

	* crtstuff.c: If HAVE_INITFINI_ARRAY is defined, use
	.init_array/.fini_array sections instead of .init/.fini
	sections.

--- gcc/config/linux.h.array	2003-12-03 09:43:14.000000000 -0800
+++ gcc/config/linux.h	2005-02-09 16:51:20.000000000 -0800
@@ -124,3 +124,6 @@ Boston, MA 02111-1307, USA.  */
 #endif
 
 #define TARGET_HAS_F_SETLKW
+
+/* Linux passes (argc, argv, envp) to functions in .init_array.  */
+#define INIT_ARRAY_LIKE_MAIN
--- gcc/crtstuff.c.array	2004-10-14 11:17:55.000000000 -0700
+++ gcc/crtstuff.c	2005-02-10 10:32:43.048912726 -0800
@@ -80,6 +80,15 @@ call_ ## FUNC (void)					\
 }
 #endif
 
+/* Make sure that we don't use CRT_CALL_STATIC_FUNCTION by accident.  */
+#ifdef HAVE_INITFINI_ARRAY
+# undef CRT_CALL_STATIC_FUNCTION
+# undef INIT_SECTION_ASM_OP
+# define INIT_SECTION_ASM_OP
+# else
+# undef INIT_ARRAY_LIKE_MAIN
+#endif
+
 #if defined(OBJECT_FORMAT_ELF) && defined(HAVE_LD_EH_FRAME_HDR) \
     && !defined(inhibit_libc) && !defined(CRTSTUFFT_O) \
     && defined(__GLIBC__) && __GLIBC__ >= 2
@@ -138,6 +147,11 @@ extern void _Jv_RegisterClasses (void *)
 
 /*  Declare a pointer to void function type.  */
 typedef void (*func_ptr) (void);
+#ifdef INIT_ARRAY_LIKE_MAIN
+typedef void (*ctors_ptr) (int, char **, char **);
+#else
+typedef void (*ctors_ptr) (void);
+#endif
 #define STATIC static
 
 #else  /* OBJECT_FORMAT_ELF */
@@ -169,15 +183,15 @@ CTOR_LIST_BEGIN;
 #elif defined(CTORS_SECTION_ASM_OP)
 /* Hack: force cc1 to switch to .data section early, so that assembling
    __CTOR_LIST__ does not undo our behind-the-back change to .ctors.  */
-static func_ptr force_to_data[1] __attribute__ ((__unused__)) = { };
+static ctors_ptr force_to_data[1] __attribute__ ((__unused__)) = { };
 asm (CTORS_SECTION_ASM_OP);
-STATIC func_ptr __CTOR_LIST__[1]
-  __attribute__ ((__unused__, aligned(sizeof(func_ptr))))
-  = { (func_ptr) (-1) };
+STATIC ctors_ptr __CTOR_LIST__[1]
+  __attribute__ ((__unused__, aligned(sizeof(ctors_ptr))))
+  = { (ctors_ptr) (-1) };
 #else
-STATIC func_ptr __CTOR_LIST__[1]
-  __attribute__ ((__unused__, section(".ctors"), aligned(sizeof(func_ptr))))
-  = { (func_ptr) (-1) };
+STATIC ctors_ptr __CTOR_LIST__[1]
+  __attribute__ ((__unused__, section(".ctors"), aligned(sizeof(ctors_ptr))))
+  = { (ctors_ptr) (-1) };
 #endif /* __CTOR_LIST__ alternatives */
 
 #ifdef DTOR_LIST_BEGIN
@@ -287,8 +301,16 @@ __do_global_dtors_aux (void)
   completed = 1;
 }
 
+#ifdef HAVE_INITFINI_ARRAY
+static const func_ptr __do_global_dtors_aux_array []
+  __attribute__ ((used, section (".fini_array"), aligned (sizeof (func_ptr)))) =
+{
+  &__do_global_dtors_aux
+};
+#else
 /* Stick a call to __do_global_dtors_aux into the .fini section.  */
 CRT_CALL_STATIC_FUNCTION (FINI_SECTION_ASM_OP, __do_global_dtors_aux)
+#endif
 
 #if defined(USE_EH_FRAME_REGISTRY) || defined(JCR_SECTION_NAME)
 /* Stick a call to __register_frame_info into the .init section.  For some
@@ -317,7 +339,15 @@ frame_dummy (void)
 #endif /* JCR_SECTION_NAME */
 }
 
+#ifdef HAVE_INITFINI_ARRAY
+static const func_ptr frame_dummy_array []
+  __attribute__ ((used, section (".init_array"), aligned (sizeof (func_ptr)))) =
+{
+  &frame_dummy
+};
+#else
 CRT_CALL_STATIC_FUNCTION (INIT_SECTION_ASM_OP, frame_dummy)
+#endif
 #endif /* USE_EH_FRAME_REGISTRY || JCR_SECTION_NAME */
 
 #else  /* OBJECT_FORMAT_ELF */
@@ -418,15 +448,15 @@ CTOR_LIST_END;
 #elif defined(CTORS_SECTION_ASM_OP)
 /* Hack: force cc1 to switch to .data section early, so that assembling
    __CTOR_LIST__ does not undo our behind-the-back change to .ctors.  */
-static func_ptr force_to_data[1] __attribute__ ((__unused__)) = { };
+static ctors_ptr force_to_data[1] __attribute__ ((__unused__)) = { };
 asm (CTORS_SECTION_ASM_OP);
-STATIC func_ptr __CTOR_END__[1]
-  __attribute__((aligned(sizeof(func_ptr))))
-  = { (func_ptr) 0 };
+STATIC ctors_ptr __CTOR_END__[1]
+  __attribute__((aligned(sizeof(ctors_ptr))))
+  = { (ctors_ptr) 0 };
 #else
-STATIC func_ptr __CTOR_END__[1]
-  __attribute__((section(".ctors"), aligned(sizeof(func_ptr))))
-  = { (func_ptr) 0 };
+STATIC ctors_ptr __CTOR_END__[1]
+  __attribute__((section(".ctors"), aligned(sizeof(ctors_ptr))))
+  = { (ctors_ptr) 0 };
 #endif
 
 #ifdef DTOR_LIST_END
@@ -472,15 +502,31 @@ STATIC void *__JCR_END__[1] 
 
 #ifdef OBJECT_FORMAT_ELF
 static void __attribute__((used))
+#ifdef INIT_ARRAY_LIKE_MAIN
+__do_global_ctors_aux (int argc, char *argv[], char *envp[])
+#else
 __do_global_ctors_aux (void)
+#endif
 {
-  func_ptr *p;
-  for (p = __CTOR_END__ - 1; *p != (func_ptr) -1; p--)
+  ctors_ptr *p;
+  for (p = __CTOR_END__ - 1; *p != (ctors_ptr) -1; p--)
+#ifdef INIT_ARRAY_LIKE_MAIN
+    (*p) (argc, argv, envp);
+#else
     (*p) ();
+#endif
 }
 
+#ifdef HAVE_INITFINI_ARRAY
+static const ctors_ptr __do_global_ctors_aux_array []
+  __attribute__ ((used, section (".init_array"), aligned (sizeof (ctors_ptr)))) =
+{
+  &__do_global_ctors_aux
+};
+#else
 /* Stick a call to __do_global_ctors_aux into the .init section.  */
 CRT_CALL_STATIC_FUNCTION (INIT_SECTION_ASM_OP, __do_global_ctors_aux)
+#endif
 #else  /* OBJECT_FORMAT_ELF */
 
 /* Stick the real initialization code, followed by a normal sort of
@@ -527,11 +573,11 @@ extern void __do_global_ctors (void);
 void
 __do_global_ctors (void)
 {
-  func_ptr *p;
+  ctors_ptr *p;
 #if defined(USE_EH_FRAME_REGISTRY) || defined(JCR_SECTION_NAME)
   __do_global_ctors_1();
 #endif
-  for (p = __CTOR_END__ - 1; *p != (func_ptr) -1; p--)
+  for (p = __CTOR_END__ - 1; *p != (ctors_ptr) -1; p--)
     (*p) ();
 }
 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]