OpenSSL 3.x爆出漏洞,如何妥善应对?

10月25日,OpenSSL项目团队发布了OpenSSL 3.x版中一个关键安全漏洞的修复程序。该修复程序已于11月1日正式发布。

由于OpenSSL有着极为广泛的使用,该公告引起了很大反响。Akamai希望能通过本文帮助相关用户了解情况,介绍有关检测和缓解威胁的背景知识。本文将概括介绍OpenSSL和该漏洞的影响范围,各种应用程序对OpenSSL的使用方式,并提供可以帮助用户检测这些漏洞的工具。

需要注意的是,Akamai通过HTTP和HTTPS协议交付的内容并不受此漏洞的影响,因为我们的服务器所运行的OpenSSL版本并不受此漏洞影响。此外,Akamai也可以利用符合行业标准的保护机制缓解这一攻击向量。Akamai正在对可能受此影响的内部系统安装补丁,这些工作应该不会让使用Akamai服务的客户遭遇停机。

该漏洞的影响范围有多大?

该漏洞引起安全界广泛关注的一个原因在于:OpenSSL团队最初将该漏洞标记为“关键”,但稍后又降级为“高危”。自从在Heartbleed(一个导致内存泄漏并可能导致密钥泄漏的漏洞)出现后引入了这些分级标签后,此前只有一个漏洞(CVE-2016-6309)被分类为“关键”。

根据OpenSSL团队的要求,为了分类为“关键”,漏洞必须能影响到最常见的配置,并且很可能被利用。例如,这样的漏洞很可能会“导致服务器内存内容被大范围泄漏(从而导致用户信息外泄),很容易被远程利用进而破坏服务器私钥,或者很容易在常见情况下被用于执行远程代码”。

考虑到OpenSSL库的适用范围是如此之广,其中存在的漏洞很可能造成严重后果。然而,尽管有必要加强警惕,但目前也并不需要恐慌。OpenSSL确实很常用,但使用最广泛的版本是1.X.X,该漏洞仅影响OpenSSL 3.0.0和后续版本(2021年9月才发布)。因此该漏洞的实际影响应该并没有那么大。

我们在自己管理的网络中运行了专用检测工具,随后发现:

  • 大约50%的被监测环境中有至少一台计算机上的至少一个进程依赖了有漏洞版本的OpenSSL。
  • 在这些网络 中,依赖有漏洞版本OpenSSL的计算机占比介于0.2%到33%之间。
  • 覆盖率中位数为6.1%,平均值为11.3%,标准差为11.6%

这些统计数据并未考虑不受此漏洞影响的OpenSSL。我们选择的唯一的衡量标准是:至少有一个进程依赖受此漏洞影响版本的OpenSSL(3.0–3.6),同一台计算机上运行的其他进程并未考虑在内。

OpenSSL到底是什么?

OpenSSL是一种开源软件工具包,因此OpenSSL大部分时候发布的都是源代码。而这也意味着对检测工作来说,用户可以通过多种方式让应用程序使用或依赖OpenSSL,进而显得该漏洞非常关键。

首先,我们需要定义OpenSSL的三个组成部分:

  1. Libcrypto — 一个实现了多种加密协议(如AES、RSA、ChaCha等)的加密库。
  2. Libssl — 一个实现了所有TLS协议(最高到TLS v1.3)的库。
  3. Openssl — 一个用于执行各种操作(如生成证书)的命令行工具。

依赖OpenSSL的应用程序必须调用libcryptolibssl的某些代码逻辑(OpenSSL本身也是一个依赖这两者的应用程序)。

缓解OpenSSL漏洞

缓解OpenSSL威胁的第一步是找出存在漏洞的系统。虽然这是一个很常见的建议,但说易行难。我们提供了一个已知的受影响应用程序列表(见下文),并提供了帮助用户在自己的网络中寻找有漏洞应用程序的方法。

1.在安装补丁前后,都可采用微分段方法缓解

虽然已经有补丁程序,但大部分时候可能无法立即安装补丁,毕竟依赖OpenSSL的往往是来自不同供应商的应用程序,需要等待供应商打补丁。但我们依然可以从检测工作获得的可见性缓解风险。我们可以通过微分段和路由机制遏制攻击者利用该漏洞发起的传播和扩散。

  • 可以考虑对面向互联网的资源进一步施加限制,例如使用(更严格的)DMZ。
  • 我们可以在整个域中建立更多的微分段,这样就算有内部计算机被攻陷,也不会传播到整个内部网络。这种方式也有助于减少有漏洞计算机的攻击面,将攻击面限制在受影响计算机真正需要通信的网络范围内。

此外,我们可以录用这种可见性和检测机制来制定修补方案,确保不漏掉任何可能相关的系统。在发布并部署了补丁后,还可以再次进行检测,并对比两次检测的结果。理想情况下,这就不会漏掉任何可能受到影响的系统。

2.已知受影响的应用程序

BoringSSL(主要被Google Chrome使用)和LibreSSL这两个库均基于OpenSSL代码,但均不受此漏洞影响。

各种Linux发行版通常会包含OpenSSL库。如果使用Linux环境,那么有必要检查自己是否使用了下列任何一个版本,这些版本中包含的OpenSSL均会受此漏洞影响:

  • Red Hat Enterprise Linux 9
  • Ubuntu 22.04+
  • CentOS Stream9
  • Kali 2022.3
  • Debian 12
  • Fedora 36

但就算你使用的Linux发行版不在上述列表中,也无法确信就不受此漏洞影响。如果你平时就会积极更新各种库(例如使用软件包管理器的升级功能),那么也可能会受到该漏洞的影响。如果希望查看系统中OpenSSL库文件的版本,可以在终端窗口中运行“openssl version”命令。

Docker也针对即将发布的版本发布了公告,其中提到,在Docker官方镜像和Docker验证的发行商镜像中,估计约有1000个Docker镜像会受到此漏洞影响。这其中也包括基于上述Linux发行版衍生出的镜像。

一些框架也可能受到影响。Node.js v18.x和v19.x使用了OpenSSL 3,因此也难逃影响。他们将通过这篇博客文章持续公布相关信息。

另一个让广大开发者“心跳加速”的编程语言是Golang。Go二进制文件中的库是静态链接的,这可能需要Go的开发者重新编译自己的软件。当Golang团队在OpenSSL补丁发布的同一天宣布即将发布包含安全修复的小型版本更新时,很多人感觉这两件事之间肯定有关联。不过并非如此:一切都是虚惊一场,Golang的版本更新和OpenSSL的漏洞没什么关系。

未来一段时间内,可能还会有更多应用程序被发现会受到此漏洞影响。下文将介绍一些检测方法和工具,借此帮助大家在自己的环境中找出使用了OpenSSL 3,会受到此漏洞影响的应用程序。

检测使用OpenSSL 3应用程序的通用方法

注意:本节介绍了应用程序使用OpenSSL的技术细节。如果你只对检测本身感兴趣,可以跳转到下文阅读与YARA规则或OSQuery查询有关的内容。

OpenSSL能够以静态或动态的方式链接到应用程序。如果使用静态链接,OpenSSL的源代码将成为应用程序代码的一部分,并与应用程序的源代码一起编译为同一个二进制文件。如果使用动态链接,OpenSSL会单独编译为共享库(Windows上通常为libssl.dll和libcrypto.dll,Linux上通常为libssl.so和libcrypto.so)。随后,应用程序代码可以引用这些共享库,这个工作通常是在加载应用程序时由操作系统负责进行的。

那么如何进行检测?实际上,只检测静态编译的二进制文件就足够了。为什么?因为如果运行中的应用程序以动态方式加载了OpenSSL,或如果由动态加载的库随后动态加载了OpenSSL,最终都会导致以静态方式加载编译后的OpenSSL库。由于所有动态加载操作都发生在同一个进程的上下文中,我们只需要查看每个进程加载了哪些库,丛中找出静态编译的库即可。

因此我们首先需要弄清楚静态编译的OpenSSL到底是什么样的。好在这挺简单,所有静态编译的OpenSSL都包含一个版本字符串,看起来类似这样:OpenSSL 3.0.6 11 Oct 2022,其中3.0.6是版本号。检测这个字符串的方法很简单,只需Regex或YARA就能做到。

不过这种方法可能无法完美匹配。因为OpenSSL是开源的,用户很容易即可根据自己的需求更改版本逻辑(导致无法用上述方法检出)。我们就遇到过一次这种情况(思科使用的字符串为CiscoSSL 1.1.1k.7.2.225),其他供应商的产品也可能出现这种情况。

那么我们是怎么做的?

虽然在修复程序发布前我们了解的情况很有限,但防御者也可以预先采取一些措施为补丁程序做准备。Akamai团队开发了一些实用工具,可以帮助大家针对自己的环境获得可见性并加以缓解。Akamai Guardicore Segmentation客户在启用Insight功能后即可在自己的环境中轻松运行这些逻辑。

1.YARA

我们可以围绕上述字符串编写规则。简洁起见,我们将检测范围限制在实际受到影响的OpenSSL版本上,但这些条件都可以轻松调整。

  rule openssl_version {
strings:
$re1 = /OpenSSL\s3\.[0-6]{1}\.[0-9]{1}[a-z]{,1}/

condition:
$re1
}

如果不希望只借助字符串进行检测,也可以检查依赖OpenSSL的主应用程序,只不过需要解析可执行文件的导入结果。不过这种方法也并非就是万无一失的,因此同样需要谨慎对待。

  import "elf"
import "pe"
rule elf_import_openssl {
    condition:
        (elf.type == elf.ET_EXEC or elf.type == elf.ET_DYN) and
        (
            for any i in (0..elf.symtab_entries):
            (
                elf.symtab[i].name contains "@OPENSSL_3"
            )
        )
}
rule pe_import_openssl {
    condition:
        pe.is_pe and
        (
            for any i in (0..pe.number_of_imports):
            (
                pe.import_details[i].library_name contains "libcrypto-3" or pe.import_details[i].library_name contains "libssl-3"
            )
        )
}

2.osquery

借助上述查询,我们还可以利用osquery的YARA表,针对所有运行中的进程运行该规则。

  WITH FIRST_QUERY AS (SELECT DISTINCT
    proc.pid,
    proc.path,
    proc.cmdline,
    proc.cwd,
    mmap.path AS mmap_path
FROM process_memory_map AS mmap
LEFT JOIN processes AS proc USING(pid))
SELECT *
FROM FIRST_QUERY
JOIN yara ON yara.path = FIRST_QUERY.mmap_path
WHERE sigrule = 'rule openssl_3 {
strings:
$re1 = /OpenSSL\s3\.[0-6]{1}\.[0-9]{1}[a-z]{,1}/
condition:
$re1
}
'
AND yara.count > 0

当然,大家也可以加入我们提到的其他YARA规则,或通过增加和减少过滤器来增大或减小需要检查的文件数量。

总结

在向安全团队告知即将发布的修复程序相关信息时,OpenSSL团队用了一种有趣的方法。这则公告为防御者留出了足够的准备时间,以便找出需要打补丁的关键系统。本文介绍的方法可以帮助大家找到可能受到影响的应用程序,并第一时间安装补丁以缓解风险。

安全方面总会有层出不穷的新故事和事故,欢迎关注Akamai,第一时间了解新出现的安全威胁以及应对和缓解措施。

你可能感兴趣的:(云计算,数据库,安全,网络,云计算,Linode)