gpt4 book ai didi

c++ - 如何使用 dladdr 获取 gnu 间接函数的名称?

转载 作者:塔克拉玛干 更新时间:2023-11-03 02:00:09 25 4
gpt4 key购买 nike

我无法获得带有间接函数的 elf 的 gnu 扩展以与 dladdr 一起工作。

在下面的例子中,fabssinlibm中的两个动态函数,其中sin也是一个间接函数从其指针查找 fabs 效果很好,但未找到 sin。我已经尝试了各种标志 dlopen-rdynamic 但没有成功。

调试器显示了如何从 gnu-indirect-function 变量__sin_avx 评估 sin

我是不是遗漏了什么或者 dladdr 不支持间接函数?

/*
compiled with g++-5 -fPIC -ldl
*/

#include <cmath>
#include <dlfcn.h>
#include <iostream>

char const * name (void * arg)
{
void * h = dlopen (NULL, RTLD_LAZY);

if (h)
{
Dl_info res;
int status = dladdr (arg, & res);
dlclose (h);

if (status && res.dli_sname && arg == res.dli_saddr)
return res.dli_sname;
}

return "";
}

int main ()
{
std::cout << fabs (0.0) << " " << name ((void *) fabs) << std::endl; // found
std::cout << sin (0.0) << " " << name ((void *) sin ) << std::endl; // not found
}

最佳答案

Am I missing something here or are indirect functions not supported by dladdr?

好的,这个很有趣。

因此 ifuncs 通过将原始函数地址(在本例中为 sin)替换为当前平台上动态链接器解析的地址来工作。 sin 可以根据 CPU 能力解析为 4 种实现之一:

libm_ifunc (__sin, (HAS_ARCH_FEATURE (FMA4_Usable) ? __sin_fma4 :
HAS_ARCH_FEATURE (AVX_Usable)
? __sin_avx : __sin_sse2));
weak_alias (__sin, sin)

现在每个 __sin_XXX 都是一个内部 Glibc 函数,不是 exportedlibm.so 就是这样为什么 dladdr 找不到它。

所以答案基本是否定的,dladdr 不能很好地配合 ifuncs...

manages to work if you remove -fPIC

发生这种情况是因为无论何时编译时不使用 -fPIC 编译器都知道当前源文件将转到主可执行文件,因此保证运行时函数地址解析为可执行文件的 PLT 条目。因此,它不是从 GOT 加载它,而是简单地将 PLT 地址传递给 namedladdr,然后愉快地在可执行文件的 symtab 中定位 sin

编辑:

由 Glibc 人员确认 here .

关于c++ - 如何使用 dladdr 获取 gnu 间接函数的名称?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41533519/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com