By-Address Symbol Sort Sections

Regular symbols and thread-local storage symbols can not be sorted together for by-address lookups. While the value of a regular symbol is the address of the function or variable, the value of a thread-local storage symbol is the variable's thread offset. Therefore, regular symbols and thread-local storage symbols use two different sort sections.

The link-editor produces the following by-address symbol sort sections.

.SUNW_dynsymsort

A section of type SHT_SUNW_SYMSORT, containing indexes to regular symbols in the combined .SUNW_ldynsym.dynsym symbol table, sorted by address. Symbols that do not represent variables or functions are not included.

.SUNW_dyntlssort

A section of type SHT_SUNW_TLSSORT, containing indexes to TLS symbols in the combined .SUNW_ldynsym.dynsym symbol table, sorted by offset. This section is only produced if the object file contains TLS symbols.

.SUNW_symtabsort

A section of type SHT_SUNW_SYMSORT, containing indexes to regular symbols in the .symtab symbol table, sorted by address. Symbols that do not represent variables or functions are not included.

.SUNW_symtlssort

A section of type SHT_SUNW_TLSSORT, containing indexes to TLS symbols in the .symtab symbol table, sorted by offset. This section is only produced if the object file contains TLS symbols.

The .SUNW_dynsymsort section and .SUNW_dyntlssort section, require that a .SUNW_ldynsym section be present. Therefore, use of the -z noldynsym option also prevents the creation of these associated sort sections.

The link-editor uses the following rules, in the order that is shown, to select which symbols are referenced by these sort sections.

  • The symbol must have a function or variable type: STT_FUNC, STT_OBJECT, STT_COMMON, or STT_TLS.

  • The following symbols are always included, if present: _DYNAMIC, _end, _fini, _GLOBAL_OFFSET_TABLE_, _init, _PROCEDURE_LINKAGE_TABLE_, and _start.

  • If a global symbol and a weak symbol are found to reference the same item, the weak symbol is included and the global symbol is excluded.

  • The symbol must not be undefined.

  • The symbol must have a non-zero size.

These rules filter out automatically generated compiler and link-editor generated symbols. The symbols that are selected are of interest to the user. However, two cases exist where manual intervention might be necessary to improve the selection process.

  • The rules did not select a needed special symbol. For example, some special symbols have a zero size.

  • Unwanted extra symbols are selected. For example, shared objects can define multiple symbols that reference the same address and have the same size. These alias symbols effectively reference the same item. You might prefer to include only one of a multiple symbol family, within the sort section.

The mapfile keywords DYNSORT and NODYNSORT provide for additional control over symbol selection for by-address sort sections. See SYMBOL_SCOPE and SYMBOL_VERSION Directives.

DYNSORT

Identifies a symbol that should be included in a sort section. The symbol type must be STT_FUNC, STT_OBJECT, STT_COMMON, or STT_TLS.

NODYNSORT

Identifies a symbol that should not be included in a sort section.

For example, an object might provide the following symbol table definitions.

$ elfdump -sN.symtab foo.so.1 | egrep "foo$|bar$"
    [37]    0x4b0   0x1c  FUNC GLOB  D   0 .text      bar
    [38]    0x4b0   0x1c  FUNC WEAK  D   0 .text      foo

The symbols foo and bar represent an aliases pair. By default, when creating a sorted array, only the symbol foo is represented.

$ cc -o foo.so.1 -G foo.c
$ elfdump -S foo.so.1 | egrep "foo$|bar$"
    [13]    0x4b0   0x1c  FUNC WEAK  D   0 .text      foo

In the case where a global and a weak symbol are found by the link-editor to reference the same item, the weak symbol is normally kept. The symbol bar is omitted from the sorted array because of the association to the weak symbol foo.

The following mapfile results in the symbol bar being represented in the sorted array. The symbol foo is omitted.

$ cat mapfile
{
        global:
                bar = DYNSORT;
                foo = NODYNSORT;
};
$ cc -M mapfile -o foo.so.2 -Kpic -G foo.c
$ elfdump -S foo.so.2 | egrep "foo$|bar$"
    [13]    0x4b0   0x1c  FUNC GLOB  D   0 .text      bar