【发布时间】:2014-05-21 10:30:46
【问题描述】:
我在共享库中有一个 sigfault。有一个堆栈跟踪。
(_bad_func+0x3dd)
函数定义为:
000000000008b030 <_bad_func>:
我找到了问题所在(0x08b950 + 0x3dd => 0x8bd2d)并感到困惑。
8bd23: bf 03 00 00 00 mov $0x3,%edi
8bd28: e8 03 ca fe ff callq 78730 <sleep@plt>
8bd2d: c6 04 25 00 00 00 00 movb $0x0,0x0
8bd34: 00
8bd35: e9 3a ff ff ff jmpq 8bc74 <xxx+0x324>
我认为“movb $0x0,0x0”总是失败。它将 0 文字写入 nullptr。 为什么编译器把它放在这里?睡眠功能是非常常见的系统之一。 我猜它不会触及它的返回地址。所以 100% 在它休眠 3 秒后 进程收到段错误。
如果存在用于对齐下一条指令的存根字节,为什么它们不只是零(或 1 字节指令 NOP = 90)。
这是英特尔 elf64 代码。
_bad_func 在 gdb 中看起来是一样的。
gdb proc
br xxx # stop and at the func after library initialized
start
disas _bad_func
0x00002aaaaaf5dd23 <+979>: mov $0x3,%edi
0x00002aaaaaf5dd28 <+984>: callq 0x2aaaaaf4a730 <sleep@plt>
0x00002aaaaaf5dd2d <+989>: movb $0x0,0x0
0x00002aaaaaf5dd35 <+997>: jmpq 0x2aaaaaf5dc74 <xxx+804>
【问题讨论】:
-
为什么编译器把它放在这里? - 也许共享库有一个错误的语句/语句序列可以转换成这个?
-
这是一个未解析的外部变量。是来自
objdump -d吗?试试objdump -r -R -d
标签: gcc assembly intel disassembly