Linker and Libraries Guide

Using the -z direct Option

The -z direct option provides a mechanism of establishing direct bindings to any dependencies that follow the option on the link-edit command line. Unlike the -B direct option, no direct bindings are established within the object that is being built.

This option is well suited for building objects that are designed to be interposed upon. For example, shared objects are sometimes designed that contain a number of default, or fall back, interfaces. Applications are free to define their own definitions of these interfaces with the intent that the application definitions are bound to at runtime. To allow an application to interpose on the interfaces of a shared object, build the shared object using the -z direct option rather than the -B direct option.

The -z direct option is also useful if you want to be selective over directly binding to one or more dependencies. The -z nodirect option allows you to toggle the use of direct bindings between the dependencies supplied with a link-edit.

From the components used in the previous example, a directly bound object can be produced.

$ cc -o -G -Kpic X.c -R. -zdirect
$ cc -o prog3 -R. main.c

The direct binding information can be viewed with elfdump(1).

$ elfdump -y
    [6]  D           <self>         a
    [7]  DB      [1]         b

The function b() has been bound directly to the dependency The function a()is defined as having a potential direct binding, “D”, with the object, but no direct binding is established.

The LD_DEBUG environment variable can be used to observe the runtime bindings.

$ LD_DEBUG=symbols,bindings,detail prog3
06177: symbol=a;  lookup in file=prog3  [ ELF ]
06177: symbol=a;  lookup in file=./  [ ELF ]
06177: binding file=./ to file=./ symbol `a'
06177: symbol=b;  lookup in file=./  [ ELF ]
06177: binding file=./ to file=./ symbol `b'  (direct)

The lari(1) utility can also reveal the direct binding information.

$ lari prog3
[2:2ESD]: a(): ./
[2:0]: a(): ./
[2:1ED]: b(): ./
[2:1ED]: b(): ./

The function a() defined by continues to satisfy the default symbol reference made by However, the function b() defined in has now been bound to directly from the reference made by