Sor*_*puc 4 c linux elf debug-symbols binutils
给定函数或变量运行时地址,我的代码需要找出名称,如果是变量,则键入符号的信息.或至少提供足够的信息,以便以后离线提取名称(和类型信息).
这是Linux代码,假设调试信息可用.
我试着研究ELF文件格式,binutils以及除了主题之外的所有内容都是巨大的,所以我希望有人可以帮我缩小范围.
我可以看到以下类型的解决方案:
找到当前加载到内存中的模块的代码/数据段的范围 - 怎么做?将地址的模块和段名称和偏移量保存在其段中.离线然后使用binutils在模块的调试信息中找到符号 - 再次,如何做?
使用一些我不知道的API /系统服务在运行时找到符号和信息 - 如何?
先感谢您.
GNU libc 为此目的提供了一个dladdr函数.但是,它只适用于函数,而不适用于变量.
#define _GNU_SOURCE /* See feature_test_macros(7) */
#include <dlfcn.h>
int dladdr(void *addr, Dl_info *info);
The function dladdr() takes a function pointer and tries to resolve
name and file where it is located. Information is stored in the
Dl_info structure:
typedef struct {
const char *dli_fname; /* Pathname of shared object that
contains address */
void *dli_fbase; /* Address at which shared object
is loaded */
const char *dli_sname; /* Name of symbol whose definition
overlaps addr */
void *dli_saddr; /* Exact address of symbol named
in dli_sname */
} Dl_info;
If no symbol matching addr could be found, then dli_sname and dli_saddr
are set to NULL.
dladdr() returns 0 on error, and nonzero on success.
Run Code Online (Sandbox Code Playgroud)
当然,通常我会从gdb做这种事情,而不是程序本身.
C 是一种完全编译语言。变量的名称和类型以及其他信息通常在编译过程中被丢弃。
一个例外是,大多数编译器将生成包含调试信息的可执行文件,以便实时调试器可以访问此信息。这些信息完全是特定于操作系统的,甚至是特定于编译器的,甚至可能位于程序无法访问的内存部分中。