例如,如果我在,perf report我可以按 Enter 键跟随分支。如果垃圾箱正在使用-g某些来源也会显示。
我真的不需要源代码,但如果我可以跟随跳转,那就非常方便了。我该怎么做才能使阅读汇编变得更容易?由于我在 Linux 上,所以我最终运行了 perf 并使用报告来阅读此内容
objdump -d --visualize-jumps=color很有趣,尽管在大型二进制文件上无法使用,因为它有很多行列。在我随机放置的一个较小的二进制文件中(在 32 位模式下测试 64 位 _Atomic 变量的对齐,以防有人好奇;这个二进制文件来自 clang):
objdump -drwC -Mintel --visualize-jumps=color
...
726: e8 a5 fd ff ff call 4d0 <pthread_create@plt>
72b: 83 c4 10 add esp,0x10
72e: 85 c0 test eax,eax
730: /-------- 75 62 jne 794 <main+0xb4>
732: /--|-------> c5 f8 57 c0 vxorps xmm0,xmm0,xmm0
736: | | c5 fb 10 8e 48 e8 ff ff vmovsd xmm1,QWORD PTR [esi-0x17b8]
73e: | | 66 90 xchg ax,ax
740: | | /----> 31 c0 xor eax,eax
742: | | | 31 d2 xor edx,edx
744: | | | 31 c9 xor ecx,ecx
746: | | | 31 db xor ebx,ebx
748: | | | f0 0f c7 8e c0 00 00 00 lock cmpxchg8b QWORD PTR [esi+0xc0]
750: | | | c5 f9 6e d0 vmovd xmm2,eax
754: | | | c4 e3 69 22 d2 01 vpinsrd xmm2,xmm2,edx,0x1
75a: | | | c5 f9 2e d0 vucomisd xmm2,xmm0
75e: | | | /-- 75 02 jne 762 <main+0x82>
760: | | +--|-- 7b de jnp 740 <main+0x60>
762: | | | \-> c5 f9 2e d1 vucomisd xmm2,xmm1
766: | | | /-- 75 02 jne 76a <main+0x8a>
768: | | \--|-- 7b d6 jnp 740 <main+0x60>
76a: | | \-> 83 ec 04 sub esp,0x4
...
Run Code Online (Sandbox Code Playgroud)
Agner Fog 的objconv反汇编器生成可组合的输出,包括分支目标上的标签,从而更容易找到循环的顶部。如何在 Linux 中反汇编二进制可执行文件以获取汇编代码?中的示例输出 objdump -d -S其他答案显示了混合源和汇编的示例。
另相关:如何从 GCC/clang 程序集输出中消除“噪音”? 我通常查看gcc -O3 ... -S输出而不是组装成二进制文件。除非我已经有一个特定的二进制文件。Godbolt编译器资源管理器有很好的工具来查找与源代码行相关的 asm,比如循环体,它在大多数情况下取决于编译器生成的调试信息。