HTTP主机头攻击
翻译
原文:https://portswigger.net/web-security/host-header
- name: 翻译
desc: 原文:https://portswigger.net/web-security/host-header
bgColor: '#F0DFB1'
textColor: 'green'
2
3
4
# 0HTTP主机头攻击
在本节中,我们将讨论错误配置和有缺陷的业务逻辑,以及如何通过 HTTP 的Host
标头使网站遭受各种攻击。我们将概述识别易受 HTTP Host
标头攻击网站的高级方法,并演示如何利用此漏洞进行以下类型的攻击:
- 密码重置投毒 (opens new window)LABS
- Web缓存投毒 (opens new window)LABS
- 利用经典的服务端漏洞 (opens new window)
- 身份验证绕过 (opens new window)LABS
- 虚拟主机暴力破解 (opens new window)
- 基于路由的 SSRF (opens new window)LABS
- 连接状态攻击 (opens new window)LABS

实验室
如果你已经熟悉 HTTP 主机头攻击背后的基本概念,并且只想在一些实际的、易受攻击的目标上练习和利用它们,那么你可以从下面的链接访问本主题中的所有实验室。
# 1HTTP Host标头是什么?
HTTP Host
标头是自 HTTP/1.1 起的强制请求标头。它指定客户端将要访问的域名。例如,当用户访问https://portswigger.net/web-security
时,他们的浏览器将编写一个包含Host
标头的请求,如下所示:
GET /web-security HTTP/1.1
Host: portswigger.net
2
在某些情况下,Host
值在到达预期的后端组件之前,可能会发生更改(例如,当请求被中间系统转发时)。我们将在下面更详细地讨论这种场景。
# 2HTTP Host标头的作用是什么?
HTTP Host
标头的用途是,帮助客户端确定 要与之通信的后端组件。如果请求不包含Host
标头,或者Host
标头的格式不正确,则在将传入请求 路由到预期应用程序时,可能会导致问题。
从历史上看,这种歧义并不存在,因为每个 IP 地址只会托管单个域的内容。如今,主要是由于 基于云的解决方案 和 外包大部分相关架构 的趋势不断增长,使用同一 IP 地址访问多个网站和应用程序是很常见的。这种方法也越来越受欢迎,部分原因是 IPv4 地址耗尽。
当可通过同一 IP 地址访问多个应用程序时,这通常是以下情况之一的结果。
# 2.1虚拟主机
一种可能的情况是,单个 Web 服务器托管多个网站或应用程序。这可能是单个所有者 具有的 多个网站,但也可能是不同的所有者 将具有的网站托管在 单个共享平台上。这种情况不像以前那么常见,但仍然发生在一些基于云的 SaaS 解决方案中。
无论哪种情况,尽管这些不同的网站 都有不同的域名,但它们都与服务器共享同一个通用的 IP 地址。以这种方式托管在单个服务器上的网站被称为 “虚拟主机”。
通常,对于访问网站的普通用户来说,虚拟主机 与 托管在自己专用服务器上的网站没有区别。
# 2.2通过中介路由流量
另一种常见的情况是,网站托管在不同的后端服务器上,但客户端和服务器之间的所有流量 都通过中间系统来路由。这可以是一个简单的负载均衡器,也可以是某种类型的反向代理服务器。在客户端通过内容分发网络(CDN)访问网站的情况下,此设置尤为普遍。
在这种情况下,即使网站托管在单独的后端服务器上,它们的所有域名都会解析为中间组件的单个 IP 地址。这带来了一些与虚拟主机相同的挑战,因为反向代理 或 负载均衡器需要知道,它应该将每个请求路由到哪一个适当的后端。
# 2.3HTTP Host标头如何解决这类问题?
在这两种情况下,都依赖于Host
标头来指定预期的收件人。一个常见的类比,给住在公寓楼里的人寄信的过程。整栋大楼都有相同的街道地址,但在这个街道地址后面 有许多不同的公寓,每个公寓都需要以某种方式 接收正确的邮件。解决这类问题的一种方法是,在地址中包含公寓号码或收件人姓名。对于 HTTP 消息,Host
标头具有类似的用途。
当浏览器发送请求时,目标 URL 将解析为特定服务器的 IP 地址。当此服务器收到请求时,它会引用Host
标头来确定预期的后端,并相应地转发请求。
# 3什么是 HTTP 主机头攻击?
HTTP 主机头攻击,易受攻击的网站以不安全的方式处理Host
标头值。如果服务器隐式信任Host
标头,并且未能正确验证或转义它,则攻击者可能使用此输入,来注入操纵服务器端行为的有害载荷。这类涉及将有效载荷直接注入Host
标头的攻击,通常被称为 “主机头注入” 攻击。
现成的 Web 应用程序通常不知道它们部署在哪个域上,除非在安装过程中,于配置文件中手动指定。当他们需要知道当前域时,例如,要在所生成的电子邮件中包含绝对 URL,这时候他们可能会从Host
标头中检索域:
<a href="https://_SERVER['HOST']/support">Contact support</a>
标头值还可以用于 网站基础设施的不同系统之间 的各种交互。
由于Host
标头实际上是用户可控的,因此这种做法可能会导致许多问题。如果输入未正确转义或验证,则Host
标头是利用一系列其他漏洞的潜在媒介,最值得注意的是:
- Web 缓存投毒
- 特定功能中的业务逻辑缺陷 (opens new window)
- 基于路由的 SSRF
- 经典的服务端漏洞,如 SQL 注入
# 4HTTP 主机头漏洞是如何产生的?
HTTP 主机头漏洞,通常是由于 标头不可由用户控制 的错误假设而产生的。这会在Host
标头中创建隐式信任,并导致验证不充分或逃逸,即使攻击者可以使用 Burp Proxy 等工具轻松修改此信任。
即使Host
标头本身的处理更安全,但根据处理传入请求的服务器配置,Host
也可能会被其他注入的标头覆盖。有时,网站所有者并不知道 默认情况下 支持这些标头,因此,它们可能不会受到相同级别的审查。
事实上,其中许多漏洞的出现,不是因为编写的代码不安全,而是因为相关基础设施中一个或多个组件的配置不安全。之所以会出现这些配置问题,是因为网站将 第三方技术 集成到其自身的体系架构中,但其不一定了解配置选项及其安全隐患。
# 5利用HTTP主机头漏洞
到目前为止,你应该已经很好地理解了 HTTP Host
标头是什么。面对渗透测试人员 和 漏洞赏金猎人,我们已经创建了一些额外的指南,指导你如何识别和利用这些类型的漏洞。我们还提供了一些故意易受攻击的LABS,以便你可以练习其中的一些技术。
# 6如何防范HTTP主机头攻击
为了防范 HTTP 主机头攻击,最简单的方法是,避免在服务端代码中完全使用Host
标头。仔细检查每个绝对 URL 是否真的被需要。你经常会发现,你可以只使用相对 URL,而非绝对 URL。这个简单的更改可以帮助你特别防止 Web 缓存投毒 (opens new window)漏洞。
防止 HTTP 主机头攻击的其他方法包括:
# 6.1保护绝对URL
当必须使用绝对 URL 时,应当要求在配置文件中手动指定当前域,并引用此静态值而不是Host
标头。例如,这种方法可以消除密码重置投毒的威胁。
# 6.2验证Host标头
如果必须使用Host
标头,请确保正确验证它。这应该包括 - 根据允许域的白名单进行检查,并对任何 无法识别主机的请求 实施拒绝或重定向。你应该查阅所使用框架的文档,以获取有关如何执行此操作的指导。例如,Django 框架在设置文件中提供了ALLOWED_HOSTS
选项。此方法可以减少你遭受 主机头注入攻击 的风险。
# 6.3不要支持Host覆盖标头
同样重要的是,一些可用于构建攻击的其他标头,要检查其是否不受支持,特别是X-Forwarded-Host
。请记住,默认情况下可能支持这些标头。
# 6.4将允许的域列入白名单
为了防止对 内部基础设施 进行基于路由的攻击,你应该配置你的负载均衡器 或 任何反向代理,仅将请求转发到允许域的白名单。
# 6.5小心使用仅限内部的虚拟主机
使用虚拟主机时,对于 “仅限内部访问的网站/应用程序” 以及 “面向公众的内容”,应避免将两者托管在同一台服务器上。否则,攻击者可能通过Host
标头操纵来访问内部域。