【发布时间】:2015-01-05 13:39:26
【问题描述】:
我正在尝试在我的 64 位 Ubuntu 上编写我的第一个“Hello world”shellcode,但它不起作用。
我有文件 hello.asm:
; 64-bit "Hello World!" in Linux NASM
global _start ; global entry point export for ld
section .text
_start:
; sys_write(stdout, message, length)
mov rax, 1 ; sys_write
mov rdi, 1 ; stdout
mov rsi, message ; message address
mov rdx, length ; message string length
syscall
; sys_exit(return_code)
mov rax, 60 ; sys_exit
mov rdi, 0 ; return 0 (success)
syscall
section .data
message: db 'Hello, world!',0x0A ; message and newline
length: equ $-message ; NASM definition pseudo-instruction
我使用了这个命令:
nasm -felf64 hello.asm -o hello.o
ld -o hello hello.o
objdump -d hello
我将来自 objdump 的 shellcode 放入我的 C 程序中:
char code[] = "\xb8\x01\x00\x00\x00\xbf\x01\x00\x00\x00\x48\xbe\xd8\x00\x60\x00\x00\x00\x00\x00\xba\x0e\x00\x00\x00\x0f\x05\xb8\x3c\x00\x00\x00\xbf\x00\x00\x00\x00\x0f\x05";
int main(int argc, char **argv)
{
int (*func)();
func = (int (*)()) code;
(int)(*func)();
return 0;
}
并在 gcc 中编译它,但运行后出现“分段错误(核心转储)”。
我不知道我做错了什么。汇编代码似乎可以工作,因为当我运行 ./hello 时,它会打印“Hello world”。
【问题讨论】:
-
.data部分(您的代码结束的地方)默认情况下不可执行。此外,您应该确保您的代码与位置无关。 -
在 x86_64 上,您确定这是有效的:
length: equ $-message