ROP 学习之 Shellcode
0
上一篇学习 ROP 的文章中提到原文的 Shellcode 调用失败了,这次就尝试分析下该 Shellcode 看看能不能找出原因。
1. 对 Shellcode 反汇编
拿到一段 Shellcode,第一步就是尝试反汇编,参考文章《使用 Python 将 Shellcode 转换成汇编》文章教程,基于 capstone 使用如下代码即可。
1 | #!/usr/bin/env python2 |
从这段源码可以看到,这是利用 capstone 的反汇编功能来实现的,但是需要指定对应汇编的处理器架构和字长信息。
2. 分析 Shellcode 原理
Linu 下 Shellcode 的原理参考《Linux下shellcode的编写》一文,关键是调用系统调用函数 execve。这个函数的参数如下:
- 参数 1:file 文件名
- 参数 2:NULL 即 0
- 参数 3:NULL 即 0
实现调用时,需要将系统调用号码 11 放入 eax 中,最终调用int 0x80
实现函数调用。
ROP 教程中的 Shellcode 分析
下面针对第一次调用失败的 Shellcode 反汇编得到的代码分析下:
1 | 0x0: xor ecx, ecx \x31\xc9 // 清空 ecx,即 ecx = 0 |
由此可见,从反汇编角度这段 Shellcode 应该是有问题的,参数没有正常的传入。
测试 Shellcode
同样我们可以将这段 Shellcode 拷贝到测试程序中进行测试。
1 | char shellcode[] = "\x31\xc9\xf7\xe1\x51\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\xb0\x0b\xcd\x80"; |
然后使用 gcc -fno-stack-protector -z execstack shellcode.c -o shellcode
进行编译,预期之内,直接报出 Segmentation fault
错误。说明这段 Shellcode 的确是有问题的。
更换为
1 | char shellcode[] = "\x31\xc0\x50\x68\x6e\x2f\x73\x68\x68\x2f\x2f\x62\x69\x89\xe3\x50\x89\xe2\x53\x89\xe1\xb0\x0b\xcd\x80"; |
测试正常,该段 Shellcode 可以参考文2来查看详细含义。