from hello.c to hello.asm (part one)
I- init
The code I want to write is the assembly analogue of the following C code:
//hello.c #include <stdio.h> int main(int argc, char *argv[]) { return (printf("Hello World!\n") - 13); } The printf function returns the total number of printed characters,or a negative value if an output error occurs The "Hello World!\n" is a 13 characters string.In this case, the program will return (13-13) or zero to the OS.
II- Compile-time, run-time
the classical "compilation" flow :
Tools:
And the two important times:compile-time and run-time
What we do mean by Linking:
Linking is a way taking object files and creating loadable executable modules with correct references to required libraries, data, and procedures
There is somehow a missing time: loading-time:
The loading time as its name suggests:
Placing a program image into main memory for execution
III- Linking :static versus dynamic
Static and dynamic linking are two processes of collecting and combining multiple object files in order to create a single executable, it is performed by programs called link editors.
the main task of linking is to clean up unresolved symbols
In fact, there are two kind of linker:
- compile-time linker (static) OR linking during compile-time: acting during compile-time.All needed libraries and modules (c standard library, user-defined modules and libraries) used in the program are copied into the final executable image during compile-time (last step in the compilation process).
- run-time linker (dynamic linker) OR linking during run-time : acting during run-time.Only the NAME (or refernce) of all needed (shared) libraries and (shared) modules (c standard library, user-defined modules and libraries) used in the program is copied into the final executable image.the ACTUAL and true linking is done by the OS during running-time!
IV- Static linking
In statically-linked programs, all code is contained in a single executable module!
The static option let us create a statically-linked hello executable:
The size of the produced executable is ...huge: 825K !All standard library is contained in the hello module!
Does the produced module( hello) depends on some external libraries? ldd is a Linux command line utility that is used in case we want to know the shared library dependencies of an executable.
The answer is: not dynamic executable.it means our hello does not depend on any external library. Because it is a statically-linked executable.It is a self-contained executable.
Let us disassemble the executable module with objdump:
objdump -Mintel -d hello
Observe the call to printf: call 41090 <_IO_printf> ; the main function calls for printf directly as it is part of the executable.
V- Dynamic linking
In dynamic linking is performed at run time by the OS.How to produce a dynamically-linked executable?
The gcc tool produces, by default, a dynamically-linked executable:
The size of the produced executable is only: 17K (compare to 825K) !
Why? Because the standard library is not merged with the hello module for dynamically-linked technique.
Where is the catch?
First, let disassemble the dynamically-linked executable :
objdump -Mintel -d hello
Observe the call to printf: call 1050 <printf@plt> ; the main function calls for printf@plt: this is a only a reference to the real printf function.It is a "fake" call!. This "fake" call is used to call external procedures/functions whose address isn't known in the time of linking (during compile-time), and is left to be resolved by the dynamic linker at run time.
PLT: Procedure Linkage Table
The presence of PLT is an indication that the executable is produced by dynamically-linked technique!
Let me put it this way :
The final binary (hello) contains some "extra" code and with the help of some structures (PLT,GOT) will find printf at runtime.
Again: Does the produced module( hello) by dynamically-linked technique depends on some external libraries?
ldd is a Linux command line utility that is used in case we want to know the shared library dependencies of an executable.
Here, we see, hello module depends on many shared libraries (libc, ld-linux,...). During run-time, hello module needs the shared libraries mentioned above: libc, ld-linux,...
In dynamic linking, sole the names of the external libraries (shared libraries) are placed in the final executable file. The ACTUAL and true linking is taking place at run time when both executable file and shared libraries are placed in the memory:
To sum it up:
- compile-time linker: is used during compile-time for statically-linked executable and dynamically-linked executable (but for different purposes)
- run-time linker or dynamic linker: is used during load-time/run-time only for dynamically-linked executable.Its main role is fixing unresolved symbols
VI- Linkers
What is the name of the compile time linker in Linux? ld
- to resolve all possible resolvable symbols
What is the name of the run-time linker in Linux? ld-linux.so
- to resolve, during load-time, all yet unresolved symbols
Where is the loader located in Linux? part kernel / part ld-linux.so
nota: ld-linux.so is a symbolic link to /lib64/ld-linux-x86-64.so.2
Stay tuned