我正在挖掘动态重定位过程,并创建了一个非常简单的共享对象:
int func_1(int v)
{
v + 10;
}
int func_2()
{
return func_1(10);
}
编译为:
gcc -fPIC -c libtest.c
gcc -shared -nostdlib -o libtest.so libtest.o
如果我们查看共享对象的动态重定位:
$ objdump -R libtest.so
libtest.so: file format elf32-i386
DYNAMIC RELOCATION RECORDS
OFFSET TYPE VALUE
00002000 R_386_JUMP_SLOT func_1
符号func_1
有一个R_386_JUMP_SLOT,因此func_2
中的调用由PLT解决。我无法找出原因...如果func_1
被声明为私有(static
),则重定位消失,并且调用(通过静态链接器)与相对分支一起解析。为什么从PLT传球比相对跳跃好?
答案 0 :(得分:1)
使用PLT,您可以覆盖来自func_2
的呼叫,以便在运行时调用func_1
的其他版本。例如,通过LD_PRELOAD
。使用static关键字,您只需硬编码自己的func_1
私有版本。它具有灵活性和较小的运行时间开销。