【问题标题】:Validating a leaf certificate from a third party in java 8在 java 8 中验证来自第三方的叶子证书
【发布时间】:2019-09-19 14:31:23
【问题描述】:

我正在寻找一种方法来验证从第三方发送的 java.security.cert.X509Certificate 对象。证书提供者使用 dns 或 ldap 来获取证书。我已包含一个链接,其中包含有关如何检索证书的其他信息。

http://wiki.directproject.org/w/images/2/24/Certificate_Discovery_for_Direct_Project_Implementation_Guide_v4.1.pdf

我还需要知道将在任何验证步骤中使用的协议和默认端口。证书需要满足本文档第 13 页第 4 节中的以下标准:

http://wiki.directproject.org/w/images/e/e6/Applicability_Statement_for_Secure_Health_Transport_v1.2.pdf

  1. 尚未过期。
  2. 具有有效的签名和有效的消息摘要
  3. 尚未撤销
  4. 绑定到预期的实体
  5. 具有受信任的证书路径

第 1 项直接将证书对象上的 getNotAfter 和 getNotBefore 方法中的日期与当前日期进行比较,或者使用引发检查异常的 checkValidity 方法。

对于第 2 项,我看到了一种获取签名的方法,但我不确定如何生成消息摘要并验证签名和消息摘要是否都有效。

对于第 3 项,通过在证书上调用此方法 getExtensionValue("2.5.29.31"),证书撤销列表似乎与其他一些数据混合在一起。检索证书撤销列表数据似乎可以通过 http 进行,而 ocsp 似乎基于 http。我一直无法在 java 中找到如何做到这一点。

对于第 4 项,我不确定在证书上下文中绑定意味着什么,或者验证它涉及什么。

对于第 5 项,通过在证书 getExtensionValue("1.3.6.1.5.5.7.1.1") 上调用此方法,看起来中间证书的数据与其他一些数据混合在一起。一旦通过 http 检索到证书数据,CertPathValidator 似乎可以帮助验证此信息。

【问题讨论】:

    标签: java ssl-certificate x509certificate


    【解决方案1】:

    证书验证是一项复杂的任务。您可以使用 native Java 8 support 或 Bouncycastle 手动执行您需要的所有验证(过期、撤销、证书链)。但我推荐的选项是使用已经考虑到所有可能性的特定库。

    看看DSS documentationCertificate Verification example

        // Trusted certificates sources, root and intermediates (#5 )
        CertificateSource trustedCertSource = null;
        CertificateSource adjunctCertSource = null;
    
    
        // The certificate to be validated
        CertificateToken token = DSSUtils.loadCertificate(new File("src/main/resources/keystore/ec.europa.eu.1.cer"));
    
        // Creates a CertificateVerifier using Online sources. It checks the revocation status with the CRL lists URLs or OCSP server extracted from the certificate #3
        CertificateVerifier cv = new CommonCertificateVerifier();
        cv.setAdjunctCertSource(adjunctCertSource);     
        cv.setTrustedCertSource(trustedCertSource);
    
        // Creates an instance of the CertificateValidator with the certificate
        CertificateValidator validator = CertificateValidator.fromCertificate(token);
        validator.setCertificateVerifier(cv);
    
        // We execute the validation (#1, #2, #3, #5)
        CertificateReports certificateReports = validator.validate();
    
        //The final result. You have also a detailedReport and DiagnosticData
        SimpleCertificateReport simpleReport = certificateReports.getSimpleReport();
    

    验证将执行您指定的所有步骤,包括到期、证书签名、吊销和检查信任链(包括中间证书的下载)。

    第 4 步我不明白你的意思。我想验证证书是否对应于受信任列表的证书实体之一

    要加载受信任的证书源,请参阅this

    CertificatePool certPool = new CertificatePool();
    CommonCertificateSource ccc = new CommonCertificateSource(certPool);
    CertificateToken cert = DSSUtils.loadCertificate(new File("root_ca.cer"));
    CertificateToken adddedCert = ccc.addCertificate(cert);
    

    【讨论】:

      【解决方案2】:

      我会将答案分成 3 部分。第一个是背景,第二个是库的选择,实现代码(我在实现中使用的参考资料)

      过去我实现了一个非常相似的用例。我让供应商完成了 IOT 制造,并且为了将它们加入,我已经实施了与您提到的相同的 X509 验证过程。

      实施: 对于我的实施,我参考了以下内容。您可以将 BC 作为您的 defaultProvider (Security.setProvider) 并使用以下代码。代码直接解决1,3,5。代码在这里:https://nakov.com/blog/2009/12/01/x509-certificate-validation-in-java-build-and-verify-chain-and-verify-clr-with-bouncy-castle/

      现在来到 2 ,答案取决于您将如何从客户端获取证书以及应用程序将提供哪些额外数据。 其高级流程如下 a) 客户生成证书 b) 客户使用某种可接受的算法进行摘要。 SHA256 非常流行,您可以根据需要和您拥有的计算量来增加强度。客户端创建摘要后,为了证明他是证书的所有者,您可以使用设备的私钥对摘要进行签名。然后可以将其传输到验证者应用程序 c) 一旦你有了证书和签名,你就可以使用证书和与之关联的公钥来验证签名,应用相同的摘要,然后验证签名。一个很好的参考在这里:http://www.java2s.com/Code/Java/Security/SignatureSignAndVerify.htm

      我不能 100% 确定 4 的含义。但如果它意味着身份证明(谁生成证书必然是他们是谁,签名和验证将提供相同的)

      虽然您可以使用 java 安全 API 来实现用例,但我使用 bouncycastle 核心 API 来实现用例。 Bouncycastle API 更加丰富并且经过实战考验,尤其是对于我们必须使用的奇怪 EC 曲线算法,您会发现很多人都对 BouncyCastle 发誓。

      希望这会有所帮助!

      【讨论】:

      • 对于数字 5,我需要下载中间证书来构建链,因为我没有提供这些证书。看起来我需要权限信息访问中列出的 URI。对于 2 号,我不确定第三方是否可以使用私钥。同样对于数字 3,crl 信息很有帮助,但是我还需要有关 java 中 oscp 实现的信息。
      • OCSP 应该是直截了当的。 Java 文档很棒 (docs.oracle.com/javase/8/docs/technotes/guides/security/…)。它向您展示了如何初始化 OCSP,然后查看撤销。 2 不是 100%。如果你能详细说明会很棒(签名和摘要也可能指颁发证书的 CA 用其私钥签署证书,然后应用程序可以找到谁是签署它的 CA,找到 CA 的指纹然后验证签名。)这是你想要的吗?
      • 我已经更新了问题,以获得更多与项目 #2 和项目 #4 相关的上下文和参考。对于第 5 项,我正在寻找一种方法来提取权限信息访问权限,然后从中获取中间证书。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-16
      • 2012-04-16
      • 1970-01-01
      相关资源
      最近更新 更多