我使用以下代码将X.509公钥转换为C#RSAParameters
,这对于1024位密钥很有效。但对于512位密钥,rsa.VerifyData(data, new SHA1CryptoServiceProvider(), sign)
返回false。
我已经验证了签名,使用Java中的公钥数据是正确的。
byte[] keyBytes = Convert.FromBase64String(publicKeyString);
byte[] modulus;
switch (keyBytes.Length)
{
case 94: // 512 bits
modulus = new byte[65];
Array.Copy(keyBytes, 24, modulus, 0, modulus.Length);
break;
case 162: // 1024 bits
modulus = new byte[128];
Array.Copy(keyBytes, 29, modulus, 0, modulus.Length);
break;
default:
throw new NotSupportedException();
}
byte[] publicExponent = new byte[3];
Array.Copy(keyBytes, keyBytes.Length - 3, publicExponent, 0, 3);
var para = new RSAParameters();
para.Modulus = modulus;
para.Exponent = publicExponent;
...
而且,这个单元测试已经过去了:
byte[] modulus = new byte[65];
Array.Copy(keyBytes, 24, modulus, 0, modulus.Length);
Array.Reverse(modulus); // big-endian
if ((modulus[modulus.Length - 1] & 0x80) > 0) // make sure positive
{
var temp = new byte[modulus.Length];
Array.Copy(modulus, temp, modulus.Length);
modulus = new byte[temp.Length + 1];
Array.Copy(temp, modulus, temp.Length);
}
var mFromByte = new BigInteger(modulus);
var mFromStr = BigInteger.Parse("10446137350258867541972982874422299386188841602828508348451210482770166585987014109048441013963536226102851240621532747362919294772011580690442657343607779"); // <- modulus output by java
Assert.AreEqual(0, mFromByte.CompareTo(mFromStr));
答案 0 :(得分:0)
谢谢@ Iridium的修正,当然512位模数应该是512位。我更改了这样的代码,verify
返回true。
case 94:
modulus = new byte[64];
Array.Copy(keyBytes, 25, modulus, 0, modulus.Length);
break;
在公钥的二进制文件中,第24行描述的模数是在65位之后,但第25行的0只是一个标志。
24 01000001 LEN(short format, 65 bits)
25 00000000