一、基础知识
1. 什么是HOST头
从HTTP/1.1开始,Host标头是必需的请求标头。它指定客户端想要访问的域名。例如,当用户访问https://www.baidu.com,,他们的浏览器将组成一个包含主机标头的请求。
- GET / HTTP/1.1
- Host: www.baidu.com
复制代码 2. HOST头作用
是确定客户端要与哪个后端组件通信。如果请求不包含主机头,或者如果主机头在某种程度上格式错误,则在请求路由到目标应用程序时会导致问题。
**虚拟主机:**单个Web服务器托管多个网站或应用程序。尽管这些不同的网站都有不同的域名,但它们都与服务器共享一个共同的IP地址。以这种方式托管在一台服务器上的网站被称为“虚拟主机”。
**路由中介(负载均衡、反向代理):**网站托管在不同的后端服务器上,但客户端和服务器之间的所有流量都通过中间系统进行路由。它们的所有域名也会解析为中间组件的单个IP地址。
以上两种方式,均有一个共同问题需要解决:需要知道应该将每个请求路由到哪个适当的后端或应用上。
依赖Host头来指定预期的收件人。当浏览器发送请求时,目标URL将解析为特定服务器的IP地址。当此服务器接收到请求时,它会参考主机标头来确定预期的后端,并相应地转发请求。
3. HOST头攻击
网站以不安全的方式处理Host的值,并且用于网站不同系统之间的各种交互。如果服务器没有合理验证或过滤该值,则会让攻击荷载成功进入到系统内部。尤其实际上Host的值是用户可控的,因此会导致许多安全问题:如
- 缓存中毒攻击
- 业务逻辑漏洞攻击
- 服务器端访问请求伪造(SSRF)
- 传统的服务器端攻击,如SQL注入
以上安全专题均会在我的系列文章中讲解。
二、漏洞利用
1. 如何识别发现Host漏洞
一些拦截代理直接从主机标头派生目标IP地址,这使得这种测试几乎是不可能的;您对标头所做的任何更改都只会导致将请求发送到完全不同的IP地址。但是,Burp软件准确地保持了主机报头和目标IP地址之间的分隔。准确的说Burp软件在安全行业人人都要会用,就像微信、QQ在社交领域,CAD在工程制图领域,PS在美图领域的地位一样。
测试时会遇到两大类反映
服务器有时被配置为默认或备用选项,以防它们接收到对它们不识别的域名的请求。恭喜你,你可以开始研究应用程序到底对host头做了哪些处理,是否有利用的可能了。
这是正常的,我们就要使用后面介绍的其他方式进行测试识别了。
有时由于某种安全措施,请求被阻止了,而不是收到“无效主机标头”响应。
应了解网站如何解析Host标头,找到可用于绕过验证的漏洞。
例如,某些解析算法将省略Host报头中的端口,这意味着只对域名进行验证。如果您还可以提供非数字端口,则可以保持域名不变,以确保您到达目标应用程序,同时可能会通过该端口注入有效负载。
- GET /example HTTP/1.1
- Host: vulnerable-website.com:bad-stuff-here
复制代码 例如,站点可能匹配白名单来验证Host值。在这种情况下,您可以通过注册一个以白名单中的域名相同的字符串结尾的任意域名来完全绕过验证:
- GET /example HTTP/1.1
- Host: notvulnerable-website.com
复制代码- GET /example HTTP/1.1
- Host: hacked-subdomain.vulnerable-website.com (有可能在前通过,有可能在后通过,需要不断测试)
复制代码
验证Host的代码和对主机执行易受攻击操作的代码,通常在不同的应用组件中,甚至位于不同的服务器上。通过识别和利用它们如何检索主机host的差异,可能够发出一个模棱两可的请求。
- GET /example HTTP/1.1
- Host: vulnerable-website.com
- Host: bad-stuff-here
复制代码 前端优先host的第一个实例,但后端更喜欢最后一个host实例。在这种情况下,可以使用第一个头来确保请求被路由到预期的目标,并使用第二个头将有效负载传递到服务器端代码。
- GET https://vulnerable-website.com/ HTTP/1.1
- Host: bad-stuff-here
复制代码 尽管请求行通常为相对路径,但许多服务器也能解析绝对URL的请求。
同时提供绝对URL和主机头所造成的歧义也可能导致不同系统之间的差异。在实践中,与重复Host头大致相同的方式利用这些差异。
- 尝试不同的协议(http\https),查看响应是否不同
- 添加换行符(表头缩进)
可以通过在HTTP头上缩进一个空格字符来发现奇怪的行为。一些服务器会将缩进标头解释为换行,因此将其视为前面标头的值的一部分。其他服务器将完全忽略缩进标头。
由于对此处理的不一致,经常会有差异。
- GET /example HTTP/1.1
- Host: bad-stuff-here
- Host: vulnerable-website.com
复制代码 如果前端忽略了缩进头部,则该请求将作为VULNERABLE-Website.com的普通请求处理。现在假设后端忽略前导空格(未忽略缩进头部),并且在出现重复项的情况下优先使用第一个标头。我们就可以利用host传递任意值。
后续会有专题文章介绍
网站通常是通过某种中间系统访问的,例如负载均衡器或反向代理。在这种体系结构中,后端服务器接收的Host标头可能包含这些中间系统的域名。(Host可能在不断变化,无法保持与浏览器最初请求的Host一致)
要解决此问题,前端可能会注入X-Forwarded-Host头,其中包含来自客户端初始请求的Host头的原始值。当X-Forwarded-Host头出现时,许多框架会转而引用它。
可以使用X-Forwarded-Host注入您的恶意输入,同时绕过对主机标头本身的任何验证。
- GET /example HTTP/1.1
- Host: vulnerable-website.com
- X-Forwarded-Host: bad-stuff-here
复制代码 其他类似功能的标头还有
X-Host
X-Forwarded-Server
X-HTTP-Host-Override
Forwarded
这通常是因为这些标头中的一个或多个在网站使用的某些第三方技术中默认启用,这几乎无法避免。
其实这也说明了为什么不管开发水平多高,安全漏洞总是存在的问题。没有一个人或一个团队能100%掌控一切,尤其在这个开源和快速迭代的时代。
(小彩蛋:本文留言写这句,我将关注你并奉上我的留言感谢!)
可以使用工具Param Miner中的"Guess headers" 功能,探测网站支持的头。
2. 漏洞利用
(1) 密码重置中毒
攻击者利用该技术操纵易受攻击的网站生成指向其控制的域的密码重置链接。此行为可被利用来窃取重置任意用户密码所需的秘密令牌,并最终危害其帐户。
主流密码重置流程如下:
- 用户点击发起重置请求
- 应用查看用户是否存在,之后生成一个临时、唯一、高度加密的口令。该口令与后端数据库该用户信息关联。
- 应用向申请用户发送邮件,邮件包括重置的链接,口令往往以URL参数形式附上。https://normal-website.com/reset?token=0a1b2c3d4e5f6g7h8i9j
- 用户点击该链接,网站验证token,并确认是哪一个账户重置。如果通过,应用提供重置页面。token随即销毁。
这个过程足够简单和相对安全。然而,它的安全性依赖于:只有目标用户才有权访问他们的电子邮件收件箱,从而访问他们的唯一令牌。
密码重置中毒可窃取此令牌以更改其他用户密码的方法。关键点于:
- 攻击者在事先获取目标用户邮箱或用户名(根据应用逻辑要求)。
- token被用作唯一的验证机制。
构造攻击:
如果发送给用户的URL是基于可控输入(如Host标头)动态生成的,则可能会构建密码重置中毒攻击,流程如下所示:
- 攻击者根据需要获取受害者的电子邮件地址或用户名,并伪装受害者发起密码重置请求。在提交表单时,拦截产生的HTTP请求并修改主机标头,使其指向攻击者控制的域。
- 受害者直接从网站收到真正的密码重置电子邮件。它包含与其帐户相关联的有效密码重置令牌。但是由于之前拦截修改了Host,导致URL中的域名指向攻击者的服务器:https://evil-user.net/reset?token=0a1b2c3d4e5f6g7h8i9j
- 如果受害者单击此链接(或通过某种其他方式获取该链接,例如,通过防病毒扫描程序),密码重置令牌将被发送到攻击者的服务器。
- 攻击者现在可以访问易受攻击网站的真实URL,并通过相应的参数提供受害者被盗的令牌。重置任意密码,然后登录受害者的帐户。
例题 1、2、3
(2) 通过Host标头Web缓存中毒
此处不再赘述可以参考我的另外一篇博文《WEB缓存中毒》
例题4
(3)绕过访问限制
网站将某些功能的访问权限限制为仅限内部用户使用是很常见的。然而,一些网站的访问控制功能有缺陷,允许通过对Host进行简单修改来绕过这些限制。
例题5
(4)使用虚拟主机暴力访问内部网站
www.example.com: 12.34.56.78
intranet.example.com: 10.0.0.132
详见后续文章《信息泄露》
(5)基于路由的SSRF
典型的SSRF漏洞通常基于XXE或可利用的业务逻辑,该业务逻辑将HTTP请求发送到用户可控制的输入产生的URL。另一方面,基于路由的SSRF依赖于许多基于云的体系结构中普遍存在的中间组件。这包括内部负载平衡器和反向代理。
尽管这些组件用于不同的目的,但从根本上说,它们接收请求并将它们转发到适当的后端。如果它们配置不安全,让未经验证的Host标头请求转发,则可以尝试操纵将请求错误地路由到攻击者选择的任意系统。
这些系统是极好的靶子。他们处于网络特权位置,允许他们直接从公共网络接收请求,同时还可以访问内部网络的大部分地方。这使得Host标头成为SSRF攻击的强大载体,可能会将简单的负载均衡器转换为整个内部网络的网关。
使用Burp Collaborator来帮助识别上述漏洞。如果在Host标头中提供了Collaborator服务器的域,并且随后从目标服务器或另一个In-Path系统收到了DNS查找,这表示可能能够将请求路由到任意域。
在确认可以成功将中间系统请求路由到任意公共服务器之后,下一步是查是否可以利用此行为访问仅限内部的系统。为此,需要识别目标的内部网络IP,方法如下:
- 应用程序泄露的任何IP地址
- 扫描属于该公司的主机名,以查看是否有任何解析为专用IP地址。
- 如果所有其他方法都失败了,可以通过暴力破解标准私有IP范围(如192.168.0.0/16)来识别有效的IP地址。
例题6、7
(6) 通过请求错误的请求行实现SSRF
自定义代理有时无法正确验证请求行,在这种情况下反而允许提供异常的、格式错误的输入,从而导致错误的结果。
正常访问 http://backend-server/example
但构造数据包为:
- GET @private-intranet/example HTTP/1.1
- Host: //backend-server
复制代码 实际请求变为:http://backend-server@private-intranet/example
大多数HTTP库将其解释为使用用户名Backend-Sever访问私有内部网的请求。
三、漏洞实例
1. 基本密码重置中毒(Basic password reset poisoning)
登陆carlos的账户
- GET /forgot-password HTTP/1.1
- Host: ace91ff21e5626fdc0aa2d7c004700d6.web-security-academy.net
- Cookie: _lab=46%7cMCwCFEcIOnfV6IvWnIia8prSWMi8FwJGAhRNQAon6%2b4BuE3C%2b1RhJfJNnjDLkcJROD6XfAHLtKor2EFFpCsl2mkfoQNbrBEfskkDE36pkQXfZ84PNQ4IF5IIFnpcfq%2fAVy2jZTk2sb0ADIY0dlYuMu8aJ6k1qVkX%2fjfUSx%2fffZ1fsCQ%3d; session=oEXahzmqBvEf82f7vmU45ELqQVhbmL4x
复制代码
- 下一步发现只需提供用户名或邮箱,本题已知目标用户名。故两个条件均满足。可尝试密码重置攻击
- 截取数据包,更换Host值为攻击机域名,使产生的连接实为攻击机的域名+token
- GET /forgot-password HTTP/1.1
- Host: exploit-ace51f971e9c26a1c0852dda01e300ee.web-security-academy.net
- Cookie: _lab=46%7cMCwCFEcIOnfV6IvWnIia8prSWMi8FwJGAhRNQAon6%2b4BuE3C%2b1RhJfJNnjDLkcJROD6XfAHLtKor2EFFpCsl2mkfoQNbrBEfskkDE36pkQXfZ84PNQ4IF5IIFnpcfq%2fAVy2jZTk2sb0ADIY0dlYuMu8aJ6k1qVkX%2fjfUSx%2fffZ1fsCQ%3d; session=oEXahzmqBvEf82f7vmU45ELqQVhbmL4x
复制代码
- 再输入目标名carlos,查看攻击机日志获取token
"GET /forgot-password?temp-forgot-password-token=YiVBMo5GwYDaB9flrRVmxf2ADHYEgTXU HTTP/1.1"
https://ace91ff21e5626fdc0aa2d7c004700d6.web-security-academy.net/forgot-password?temp-forgot-password-token=YiVBMo5GwYDaB9flrRVmxf2ADHYEgTXU
2. 通过中间件进行密码重置中毒(Password reset poisoning via middleware)
登陆carlos的账户
此题抓包分析后,与上题一样,只是在更换Host值后发现验证不过。系统对host有验证。
根据本文上面给出的多个方式,一个个试过来,最终发现X-Forwarded-Host可以传入攻击机域名。
我的文章不仅仅是一篇技术文档,更是一个安全渗透测试的技术参照手册,娓娓道来,尽可能的写出所有方式。如果您有幸能看到这段文字,希望你能发现这篇文章的真正含金量。
- GET /forgot-password?temp-forgot-password-token=YQvW4Q2DP1iK8GlAoBOBl3xvDoNYsBNk HTTP/1.1
- Host: ac4a1f7f1eb95572c05c2e0f00330076.web-security-academy.net
- X-Forwarded-Host: exploit-ac701f0b1e1255f2c0af2e4501d70019.web-security-academy.net
复制代码 3. 通过悬挂式标记进行密码重置中毒(Password reset poisoning via dangling markup)
登陆carlos的账户
这道题很疯狂,是的,疯狂。要做明白这道题需要学会我的另一篇文章XSS(Cross Site Scripting)跨站脚本攻击,再把现在这个文章看懂。这道题才能明白原理。同时有大量动手练习靶场的经验支持下,这道题才能攻破。
- 按上述题目等流程了解这个网站的整体流程和验证方式。注入点经过耐心的反复测试能找到,,就在Host值的port位置。Host: your-lab-id.web-security-academy.net:arbitraryport
- 但能发现一点不同。此题邮件没有token,会直接将密码发你,链接也仅是登陆页面的链接,怎么办呢?
- 这真的很考验一个黑客的意识了,其实说出来很简单很直接。但是没有长久训练是很难想到的。就是要让这封邮件的密码传到我攻击机的log上,仅此而已。
- 怎么做做到呢?邮件中有显示源码功能,能看到如下信息:看到ckick here的href连接,怎么做呢?
- Sent: 2022-05-17 11:02:29 +0000
- From: no-reply@ace11f121fea5e94c0b7148700fc007c.web-security-academy.net
- To: wiener@exploit-acdb1f781fc05e06c07214cb01540042.web-security-academy.net
- Subject: Account recovery
- <p>Hello!</p>
- <p>Please <a target="_blank" href='https://ace11f121fea5e94c0b7148700fc007c.web-security-academy.net/login'>click here</a> to login with your new password: EqTvdZeckf</p>
- <p>Thanks,<br/>Support team</p><i>This email has been scanned by the MacCarthy Email Security service</i>
复制代码
- 一个熟练的渗透测试人员应该能第一时间想到,是的XSS在属性中闭合的xss。 但要怎么闭合呢。我先给出答案,再来分析给出tips,**根据实际代码要设计的很有技巧。**其实大家要向弄明白还是要看那个之前的文章。
:' |