executing init and fini

后端 未结 2 533
星月不相逢
星月不相逢 2021-02-01 04:45

I just read about init and fini sections in ELF files and gave it a try:

#include 
int main(){
  puts(\"main\");
  return 0;
}

void init(){
  put         


        
2条回答
  •  小蘑菇
    小蘑菇 (楼主)
    2021-02-01 05:24

    It is not a bug in ld but in the glibc startup code for the main executable. For shared objects the function set by the -init option is called.


    This is the commit to ld adding the options -init and -fini.
    The _init function of the program isn't called from file glibc-2.21/elf/dl-init.c:58 by the DT_INIT entry by the dynamic linker, but called from __libc_csu_init in file glibc-2.21/csu/elf-init.c:83 by the main executable.

    That is, the function pointer in DT_INIT of the program is ignored by the startup.

    If you compile with -static, fini isn't called, too.

    DT_INIT and DT_FINI should definitely not be used, because they are old-style, see line 255.

    The following works:

    #include 
    
    static void preinit(int argc, char **argv, char **envp) {
        puts(__FUNCTION__);
    }
    
    static void init(int argc, char **argv, char **envp) {
        puts(__FUNCTION__);
    }
    
    static void fini(void) {
        puts(__FUNCTION__);
    }
    
    
    __attribute__((section(".preinit_array"), used)) static typeof(preinit) *preinit_p = preinit;
    __attribute__((section(".init_array"), used)) static typeof(init) *init_p = init;
    __attribute__((section(".fini_array"), used)) static typeof(fini) *fini_p = fini;
    
    int main(void) {
        puts(__FUNCTION__);
        return 0;
    }
    

    $ gcc -Wall a.c
    $ ./a.out
    preinit
    init
    main
    fini
    $ 
    

提交回复
热议问题