【问题标题】:ITextSharp Document Signing showing invalidITextSharp 文档签名显示无效
【发布时间】:2015-11-12 11:20:07
【问题描述】:

所以我最近一直在做 PDF 文档的签名工作,今天我遇到了一个新奇的问题。因此,当我签署文档(文档实际上是在服务器上签名)并在我的机器上打开该文档时,签名显示有效并且它启用了 LTV,因此几乎可以按预期工作。但是,当我在老板的计算机上打开同一个文档时,它显示即使在证书被信任后也无法验证签名的身份,但是如果我打开证书属性,它会说证书有效并且吊销已成功执行。这可能是什么原因?

图 1:证书本身是可信的。

图 2:中间证书是可信的。

图 3:受信任的根证书

签名文件:https://drive.google.com/file/d/0B9RyqgJoa6W8WlBLemVETXJRU0U/view?usp=sharing

另一个奇怪的事情,对于时间戳签名,当我将根证书作为受信任的根证书添加到 adobe 时,它​​说 LTV 未启用,但是如果我将 GlobalTrustFinder 证书本身添加为受信任的证书,它会说 LTV已启用。有什么理由这样做吗?

任何帮助将不胜感激

将 LTV 添加到现有签名块以及添加时间戳签名的代码:

private void SignDocumentSigningBlockAddLTVVerification(PdfStamper stamper, Certificate certificate)
    {
        LtvVerification ltvVerification = stamper.LtvVerification;
        List<string> signatureFieldNames = stamper.AcroFields.GetSignatureNames();
        ITSAClient tsaClient = new TSAClientBouncyCastle(_settingManager["DocumentSigningTimestampingServiceAddress"], String.Empty, String.Empty, Int32.Parse(_settingManager["DocumentSigningEstimatedTimestampSize"]), _settingManager["DocumentSigningEncryptionHashAlgorithm"]);
        IOcspClient ocspClient = new OcspClientBouncyCastle();
        ICrlClient crlClient = new CrlClientOnline(SignDocumentSigningBlockBuildChain(new X509Certificate2(certificate.Bytes, certificate.Password, X509KeyStorageFlags.Exportable)).ToList());

        PdfPKCS7 pkcs7 = stamper.AcroFields.VerifySignature(signatureFieldNames.Last());
        if (pkcs7.IsTsp)
        {
            ltvVerification.AddVerification(signatureFieldNames.Last(), ocspClient, crlClient, LtvVerification.CertificateOption.SIGNING_CERTIFICATE, LtvVerification.Level.OCSP_CRL, LtvVerification.CertificateInclusion.NO);
        }
        else
        {
            foreach (string name in stamper.AcroFields.GetSignatureNames())
            {
                ltvVerification.AddVerification(name, ocspClient, crlClient, LtvVerification.CertificateOption.WHOLE_CHAIN, LtvVerification.Level.OCSP_CRL, LtvVerification.CertificateInclusion.NO);
            }
        }
        ltvVerification.Merge();

        PdfSignatureAppearance appearance = stamper.SignatureAppearance;
        LtvTimestamp.Timestamp(appearance, tsaClient, null);
    }

亲切的问候

【问题讨论】:

    标签: pdf itextsharp itext signing


    【解决方案1】:

    无法检查吊销

    但是当我在老板的计算机上打开同一个文档时,它显示即使在证书被信任后也无法验证签名的身份,但是如果我打开证书属性,它会说证书是有效的并且撤销是成功执行。这可能是什么原因?

    由于我无法检查您老板的计算机,这肯定是猜测。所以...

    试一试

    您说证书是受信任的,但涉及的证书很多。那么,你信任哪一个呢?根据你的截图

    您不信任该用户证书(如果您信任该证书,则不会根据 CRL 检查该证书,而是无需进一步测试就可以信任它)。

    可能您信任了老板计算机上的根 CA 证书。 如果您信任了,则不仅要检查最终用户证书是否撤销,还要检查中间 CA 证书(SAPO 类4 CA)!可能这就是你的问题出现的地方

    因此,当您在吊销选项卡上时,请选择中间证书并查看是否可以对其执行吊销检查。如果没有,那就是你遇到的问题。

    PS:不是这样的

    OP 测试了上面提到的想法,但是

    于是我又回去检查了所有的证书,看来CRL检查是按预期进行的。

    因此,它并不像我上面想象的那么容易

    设置的不同之处在于我信任我作为根证书签名的证书,因此在我的机器上显示为成功签名,我现在设置了我的安全设置,以便我得到与上相同的结果我老板的电脑。

    好的,那么说明这两台计算机上的结果之间的差异。

    要确定问题是在确定 CA 证书的吊销状态还是您的用户证书,您能否重新配置您的设置并信任 CA 证书?

    如果在此更改后问题仍然存在,则问题很可能与您的用户证书相关联并检查其吊销状态。如果它消失了,问题很可能与检查 CA 证书的吊销状态有关。

    我现在信任 CA,它仍然有同样的问题,但如果我信任标记“将此证书用作受信任的根”和认证文档复选框的用户证书,则签名显示为有效以及 LTV启用,但前提是我将其标记为根。在所有其他情况下,签名都会发出警告,指出未执行吊销检查。

    如果您立即信任您的用户证书,签名将得到肯定验证,无需多言。毕竟,您确实信任该证书...

    除此之外,检查用户证书时已经存在问题。我会尝试调查更多。

    PPS:所以这就是为什么...

    如果所有其他方法都失败了,请开始检查签名,或者在我在证书中找不到任何真正糟糕的东西之后我想。我在 ASN.1 Dump 实用程序中打开了签名,然后...

    ...
        <30 42>
    2174   66:             SEQUENCE {
        <06 09>
    2176    9:               OBJECT IDENTIFIER '1 2 840 113583 1 1 8'
        <31 35>
    2187   53:               SET {
        <30 33>
    2189   51:                 SEQUENCE {
        <A0 31>
    2191   49:                   [0] {
        <30 2F>
    2193   47:                     SEQUENCE {
        <2D 2D>
    2195   45:                       Unknown (Reserved) {
        <2D 2D>
    2197   45:                         Unknown (Reserved) {
        <2D 42>
    2199   66:                           Unknown (Reserved) {
        <45 47>
    2201   71:                             [APPLICATION 5]
             :                   'IN X509 CRL-----.MIIfZzCCHU8CAQEwDQYJKo0...*.H..'
             :                   '............0...Ix<..N+'
             :                   Error: IA5String contains illegal character(s).
    Error: Inconsistent object length, 7 bytes difference.
             :                             }
    Error: Inconsistent object length, 30 bytes difference.
             :                           }
    Error: Inconsistent object length, 32 bytes difference.
             :                         }
    Error: Inconsistent object length, 32 bytes difference.
             :                       }
    Error: Inconsistent object length, 32 bytes difference.
             :                     }
    Error: Inconsistent object length, 32 bytes difference.
             :                   }
    Error: Inconsistent object length, 32 bytes difference.
             :                 }
    Error: Inconsistent object length, 32 bytes difference.
             :               }
    Error: Inconsistent object length, 32 bytes difference.
             :             }
    ...
    

    所以签名本身存在语法错误,更确切地说是在 PDF 签名证书吊销信息属性中 (OID 1 2 840 113583 1 1 8)。

    (用不同的查看器查看该区域,可以看到有一个文本(!)“-----BEGIN X509 CRL-----” - 似乎有一个无效的文本 CRL 表示在这里。)

    因此,当在签名验证期间尝试检查证书吊销时,Adobe Reader 会检查可用于在签名期间添加吊销信息的签名属性,发现损坏的属性值并似乎停止验证检查失败...

    用于填写证书详细信息窗口的代码似乎是单独编码的。

    为什么?

    您可能想知道文本 CRL 表示如何恰好包含在您签名的 PDF 签名证书撤销信息属性中。

    我查看了嵌入的“CRL”。它是 PEM 格式,在 47 个字节后被截断。因此,我通过证书 (https://pki.trustcentre.co.za/crl/sapo_c4ca.crl) 中给出的 URL 访问了 CRL,并且确实检索到了 PEM 格式的(完整)CRL,它是文本的。签名创建代码似乎试图按原样包含它,但它被取消了。

    PKI 以 PEM 格式而不是 DER 格式提供 CRL 是否错误?还是假设在指向的位置找到 DER 编码的 CRL 时签名创建代码是错误的?

    Internet X.509 公钥基础结构证书和证书撤销列表 (CRL) 配置文件的当前规范 (RFC 5280) 指定:

    当使用 HTTP 或 FTP URI 方案时,URI 必须指向 [RFC2585] 中指定的单个 DER 编码 CRL。

    (Section 4.2.1.13. CRL Distribution Points)

    但它没有说明 HTTPS URI 方案的任何等效内容!

    由于 PKI 采用 HTTPS 方案,因此,PKI 可能被认为符合 RFC 的规定。

    尽管 HTTPS 方案本质上只是 HTTP 方案的安全变体,因此 PKI 明确且不必要地违反了 RFC 的精神,但它似乎并没有违反它的字面意思。

    因此,CRL 检索类(如 iText 的 CrlClientOnline)最好检查检索到的 CRL 的格式,并在必要时对其进行转换。

    启用或不启用 LTV

    解释

    另一个奇怪的事情,对于时间戳签名,当我将根证书作为受信任的根证书添加到 adobe 时,它​​说 LTV 未启用,但是如果我将 GlobalTrustFinder 证书本身添加为受信任的证书,它会说 LTV已启用。有什么理由这样做吗?

    这很明显:

    如果您信任根证书,则必须检查中间 CA 和最终实体证书的吊销。由于您的文档中没有嵌入 CRL 或 OCSP 响应,因此您的时间戳未启用 LTV。

    另一方面,如果您明确信任最终实体证书,即创建时间戳的证书,Adobe 验证器会立即信任时间戳。无需检查显式信任的证书的吊销...因此,在这种情况下,时间戳启用了 LTV。

    (术语“LTV 启用”是一个 Adob​​e 术语,其值非常可变。有关该术语和其他 LTV 相关术语的背景,请参阅 this answer 中的 Background 部分和其他从那里引用的答案,)

    后续问题

    对于时间戳我有点困惑,我遵循了您推荐的帖子中的代码示例,我使用的代码是该代码的变体,但原则上是相同的,为什么 CRL 和 OCSP 会响应不嵌入?

    最大的区别是my referenced answer 中的代码不应用文档时间戳,它只是添加了与验证相关的信息(证书、CRL、OCSP 响应) .

    Adobe 的专有术语“启用 LTV” 是指文档签名或文档时间戳,其中“验证所有相关签名所需的所有信息(包括那些签名验证过程中使用的 CRL、OCSP 响应和时间戳)在验证 Adob​​e Reader 的安全设置的上下文中包含在 PDF 中”。您的代码在添加验证相关信息后会添加文档时间戳,因此验证该时间戳所需的信息通常在 PDF 中尚不可用。

    ETSI 的标准化术语“带有 LTV 的 PDF 文档”指的是带有验证相关信息的签名 PDF(例如“支持 LTV”的 PDF)加上最终文档时间戳。强>

    您使用的 iText 示例代码尝试创建 ETSI“具有 LTV 的 PDF 文档”,因此必须进行调整以尝试创建所有文档签名和时间戳都为 Adob​​e“启用 LTV”的 PDF。

    至于添加 crls 和 ocsps,据我了解,要添加 LTV,您必须将验证添加到文档中的所有签名和最终文档时间戳,就像我在提供的代码中所做的那样,是不是这样吗?

    在 LTV 的上下文中有不同的用例,根据一个人的用例,可能需要添加不同的信息。

    【讨论】:

    • 感谢您非常详细的回答。于是我又回去检查了所有的证书,看来CRL检查是按预期进行的。我确实信任链中的所有证书。我是否需要将用户证书作为根证书信任,因为这样就不会执行吊销检查?对于时间戳我有点困惑,我按照你推荐的帖子中的代码示例,我使用的代码是它的变体,但原则上是相同的,为什么不嵌入 CRL 和 OCSP 响应?亲切的问候
    • 我已使用吊销选项卡中的图像以及用于将 LTV 验证添加到签名块的代码更新了原始问题
    • 所以再次检查,在签名面板中它说无法检查吊销,但是如果我查看属性它说它是有效的......我在这里误解了什么,因为它确实似乎撤销检查在这里有问题,但我不完全明白为什么?
    • 正如我的回答中提到的,我们只能猜测。要获得更有根据的答案,了解您的计算机与老板计算机之间的实际差异(关于 Adob​​e 阅读器和操作系统的安全设置)可能会有所帮助。
    • 所以起初设置的不同之处在于我信任我作为根证书签名的证书,因此在我的机器上显示为成功签名,我现在已经设置了我的安全设置,所以我得到的结果与我老板的计算机上的结果相同。我感觉证书 CRL 可能有问题,因为即使我不使用 LTV,证书仍然出现无法验证 CRL。我对此感到有些不知所措。感谢您的输入 mkl :P
    猜你喜欢
    • 2015-07-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-01-20
    • 1970-01-01
    • 1970-01-01
    • 2016-01-21
    • 1970-01-01
    相关资源
    最近更新 更多