Back to index

glibc  2.9
initfini.c
Go to the documentation of this file.
00001 /* Special .init and .fini section support.
00002    Copyright (C) 1995, 1996, 1997, 2000 Free Software Foundation, Inc.
00003    This file is part of the GNU C Library.
00004 
00005    The GNU C Library is free software; you can redistribute it and/or
00006    modify it under the terms of the GNU Lesser General Public
00007    License as published by the Free Software Foundation; either
00008    version 2.1 of the License, or (at your option) any later version.
00009 
00010    In addition to the permissions in the GNU Lesser General Public
00011    License, the Free Software Foundation gives you unlimited
00012    permission to link the compiled version of this file with other
00013    programs, and to distribute those programs without any restriction
00014    coming from the use of this file. (The GNU Lesser General Public
00015    License restrictions do apply in other respects; for example, they
00016    cover modification of the file, and distribution when not linked
00017    into another program.)
00018 
00019    Note that people who make modified versions of this file are not
00020    obligated to grant this special exception for their modified
00021    versions; it is their choice whether to do so. The GNU Lesser
00022    General Public License gives permission to release a modified
00023    version without this exception; this exception also makes it
00024    possible to release a modified version which carries forward this
00025    exception.
00026 
00027    The GNU C Library is distributed in the hope that it will be useful,
00028    but WITHOUT ANY WARRANTY; without even the implied warranty of
00029    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00030    Lesser General Public License for more details.
00031 
00032    You should have received a copy of the GNU Lesser General Public
00033    License along with the GNU C Library; if not, write to the Free
00034    Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
00035    02111-1307 USA.  */
00036 
00037 /* This file is compiled into assembly code which is then munged by a sed
00038    script into two files: crti.s and crtn.s.
00039 
00040    * crti.s puts a function prologue at the beginning of the
00041    .init and .fini sections and defines global symbols for
00042    those addresses, so they can be called as functions.
00043 
00044    * crtn.s puts the corresponding function epilogues
00045    in the .init and .fini sections. */
00046 
00047 #include <stdlib.h>
00048 
00049 /* We use embedded asm for .section unconditionally, as this makes it
00050    easier to insert the necessary directives into crtn.S. */
00051 #define SECTION(x) asm (".section " x )
00052 
00053 /* Embed an #include to pull in the alignment and .end directives. */
00054 asm ("\n#include \"defs.h\"");
00055 
00056 /* The initial common code ends here. */
00057 asm ("\n/*@HEADER_ENDS*/");
00058 
00059 /* To determine whether we need .end and .align: */
00060 asm ("\n/*@TESTS_BEGIN*/");
00061 extern void dummy (void (*foo) (void));
00062 void
00063 dummy (void (*foo) (void))
00064 {
00065   if (foo)
00066     (*foo) ();
00067 }
00068 asm ("\n/*@TESTS_END*/");
00069 
00070 /* The beginning of _init:  */
00071 asm ("\n/*@_init_PROLOG_BEGINS*/");
00072 
00073 static void
00074 call_gmon_start(void)
00075 {
00076   extern void __gmon_start__ (void) __attribute__ ((weak)); /*weak_extern (__gmon_start__);*/
00077   void (*gmon_start) (void) = __gmon_start__;
00078 
00079   if (gmon_start)
00080     gmon_start ();
00081 }
00082 
00083 SECTION (".init");
00084 extern void __attribute__ ((section (".init"))) _init (void);
00085 void
00086 _init (void)
00087 {
00088   /* We cannot use the normal constructor mechanism in gcrt1.o because it
00089      appears before crtbegin.o in the link, so the header elt of .ctors
00090      would come after the elt for __gmon_start__.  One approach is for
00091      gcrt1.o to reference a symbol which would be defined by some library
00092      module which has a constructor; but then user code's constructors
00093      would come first, and not be profiled.  */
00094   call_gmon_start ();
00095 
00096   asm ("ALIGN");
00097   asm("END_INIT");
00098   /* Now the epilog. */
00099   asm ("\n/*@_init_PROLOG_ENDS*/");
00100   asm ("\n/*@_init_EPILOG_BEGINS*/");
00101   SECTION(".init");
00102 }
00103 asm ("END_INIT");
00104 
00105 /* End of the _init epilog, beginning of the _fini prolog. */
00106 asm ("\n/*@_init_EPILOG_ENDS*/");
00107 asm ("\n/*@_fini_PROLOG_BEGINS*/");
00108 
00109 SECTION (".fini");
00110 extern void __attribute__ ((section (".fini"))) _fini (void);
00111 void
00112 _fini (void)
00113 {
00114 
00115   /* End of the _fini prolog. */
00116   asm ("ALIGN");
00117   asm ("END_FINI");
00118   asm ("\n/*@_fini_PROLOG_ENDS*/");
00119 
00120   {
00121     /* Let GCC know that _fini is not a leaf function by having a dummy
00122        function call here.  We arrange for this call to be omitted from
00123        either crt file.  */
00124     extern void i_am_not_a_leaf (void);
00125     i_am_not_a_leaf ();
00126   }
00127 
00128   /* Beginning of the _fini epilog. */
00129   asm ("\n/*@_fini_EPILOG_BEGINS*/");
00130   SECTION (".fini");
00131 }
00132 asm ("END_FINI");
00133 
00134 /* End of the _fini epilog.  Any further generated assembly (e.g. .ident)
00135    is shared between both crt files. */
00136 asm ("\n/*@_fini_EPILOG_ENDS*/");
00137 asm ("\n/*@TRAILER_BEGINS*/");
00138 
00139 /* End of file. */