Back to index

glibc  2.9
pt-initfini.c
Go to the documentation of this file.
00001 /* Special .init and .fini section support.  Linuxthread version.
00002    Copyright (C) 1995,1996,1997,2000,2001,2002 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
00006    and/or modify it under the terms of the GNU Lesser General Public
00007    License as published by the Free Software Foundation; either
00008    version 2 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 Library 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    The GNU C Library is distributed in the hope that it will be
00020    useful, but WITHOUT ANY WARRANTY; without even the implied warranty
00021    of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00022    GNU Lesser General Public License for more details.
00023 
00024    You should have received a copy of the GNU Lesser General Public
00025    License along with the GNU C Library; see the file COPYING.LIB.  If not,
00026    write to the Free Software Foundation, 59 Temple Place - Suite 330,
00027    Boston, MA 02111-1307, USA.  */
00028 
00029 /* This file is compiled into assembly code which is then munged by a sed
00030    script into two files: crti.s and crtn.s.
00031 
00032    * crti.s puts a function prologue at the beginning of the
00033    .init and .fini sections and defines global symbols for
00034    those addresses, so they can be called as functions.
00035 
00036    * crtn.s puts the corresponding function epilogues
00037    in the .init and .fini sections. */
00038 
00039 #include <stdlib.h>
00040 
00041 /* We use embedded asm for .section unconditionally, as this makes it
00042    easier to insert the necessary directives into crtn.S. */
00043 #define SECTION(x) asm (".section " x )
00044 
00045 /* Embed an #include to pull in the alignment and .end directives. */
00046 asm ("\n#include \"defs.h\"");
00047 
00048 /* The initial common code ends here. */
00049 asm ("\n/*@HEADER_ENDS*/");
00050 
00051 /* To determine whether we need .end and .align: */
00052 asm ("\n/*@TESTS_BEGIN*/");
00053 extern void dummy (void (*foo) (void));
00054 void
00055 dummy (void (*foo) (void))
00056 {
00057   if (foo)
00058     (*foo) ();
00059 }
00060 asm ("\n/*@TESTS_END*/");
00061 
00062 /* The beginning of _init:  */
00063 asm ("\n/*@_init_PROLOG_BEGINS*/");
00064 
00065 static void
00066 call_initialize_minimal (void)
00067 {
00068   extern void __pthread_initialize_minimal_internal (void)
00069     __attribute ((visibility ("hidden")));
00070 
00071   __pthread_initialize_minimal_internal ();
00072 }
00073 
00074 SECTION (".init");
00075 extern void __attribute__ ((section (".init"))) _init (void);
00076 void
00077 _init (void)
00078 {
00079   /* The very first thing we must do is to set up the registers.  */
00080   call_initialize_minimal ();
00081 
00082   asm ("ALIGN");
00083   asm("END_INIT");
00084   /* Now the epilog. */
00085   asm ("\n/*@_init_PROLOG_ENDS*/");
00086   asm ("\n/*@_init_EPILOG_BEGINS*/");
00087   SECTION(".init");
00088 }
00089 asm ("END_INIT");
00090 
00091 /* End of the _init epilog, beginning of the _fini prolog. */
00092 asm ("\n/*@_init_EPILOG_ENDS*/");
00093 asm ("\n/*@_fini_PROLOG_BEGINS*/");
00094 
00095 SECTION (".fini");
00096 extern void __attribute__ ((section (".fini"))) _fini (void);
00097 void
00098 _fini (void)
00099 {
00100 
00101   /* End of the _fini prolog. */
00102   asm ("ALIGN");
00103   asm ("END_FINI");
00104   asm ("\n/*@_fini_PROLOG_ENDS*/");
00105 
00106   {
00107     /* Let GCC know that _fini is not a leaf function by having a dummy
00108        function call here.  We arrange for this call to be omitted from
00109        either crt file.  */
00110     extern void i_am_not_a_leaf (void);
00111     i_am_not_a_leaf ();
00112   }
00113 
00114   /* Beginning of the _fini epilog. */
00115   asm ("\n/*@_fini_EPILOG_BEGINS*/");
00116   SECTION (".fini");
00117 }
00118 asm ("END_FINI");
00119 
00120 /* End of the _fini epilog.  Any further generated assembly (e.g. .ident)
00121    is shared between both crt files. */
00122 asm ("\n/*@_fini_EPILOG_ENDS*/");
00123 asm ("\n/*@TRAILER_BEGINS*/");
00124 
00125 /* End of file. */