我正在基于.net的智能卡上签名一些数据并尝试在java环境中验证该签名 - 但没有成功。
智能卡(c#):
RSACryptoServiceProvider rsaProvider = new RSACryptoServiceProvider(1024);
// In a different method, rsaParams.Exponent and rsaParams.Modulus are set
rsaProvider.ImportParameters(rsaParams); // Here I'm importing the key
SHA1 sha1 = SHA1.Create();
byte[] signature = rsaProvider.SignData(data, sha1);
客户端(Java):
Signature sig = Signature.getInstance("SHA1withRSA");
sig.initVerify(rsaPublicKey); // initiate the signature with public key
sig.update(data); // update signature with the data that was signed by the card
sig.verify(signedData); // Test card signature - this always returns false
然后我尝试在Java客户端上创建签名(用于测试) - 事实证明,在Java客户端上创建的签名与在智能卡上创建的签名不同。我这样创建了它:
Signature sig = Signature.getInstance("SHA1withRSA");
sig.initSign(rsaPrivateKey);
sig.update(data);
locallySigned = sig.sign();
现在我明白签名就像(传递的数据+使用的算法)的哈希。这些实现可能在这里不兼容吗?我错过了别的什么吗?谢谢!
PS:是的,我确认输入和输出都正确地从/向卡传输,关键参数设置和输入/输出完全相同。
编辑: Java中的密钥生成:
// Create a key-pair and install the private key on the card
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
SecureRandom random = SecureRandom.getInstance("SHA1PRNG", "SUN");
keyGen.initialize(1024, random);
KeyPair keyPair = keyGen.genKeyPair();
privateKey = (RSAPrivateKey)keyPair.getPrivate();
publicKey = (RSAPublicKey)keyPair.getPublic();
然后我在卡片上设置私钥的exp和mod。
答案 0 :(得分:3)
//在另一种方法中,设置rsaParams.Exponent和rsaParams.Modulus
要在RSA密钥中设置私有指数,您应该使用RSAParameters.D
。 RSAParameters.Exponent
用于 public 指数。