带有.NET的OpenSSL S/MIME签名 [英] OpenSSL S/MIME signature with .NET

查看:109
本文介绍了带有.NET的OpenSSL S/MIME签名的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

对于我正在开发的应用程序,我需要先创建一个签名文件,然后才能上传文件.它的文档解释了如何使用openssl做到这一点:

For an application I'm developing I need to create a signature file before I can upload files. The documentation of it explains how to do this with openssl:

首先,您需要准备密钥:

First you need to prepare your key:

$ openssl pkcs12 -in certificate.pfx -passin pass:xxxxxxxxxx -out pem -clcerts -nokeys
$ openssl pkcs12 -in certificate.pfx -passin pass:xxxxxxxxxx -passout pass:xxxxxx -out key

之后,您可以使用以下语法对任何文件进行签名:

After which you can sign any file using the following syntax:

$ openssl smime -sign -in inputfile -signer pem -inkey key -passin pass:xxxxxx -outform PEM -out signaturefile

这行得通,但是我宁愿避免运行外部程序只是为了创建签名文件(如果可以使用本机.NET代码实现的话).

This works, but I'd rather avoid having to run an external program just to create signature files if it's possible to do it with native .NET code.

我尝试在vb.net中对此进行编码,并得到以下信息:

I've tried to code this in vb.net and got the following:

Public Shared Sub SignFile(ByVal theFilename As String, ByVal theCertFile As String, ByVal thePassword As String, ByVal theDestination As String)
    Dim aCertificate = New X509Certificates.X509Certificate2(theCertFile, thePassword)
    Dim aByteArray = IO.File.ReadAllBytes(theFilename)
    Dim anOid = New System.Security.Cryptography.Oid("1.2.840.113549.1.7.2")
    Dim aContentInfo = New Pkcs.ContentInfo(anOid, aByteArray)
    Dim aSignedCms = New Pkcs.SignedCms(aContentInfo, True)
    Dim aCmsSigner = New Pkcs.CmsSigner(Pkcs.SubjectIdentifierType.IssuerAndSerialNumber, aCertificate)

    aSignedCms.ComputeSignature(aCmsSigner)
    Dim aSignature = Convert.ToBase64String(aSignedCms.Encode())
    IO.File.WriteAllText(theDestination, Convert.ToBase64String(anOutput.ToArray()))
End Sub

它生成的文件与openssl所期望的不完全相同:我仍然需要插入-----BEGIN PKCS7----------END PKCS7-----并添加换行符,以使行的长度不超过65个字符. 但是,即使这样做了,我通过这种方式创建的签名仍然无效,当我使用openssl检查时,仍然收到以下错误消息:

The file it makes isn't exactly what openssl expects: I still need to insert the -----BEGIN PKCS7----- and -----END PKCS7----- and add in line breaks so that lines aren't longer than 65 characters. But, even after doing that, the signature I made this way isn't valid, when I check with openssl I get the following error:

5768:error:21071065:PKCS7 routines:PKCS7_signatureVerify:digest failure:.\crypto\pkcs7\pk7_doit.c:1051:
5768:error:21075069:PKCS7 routines:PKCS7_verify:signature failure:.\crypto\pkcs7\pk7_smime.c:410:

我想我忘记了某个地方的小细节,但我不能仅仅弄清楚是什么.

I think I'm forgetting a small detail somewhere, but I can't just figure out what.

任何人都可以帮助我使该代码正常工作吗?如果没有,请指向具有此类功能的.NET库,并可能附带一个示例方法.

Can anyone help me out make that code work? And if not, point to a .NET library that has such functionality with possibly an example of how to do it?

推荐答案

您要添加哪些确切的换行符? CRLF还是LF?

What exact line breaks do you add? CRLF or just LF?

我在验证smime消息时遇到类似的问题.我找到了原因. OpenSSL将换行符更改为CRLF(我的消息仅使用LF),因此内容与原始内容有所不同,摘要检查失败.可能也是你的情况吗? 不幸的是我找不到解决方法.

I have similar problem verifying smime message. And I find the cause. OpenSSL changes line breaks to CRLF (my message use only LF) so content become different from original and digest check fails. May be it is you case too? Unfortunately I can't find solution.

这篇关于带有.NET的OpenSSL S/MIME签名的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆