强制Chrome在TLS期间发送链中的所有证书

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了强制Chrome在TLS期间发送链中的所有证书相关的知识,希望对你有一定的参考价值。

我编写了一个TLS代码,它在Java上进行相互身份验证,因此客户端在服务器发送证书后发送证书。我想验证OCSP证书链中的所有证书,它来自客户端到服务器端。

我编写了我的循环逻辑,假设最后一个证书是链中的根(CA)证书,而不是为它发送任何OCSP查询;

        int certificateChainSize= x509Certificates.length;

        // Verifies certificate chain respectively (issuer certificate required).
        CertificateResult response = null;

        try {
            for (int i = 0; i < certificateChainSize-1 ; i++) {
                response = client.verify(x509Certificates[i], x509Certificates[i+1]);
            }
        } catch (OcspException e) {
            e.printStackTrace();
        }

当我测试TLS并获得Wireshark捕获时,我意识到Google Chrome作为客户端一直在发送没有root的证书链。结果是;由于循环逻辑,因此我的代码假定中间证书是root,因此不会查询中间证书。

如何强制客户端发送证书链的所有节点?

谢谢

答案

我意识到谷歌Chrome作为客户端一直在发送没有root的证书链。

这是完全正常的,也是唯一正确的行为。

根证书是信任锚,它必须是验证证书的一方的本地。即使它是发送,在验证证书时也应忽略它,即只应使用本地信任锚 - 否则中间的人可以提供他自己的证书链,包括他自己的根证书。这意味着在这种情况下,服务器必须已在本地拥有根证书,因此客户端无需发送它。

换句话说:不要试图改变Chrome的行为方式,而是根据正确的行为调整您的期望(和您的代码)。

另一答案

我同意Steffen的观点,但是为了提供更多的事实,TLS 1.3明确表示:

certificate_list:CertificateEntry结构的序列(链),每个结构包含一个证书和一组扩展。

发件人的证书必须位于列表中的第一个CertificateEntry中。以下每个证书都应该直接证明其前面的证书。由于证书验证要求独立分发信任锚,因此可以从链中省略指定信任锚的证书,前提是已知支持的对等方拥有任何省略的证书。

最后订购:

注意:在TLS 1.3之前,“certificate_list”命令要求每个证书对其前面的证书进行认证;但是,一些实现允许一些灵活性。服务器有时会为过渡目的发送当前和已弃用的中间件,而其他服务器的配置不正确,但这些情况仍然可以正确验证。为了获得最大的兼容性,所有实现都应该准备好处理来自任何TLS版本的潜在无关证书和任意排序,但必须首先是最终实体证书。

因此Chrome正确应用此规范。你需要改变你的目标来应对它。

以上是关于强制Chrome在TLS期间发送链中的所有证书的主要内容,如果未能解决你的问题,请参考以下文章

OCSP查询没有颁发者证书的中间证书

在TLS / SSL握手(证书等)中泄露了哪些信息? [关闭]

五月起谷歌Chrome强制执行SSL证书透明度政策

在握手期间检索公共服务器证书密钥

在 SSL/TLS 握手中的“server-hello”消息期间选择证书链的逻辑?

使用网络面板进行分析时强制 Chrome 关闭/重新打开所有 TCP/TLS 连接