Fix program symbols exported in dynsym section
Prior to this commit TinyCC was exporting symbols defined in programs only when they resolve an undefined symbol of a library. However, the expected behavior (see --export-dynamic in GNU ld manpage) is that all symbols used by libraries and defined by a program should be exported in dynsym section. This is because symbol resolution search first in program and then in libraries, thus allowing program symbol to interpose symbol defined in a library.
This commit is contained in:
5
tccelf.c
5
tccelf.c
@ -1875,23 +1875,22 @@ static void bind_libs_dynsyms(TCCState *s1)
|
|||||||
/* now look at unresolved dynamic symbols and export
|
/* now look at unresolved dynamic symbols and export
|
||||||
corresponding symbol */
|
corresponding symbol */
|
||||||
for_each_elem(s1->dynsymtab_section, 1, esym, ElfW(Sym)) {
|
for_each_elem(s1->dynsymtab_section, 1, esym, ElfW(Sym)) {
|
||||||
if (esym->st_shndx == SHN_UNDEF) {
|
|
||||||
name = (char *) s1->dynsymtab_section->link->data + esym->st_name;
|
name = (char *) s1->dynsymtab_section->link->data + esym->st_name;
|
||||||
sym_index = find_elf_sym(symtab_section, name);
|
sym_index = find_elf_sym(symtab_section, name);
|
||||||
if (sym_index) {
|
if (sym_index) {
|
||||||
/* XXX: avoid adding a symbol if already present because of
|
/* XXX: avoid adding a symbol if already present because of
|
||||||
-rdynamic ? */
|
-rdynamic ? */
|
||||||
sym = &((ElfW(Sym) *)symtab_section->data)[sym_index];
|
sym = &((ElfW(Sym) *)symtab_section->data)[sym_index];
|
||||||
|
if (sym->st_shndx != SHN_UNDEF)
|
||||||
put_elf_sym(s1->dynsym, sym->st_value, sym->st_size,
|
put_elf_sym(s1->dynsym, sym->st_value, sym->st_size,
|
||||||
sym->st_info, 0, sym->st_shndx, name);
|
sym->st_info, 0, sym->st_shndx, name);
|
||||||
} else {
|
} else if (esym->st_shndx == SHN_UNDEF) {
|
||||||
/* weak symbols can stay undefined */
|
/* weak symbols can stay undefined */
|
||||||
if (ELFW(ST_BIND)(esym->st_info) != STB_WEAK)
|
if (ELFW(ST_BIND)(esym->st_info) != STB_WEAK)
|
||||||
tcc_warning("undefined dynamic symbol '%s'", name);
|
tcc_warning("undefined dynamic symbol '%s'", name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
/* Export all non local symbols (for shared libraries) */
|
/* Export all non local symbols (for shared libraries) */
|
||||||
static void export_global_syms(TCCState *s1)
|
static void export_global_syms(TCCState *s1)
|
||||||
|
|||||||
Reference in New Issue
Block a user