为什么 strace 报告我的 x64 FASM 程序以 32 位模式运行?
Why does strace report my x64 FASM program runs in 32-bit mode?
我的源文件顶部有 format ELF64 executable 3
。
我使用 fasm main.asm
编译了我的程序
输出:
flat assembler version 1.73.13 (16384 kilobytes memory, x64)
3 passes, 319 bytes.
然后我尝试使用 strace ./main
运行 它,因为它没有按预期工作并且在输出中有 strace: [ Process PID=3012310 runs in 32 bit mode. ]
.
file main
: main: ELF 64-bit LSB executable, x86-64, version 1 (GNU/Linux), statically linked, no section header
uname -m
: x86_64
使用syscall
代替int 0x80
strace
是错误的,您的过程实际上不是 运行 在 32 位模式下,只是使用 32- bit int 0x80
系统调用 ABI.
您可以使用 gdb ./main
检查并使用 starti
。 info regs
会显示寄存器状态为64位,包括16个64位寄存器,不包括8个32位寄存器。或者更简单地说,layout reg
.
我在使用 NASM 构建程序时看到相同的 strace 错误(?),该程序在 64 位模式下使用 32 位 int 0x80
ABI 来构建 exit
系统打电话。
我在第一次系统调用之前添加了一个延迟循环,我发现 strace
在进行系统调用之前不会打印出目标进程的位数。所以 显然 strace
从它是使用 64 位 syscall
ABI 还是 32 位 int 0x80
/ sysenter
ABI 来推断!
也许这与 strace
试图弄清楚如何解码系统调用有关: strace
使用的 Linux ptrace
API 没有'没有一个简单可靠的机制来判断进程调用了哪个系统调用 ABI。 https://superuser.com/questions/834122/how-to-distinguish-syscall-from-int-80h-when-using-ptrace
使用32位系统调用的64位进程过去只是根据64位调用号进行解码。但现在看来现代 strace
检查:
我用 eax=1
/ syscall
调用 write
,用 eax=1
/ int 0x80
调用 exit
, strace
正确解码了它们
execve("./nasm-test", ["./nasm-test"], 0x7ffdb8da5890 /* 52 vars */) = 0
write(0, NULL, 0) = 0
strace: [ Process PID=5219 runs in 32 bit mode. ]
exit(0) = ?
+++ exited with 0 +++
这是 Linux 5.3.1-arch1-1-ARCH 上的 strace 5.3
。
我的源文件顶部有 format ELF64 executable 3
。
我使用 fasm main.asm
输出:
flat assembler version 1.73.13 (16384 kilobytes memory, x64)
3 passes, 319 bytes.
然后我尝试使用 strace ./main
运行 它,因为它没有按预期工作并且在输出中有 strace: [ Process PID=3012310 runs in 32 bit mode. ]
.
file main
: main: ELF 64-bit LSB executable, x86-64, version 1 (GNU/Linux), statically linked, no section header
uname -m
: x86_64
使用syscall
代替int 0x80
strace
是错误的,您的过程实际上不是 运行 在 32 位模式下,只是使用 32- bit int 0x80
系统调用 ABI.
您可以使用 gdb ./main
检查并使用 starti
。 info regs
会显示寄存器状态为64位,包括16个64位寄存器,不包括8个32位寄存器。或者更简单地说,layout reg
.
我在使用 NASM 构建程序时看到相同的 strace 错误(?),该程序在 64 位模式下使用 32 位 int 0x80
ABI 来构建 exit
系统打电话。
我在第一次系统调用之前添加了一个延迟循环,我发现 strace
在进行系统调用之前不会打印出目标进程的位数。所以 显然 strace
从它是使用 64 位 syscall
ABI 还是 32 位 int 0x80
/ sysenter
ABI 来推断!
也许这与 strace
试图弄清楚如何解码系统调用有关: strace
使用的 Linux ptrace
API 没有'没有一个简单可靠的机制来判断进程调用了哪个系统调用 ABI。 https://superuser.com/questions/834122/how-to-distinguish-syscall-from-int-80h-when-using-ptrace
使用32位系统调用的64位进程过去只是根据64位调用号进行解码。但现在看来现代 strace
检查:
我用 eax=1
/ syscall
调用 write
,用 eax=1
/ int 0x80
调用 exit
, strace
正确解码了它们
execve("./nasm-test", ["./nasm-test"], 0x7ffdb8da5890 /* 52 vars */) = 0
write(0, NULL, 0) = 0
strace: [ Process PID=5219 runs in 32 bit mode. ]
exit(0) = ?
+++ exited with 0 +++
这是 Linux 5.3.1-arch1-1-ARCH 上的 strace 5.3
。