如何伪造X-Forwarded-For绕过IP限制?
TOPIC SOURCE
新版newbugku-web6-x-forwarded-for Writeup
在很多 Web 防护体系中,IP 白名单往往通过读取 X-Forwarded-For(XFF)头部来判断客户端来源。若后端直接信任该字段,攻击者只需在请求中注入自定义 IP,即可摆脱本地 IP 限制,拿到本应受保护的资源。
X-Forwarded-For 机制概述
代理服务器在转发请求时,会在 HTTP 首部加入 X-Forwarded-For: 客户端IP, 代理IP,按顺序记录每一次转发的地址。多数负载均衡或 CDN 直接取该字段的第一个值作为“真实 IP”。如果后端程序未做二次校验,任意外部请求均可自行写入该字段。
常见的限制实现方式
CTF 以及真实业务里常见的 “IP 禁止访问” 提示,其实背后往往是如下代码片段:
ip = request.headers.get('X-Forwarded-For') or request.remote_addr
if ip in blacklist:
abort(403, 'IP 禁止访问')
只要能让 request.headers['X-Forwarded-For'] 返回白名单 IP,黑名单检查便失效。
伪造 Header 的技术路径
- 确定目标系统信任的白名单 IP(常见为本地回环 127.0.0.1、公司内部 10.x.x.x 等)。
- 使用抓包工具(Burp、Fiddler)或浏览器插件直接在请求头中添加
X-Forwarded-For,值设为白名单 IP。 - 若服务器在多层代理后仍取第一个值,可在头部构造链式 IP,例如
1.2.3.4, 5.6.7.8,让第一个即为白名单。 - 在命令行下,
curl示例:
curl -H "X-Forwarded-For: 10.0.0.1" https://target.example.com/admin
实际测试中,若目标对 X-Forwarded-For 做了正则过滤,需要在值后加入空格或换行符来规避匹配;有的系统会把多个 IP 用逗号隔开,这时只要保证白名单出现在最左侧即可。
安全团队应当在获取客户端 IP 时,优先使用
request.remote_addr,并对X-Forwarded-For做来源可信度校验,否则很容易被“伪造 XFF”绕过。

参与讨论
暂无评论,快来发表你的观点吧!