2011-07-17 71 views
1

使用BouncyCastle的,并帮助从计算器问题,我得到这个(签署了RSA私钥):C#验证数据与公开密钥

 using System.Net.Sockets; 
     using System.Security.Cryptography; 
     using Org.BouncyCastle.Crypto.Parameters; 
     using Org.BouncyCastle.OpenSsl; 

...

 TcpClient client = new TcpClient("127.0.0.1", 1337); 
     NetworkStream stream = client.GetStream(); 

     StreamWriter writer= new StreamWriter(stream); 
     StreamReader reader = new StreamReader(stream); 

     writer.WriteLine("hello"); 
     writer.AutoFlush = true; 

     string response = Convert.FromBase64String(reader.ReadToEnd()).ToString(); 

     RSACryptoServiceProvider RCP; 
     var x = new PemReader(File.OpenText(pubkey)); 
     var y = (RsaKeyParameters)x.ReadObject(); 

     RCP = (RSACryptoServiceProvider)RSACryptoServiceProvider.Create(); 

     var pa = new RSAParameters(); 
     pa.Modulus = y.Modulus.ToByteArray(); 
     pa.Exponent = y.Exponent.ToByteArray(); 

     RCP.ImportParameters(pa); 
     byte[] test = RCP.Decrypt(response, true); 

现在,很明显解密将会失败,因为我试图解密已签名的东西(不是“加密”),而且肯定不是由相同的“密钥”解密。我很困惑,因为我认为我应该使用像VerifyData()这样的方法,但是这会返回一个布尔值,并且我不确定我有没有参数。

我希望完成的是C#相当于openssl rsautl -verify -inkey public.pem -pubin。也就是说,用pubkey“解密”来验证所述消息的内容。

我在正确的轨道上吗?

  • Mik的
+0

尽管为了我的目的,我可能已经进行了验证,并且不需要解密,但我确实将其用于其他目的。比起Bouncycastle更简单的解决方案(至少对我来说)是这样的:'OpenSSL.Core.BIO bin = new OpenSSL.Core.BIO(public_key_as_string); OpenSSL.Crypto.RSA rsa = OpenSSL.Crypto.RSA.FromPublicKey(bin,null,null); byte [] message = new byte [1024]; message = rsa.PublicDecrypt(base64string,OpenSSL.Crypto.RSA.Padding.PKCS1);'使用托管的[OpenSSL.NET](http://openssl-net.sourceforge.net/)包装器。 – Mik

回答

0

事实上,除非你指定了错误的编码参数的签名的解密应该永远不会失败 - 签名是简单的数据(通常是SHA1)的私有密钥加密散​​列;使用验证例程的唯一好处是它可以解密块并为你进行散列比较,如果你想成为血腥头脑的人,你可以用你的公钥进行解密操作,并自己比较散列字节。

我真的不确定response是什么在您的程序的上下文中;你应该只有被传递给它的RSA数据,如果你也给它提供的数据是第一个签名的地方你是做错了 - 同样,请检查该函数是否实际接受一个字符串,in我的经验BouncyCastle的普遍预计一byte[]

我推荐使用SignerUtilities.GetSigner() - 它需要一个字符串参数告诉它你使用什么样的签名,我会想象"SHA1WithRSA"是适合你的。