• No se han encontrado resultados

Igualdad y Educación Afectivo Sexual y de Género

The concept of dynamic linking is at the very core of the concept of dynamic libraries. It is practically impossible to fully understand how the dynamic libraries work without understanding the complex interplay between the dynamic library, the client executable, and the operating system. The focus of this section is to provide the necessary broad level understanding of the process of dynamic linking. Once its essence is understood, the subsequent sections of this document will pay the due attention to the details.

So, let’s see what really happens during the process of dynamic linking.

Part 1: Building the Dynamic Library

As the previous figures suggest, the process of building a dynamic library is a complete build, as it encompasses both compilation (converting the source into the binary object files) as well as resolving the references. The product of the dynamic library building process is the binary file whose nature is identical to the nature of executable, the only difference being that dynamic library lacks the startup routines that would allow it to be started as independent program (Figure 4-5). 0001011 11 011 001 1110010 11 001 011 0110011 11 110 010 110110 000111 1011001 1001011 x = A; Y = B; Dynamic library

LINKER

Export symbols

COMPILER

PROJECT

Source files Object files

Figure 4-5. Building the dynamic library

Here are some notes to consider:

In Windows, building a dynamic library strictly requires that all the references must be •

resolved. If the dynamic library code calls a function in some other dynamic library, that other library and the references symbol it contains must be known at build time.

In Linux, however, the default option allows some more flexibility, allowing that some the •

symbols be unresolved with the expectation that they will eventually show up in the final binary after some other dynamic library is linked in. Additionally, the Linux linker provides the option to fully match the Windows linker’s strictness.

In Linux, it is possible to modify the dynamic library to make it runnable by itself (still •

researching whether such option exists on Windows). In fact, the libc (C runtime library) is executable by itself; when invoked by typing its filename into the shell window, it prints a message on the screen and terminates. For more details of how to implement such feature, please check Chapter 14.

Part 2: Playing by Trust While Building the Client Executable (Looking

for the Symbols Only)

The next stage in the scenario of using a dynamic library happens when you try to build the executable that intends on using the dynamic library at runtime. Unlike the static libraries scenario in which the linker is creating the executable on its own at will, the scenario of linking the dynamic libraries is peculiar in that the linker tries to combine its current work with the existing results of the previously completed linking procedure that created dynamic library binary.

The crucial detail in this part of the story is that linker pays almost all of its attention to the dynamic library’s symbols. It appears that at this stage the linker is almost not interested in any of the sections, neither code (.text), nor data (.data/.bss).

More specifically, the linker in this stage of operation “plays it by trust.”

It does not examine the binary of the dynamic library thoroughly; it neither tries to find the sections or their sizes, nor attempts to integrate them into the resultant binary. Instead, it solely tries to verify that the dynamic library contains the symbols needed by the resultant binary. Once it finds it, it completes the task and creates the executable binary (see Figure 4-6).

0001011 11 011 001 1110010 11 001 011 0110011 11 110 010 110110 000111 1011001 1001011 x = A; Y = B; Shared library EXECUTABLE

LINKER

COMPILER

PROJECT

Source files Object files

At build time, linker only looks for the shared library symbols;

integration of shared lib segments will happen at load time.

Figure 4-6. Build time linking with a dynamic library

The approach of “playing by trust” is not completely unintuitive. Let’s consider a real-life example: if you tell someone that in order to mail a letter he needs to go to the kiosk in the nearby square and buy a postage stamp, you are essentially basing your advice on reasonable amount of trust. You do know that there should be a kiosk on the square, and that it carries postage stamps. The fact that you don’t know the particular details of the kiosk operation (working hours, who works there, the price of postage stamps) does not diminish the validity of your advice, as at runtime all these less important details will be resolved. The idea of dynamic linking is based on completely analogous assumptions.

Let it be noticed, however, that this amount of trust leaves open doors for many interesting scenarios, all of which fall under the “build with one, load the other” paradigm. The practical implications vary from peculiar software design tricks all the way to the whole new paradigm (plug-ins), both of which will be discussed later in the book.

Part 3: Runtime Loading and Symbol Resolution

The events happening at load time are of crucial importance, as this is the time when the confidence that the linker had in the dynamic library’s promises needs to be confirmed. Previously, the build procedure (possibly completed on a build machine “A”) examined the copy of dynamic library binary in the search for symbols that executable needs. Now what needs to happen at runtime (possibly on different, runtime machine “B”) is the following:

1. The dynamic library binary file needs to be found.

Each operating system has a set of rules stipulating in which directory the loader should look for the dynamic libraries’ binaries.

2. The dynamic library needs to be successfully loaded into the process.

This is the moment where the promise of build-time linking must be fulfilled at runtime. In fact, the dynamic library loaded at runtime must carry the identical set of symbols

promised to be available at build time. More specifically, in the case of function symbols

the term “identical” means that the function symbols found in the dynamic library at runtime must exactly match the complete function signature (affiliations, name, list of arguments, linkage/calling convention) promised at build time.

Interestingly enough, it is not required that the actual assembly code (i.e., the sections

contents) of the dynamic library found at runtime matches the code found in the dynamic library binary used during the build time. This opens up a lot of interesting scenarios which will be discussed in detail later on.

3. The executable symbols need to be resolved to point to the right address in the part of process of memory map where the dynamic library is mapped into.

It is this stage the integration of dynamic library into the process memory map truly deserves to be called dynamic linking, as unlike the conventional linking it happens at

load time.

If all the steps of this stage completed successfully, you may have your application executing the code contained in the dynamic library, as illustrated in Figure 4-7.

Documento similar