我有一个用.NET Framework 2.0编译的程序集(是的,很旧的东西),该程序集使用证书的公钥进行加密。代码非常简单:
X509Certificate2 objCert = new X509Certificate2(path);
RSACryptoServiceProvider rsa = (RSACryptoServiceProvider)objCert.PublicKey.Key;
byte [] EncrRes = rsa.Encrypt(data, false);
此功能继续适用于所有最新版本的.NET Framework,但拒绝在.NET Core下使用。我收到两个不同但相似的错误消息。
Windows 10:无法将类型为“ System.Security.Cryptography.RSACng”的对象转换为类型为“ System.Security.Cryptography.RSACryptoServiceProvider”。
Linux:无法将类型为'System.Security.Cryptography.RSAOpenSsl'的对象转换为类型为'System.Security.Cryptography.RSACryptoServiceProvider'。
是否有一种方法可以对这种简单的操作进行编码,以使其在.NET Framework 2.0+和.NET Core上均可工作?
提前感谢。
在.NET Core中,X509Certificate2.PublicKey.Key
和X509Certificate2.PrivateKey
使用特定于平台的密钥实现。在Windows上,有两种实现,传统RSACryptoServiceProvider
和现代RSACng
。
您必须更改访问这些属性的方式。并且不要访问它们。而是使用扩展方法:X509Certificate2 Extension Methods。它们返回您应使用的安全抽象类。不要尝试对任何内容使用显式强制转换。对于RSA
键,请使用RSA
类,依此类推。
X509Certificate2 objCert = new X509Certificate2(path);
// well, it is reasonable to check the algorithm of public key. If it is ECC,
// then call objCert.GetECDsaPublicKey()
RSA rsa = objCert.GetRsaPublicKey();
byte [] EncrRes = rsa.Encrypt(data, RSAEncryptionPadding.Pkcs1);
独自解决。代替
RSACryptoServiceProvider rsa = (RSACryptoServiceProvider)objCert.PublicKey.Key;
做
RSA rsa_helper = (RSA)objCert.PublicKey.Key;
RSAParameters certparams = rsa_helper.ExportParameters(false);
RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
RSAParameters paramcopy = new RSAParameters();
paramcopy.Exponent = certparams.Exponent;
paramcopy.Modulus = certparams.Modulus;
rsa.ImportParameters(paramcopy);
与.NET 2.0+和.NET Core一起使用!