Index: sys/kern/kern_linker.c =================================================================== --- sys/kern/kern_linker.c +++ sys/kern/kern_linker.c @@ -613,6 +613,8 @@ return (NULL); lf->ctors_addr = 0; lf->ctors_size = 0; + lf->dtors_addr = 0; + lf->dtors_size = 0; lf->refs = 1; lf->userrefs = 0; lf->flags = 0; Index: sys/kern/link_elf_obj.c =================================================================== --- sys/kern/link_elf_obj.c +++ sys/kern/link_elf_obj.c @@ -544,6 +544,17 @@ lf->ctors_addr = ef->progtab[pb].addr; lf->ctors_size = shdr[i].sh_size; } + } else if ((ef->progtab[pb].name != NULL && + strcmp(ef->progtab[pb].name, ".dtors") == 0) || + shdr[i].sh_type == SHT_FINI_ARRAY) { + if (lf->dtors_addr != 0) { + printf( + "%s: multiple dtor sections in %s\n", + __func__, filename); + } else { + lf->dtors_addr = ef->progtab[pb].addr; + lf->dtors_size = shdr[i].sh_size; + } } /* Update all symbol values with the offset. */ @@ -612,7 +623,7 @@ } static void -link_elf_invoke_ctors(caddr_t addr, size_t size) +link_elf_invoke_cbs(caddr_t addr, size_t size) { void (**ctor)(void); size_t i, cnt; @@ -653,7 +664,7 @@ /* Apply protections now that relocation processing is complete. */ link_elf_protect(ef); - link_elf_invoke_ctors(lf->ctors_addr, lf->ctors_size); + link_elf_invoke_cbs(lf->ctors_addr, lf->ctors_size); return (0); } @@ -1012,6 +1023,19 @@ lf->ctors_size = shdr[i].sh_size; } + } else if (!strcmp(ef->progtab[pb].name, + ".dtors") || + shdr[i].sh_type == SHT_FINI_ARRAY) { + if (lf->dtors_addr != 0) { + printf( + "%s: multiple dtor sections in %s\n", + __func__, filename); + } else { + lf->dtors_addr = + (caddr_t)mapbase; + lf->dtors_size = + shdr[i].sh_size; + } } } else if (shdr[i].sh_type == SHT_PROGBITS) ef->progtab[pb].name = "<>"; @@ -1196,7 +1220,7 @@ #endif link_elf_protect(ef); - link_elf_invoke_ctors(lf->ctors_addr, lf->ctors_size); + link_elf_invoke_cbs(lf->ctors_addr, lf->ctors_size); *result = lf; out: @@ -1216,6 +1240,8 @@ elf_file_t ef = (elf_file_t) file; u_int i; + link_elf_invoke_cbs(file->dtors_addr, file->dtors_size); + /* Notify MD code that a module is being unloaded. */ elf_cpu_unload_file(file); Index: sys/sys/linker.h =================================================================== --- sys/sys/linker.h +++ sys/sys/linker.h @@ -82,8 +82,10 @@ int id; /* unique id */ caddr_t address; /* load address */ size_t size; /* size of file */ - caddr_t ctors_addr; /* address of .ctors */ - size_t ctors_size; /* size of .ctors */ + caddr_t ctors_addr; /* address of .ctors/.init_array */ + size_t ctors_size; /* size of .ctors/.init_array */ + caddr_t dtors_addr; /* address of .dtors/.fini_array */ + size_t dtors_size; /* size of .dtors/.fini_array */ int ndeps; /* number of dependencies */ linker_file_t* deps; /* list of dependencies */ STAILQ_HEAD(, common_symbol) common; /* list of common symbols */