gcc告诉从哪个变量编译的寄存器

时间:2011-02-02 22:21:15

标签: gcc compiler-construction decompiler binutils readelf

我需要知道从哪个变量是obj文件中的二进制指令的寄存器是从 简而言之:每条指令从寄存器到变量的映射

示例:假设objdump提供了一段obj文件:

MOV R1 5        # move 5 to register R1
SW R2 SP[-20]   # store the value of R2 to address SP-20

我们怎么知道R1从源代码中存储变量,比如 var1 ? R2存储 var2

我在 readelf 的文档中搜索,遗憾的是徒劳无功 (虽然它可以给我源和二进制之间的行映射,但它没有帮助我了)

然后我搜索了gcc和链接器的一些调试选项。找到了一些有用的信息,但他们仍然没有解决我的问题 我发现的信息是:

  • 选项 -fdump-rtl-vartrack 可以跟踪所有变量并且似乎很有用。但是在使用此选项进行编译时,我没有找到预期的* .vartrack转储文件。
  • 选项 * fdump-rtl-vartrack-uid 显示每个变量的唯一ID(DECL_UID)。但是在使用它时我收到了这个错误:cc1:错误:无法识别的命令行选项“-fdump-tree-uid”
  • 选项 fdump-rtl-lreg 转储本地寄存器分配,但我没看到它如何告诉我从reg到变量的映射。

有没有人有经验或想法?

谢谢大家!

黑客攻击......

3 个答案:

答案 0 :(得分:0)

编译器生成混合汇编程序/源代码列表是很常见的。它将显示它编译的源代码,并在其下方显示生成的汇编代码。快速Google提供

http://www.delorie.com/djgpp/v2faq/faq8_20.html

答案 1 :(得分:0)

GCC的“-fverbose-asm”选项可能会有所帮助。它使用变量名称注释编译器的输出。不幸的是,名称通常是编译器发明的临时名称,例如“D.1234”。它仍然可以帮助您了解正在发生的事情。

尝试编写简单的内容并查看:

gcc -g -O0 -S -fverbose-asm foo.c -o foo.s

像GDB这样的调试器使用编译器生成并存储在目标文件中的DWARF调试信息来确定程序中给定点存储变量的位置(对于大多数系统)。如果您的系统使用的是DWARF,那么 readelf 将为您对此信息做一些非常基本的解释。试试这个:

readelf --debug-dump=info foo.o

解码显然不是一件容易的事。如果您想要去,请查看http://dwarfstd.org/处的DWARF标准。

答案 2 :(得分:0)

为此,您可以使用标志:

gcc foo.c -da -dp -fdump-tree-all-raw-lineno

位置:

-da生成所有RTL转储

-dp用注释说明汇编输出,该注释指示 模式和替代方法。

-fdump-tree-all-raw-lineno启用显示语句的行号。

这将创建大约167个文件,每个文件意味着GIMPLE和RTL通过,优化等不同阶段。 这是简单的解释,这是怎么回事:

https://www.cse.iitb.ac.in/~uday/courses/cs715-09/gcc-rtl.pdf

最有用的转储是:

foo.c.227t.optimized
foo.c.229r.expand
foo.c.259r.combine
foo.c.307r.finish

还有其他几种用于不同目的的