证书固定和公钥固定之间的区别

信息安全 tls 证书颁发机构 证书固定
2021-08-18 16:52:25

我明白什么是固定。我已经阅读了有关证书固定的内容,我很欣赏它的用例。但今天我了解到固定可以有两种类型 -

  1. 固定证书或
  2. 固定公钥

证书和公钥固定

我想了解每个用例。任何我们更喜欢其中一个的典型场景?

我的一个疑问是:假设我们固定了一个公钥。我们的连接是否容易受到中间人攻击。是否有 CA 认证的根证书与客户端中使用的证书具有相同的公钥?

两者之间可以帮助我更好地理解它们的任何差异都值得赞赏。

3个回答

这实际上取决于您的应用程序/站点如何管理证书和公钥,即密钥和证书的轮换频率。例如,如果您的站点经常轮换证书,那么如果您要固定证书,您还需要经常更新您的应用程序。然而,在这个用例中,固定公钥将是一个更好的主意,因为与证书关联的公钥将保持静态。

从您在问题中提到的 OWASP 链接:

证书

证书最容易固定。您可以为网站带外获取证书,让 IT 人员通过电子邮件将您的公司证书发送给您,使用 openssl s_client 检索证书等。当证书到期时,您将更新您的应用程序。假设您的应用程序没有错误或安全缺陷,该应用程序将每两年更新一次。在运行时,您在回调中检索网站或服务器的证书。在回调中,您将检索到的证书与嵌入在程序中的证书进行比较。如果比较失败,则使方法或函数失败。

固定证书有一个缺点。如果该站点定期轮换其证书,那么您的应用程序将需要定期更新。例如,Google 会轮换其证书,因此您需要大约每月更新一次您的应用程序(如果它依赖于 Google 服务)。即使 Google 轮换其证书,底层公钥(在证书内)仍然是静态的。

公钥

由于从证书中提取公钥所需的额外步骤,公钥固定更灵活但有点棘手。与证书一样,该程序使用其嵌入的公钥副本检查提取的公钥。两个公钥固定有两个缺点。首先,使用密钥(相对于证书)更难,因为您通常必须从证书中提取密钥。提取在 Java 和 .Net 中是一个小不便,但在 Cocoa/CocoaTouch 和 OpenSSL 中却不舒服。其次,密钥是静态的,可能违反密钥轮换策略。

关于 MitM,不,只要您正确实施了证书固定,您的 TLS 连接就不会受到任何 MitM 攻击。即使攻击者能够使用与您的应用程序固定的相同公钥(假设通过 rouge CA)获得他们自己域的有效证书,他们仍然不会拥有相应的私钥因此将无法与您的应用程序创建有效的 TLS 连接(因为它们本身将无法执行 TLS 握手)。

证书固定的最大问题是证书的保质期有限,而且通常要花钱。让我们加密的免费证书仅持续 90 天。如果你付钱,你可以得到两年多一点,这是 CA/Browser 论坛现在设定的限制。没有保证,未来不会进一步减少。

在您购买证书之前,您无法固定证书,一旦您购买了它,无论您是否使用它,它的生命周期都会减少。因此,如果您固定证书,您最终可能会购买许多额外的证书,并且您可能会遇到尝试使用旧版本代码进行连接的人的问题。

另一方面,公钥没有任何寿命限制。因此,如果您使用密钥固定,您可以生成一个密钥对,将私钥放在您的保险库中,将公钥放在您的应用程序中。然后几年后,您可以将私钥从您的保险库中取出,获得证书并将其投入使用。

密钥固定的潜在缺点是密钥无法撤销。如果您的密钥被泄露,您可以撤销证书,但拥有友好 CA 的攻击者可能会使用被盗密钥获得新证书。OTOH 证书吊销通常非常脆弱。

只是我的两分钱中的一部分:

我可以想象,在更新证书时(例如在嵌入式系统或物联网应用程序中)可能难以更新应用程序的场景中使用公钥固定。否则,证书固定会更方便。

如果生成的公钥具有足够的熵,则不可能有两个相同的密钥。