The got plt resembles the IAT (Import Address Table) in a Windows PE file.
To make the code address irrelevant, the basic idea is to put the relevant parts of the address into the data section.
The elf's approach is to create an array of pointers to these variables in the data segment, called Global offset table,got, which can be indirectly referenced by the corresponding item in the GOT when the code needs to reference the global variable.
The got itself is placed in the data segment , so it can be modified when the module is loaded. Delay Binding , the basic idea is to bind the function when it is first used
A very simple code:
#include <stdio.h><stdlib.h>int HelloWorld () { printf (" helloworld\n"); return 0 ;} int Main () { helloWorld (); return 0 ;}
The first instruction is the instruction of indirect jump through got. If the connector has initialized the item in the initialization phase, and the address of puts () is populated with the entry, then the result of this jump instruction is what we expect, jump to puts (), and implement the function to call correctly.
However, in order to implement delay binding, the linker does not fill in the address of puts () in the initialization phase, but instead fills in the address of the next instruction in the [email protected] entry.
So the effect of the first instruction is to jump to the second instruction, which is equivalent to no action. The second instruction is to press a number n onto the stack, which is a symbol of puts () referencing the subscript in the Reposition table ". Rel.plt".
Then there is a push instruction that presses the module ID onto the stack and jumps to 0xf7ff04f0 execution, so what address is this address? The answer is _dl_runtime_resolve, which is explained below.
The elf splits the got into two tables, ". Got" and ". Got.plt". where ". Got" is used to hold the address of a global variable reference, ". Got.plt" is used to hold the address of the function reference, and all references to external functions are placed in ". Got.plt".
From the above two pictures you can see: R_386_glob_dat is located in the. Got segment, R_386_jump_slot is located in the. GOT.PLT segment.
The top three items of ". Got.plt" are of special significance.
The first item saved is the address of the ". Dynamic" segment;
The second item holds the ID of this module, which is the value of the push in which it was previously seen;
The third item holds the address of the _dl_runtime_resolve () function, before jumping to the address 0xf7ff04f0.
After that is the address that you can see is pointing to the. PLT segment, at the time of the link, the. PLT segment is usually combined with a code snippet and so on together into a readable executable segment.
You can see the address of [email protected] 0x80482f6 located in the. Plt. And the address of the puts in the Got table entry 0x080482f6 is the address of the [email protected] second instruction.
Resources:
"Self-cultivation of programmers" dynamic link
"In-depth understanding of computer Systems", chapter seventh, links
Got & PLT