|
客户端的工作流程是:
建立和发送公共密钥给服务器。
从服务器接收被加密的对称密钥。
解密该对称密钥并将它作为私有的不对称密钥。
接收并使用不对称密钥解密信息。
代码如下:
namespace com.billdawson.crypto { public class CryptoClient { private const int RSA_KEY_SIZE_BITS = 1024; private const int RSA_KEY_SIZE_BYTES = 252; private const int TDES_KEY_SIZE_BITS = 192; private const int TDES_KEY_SIZE_BYTES = 128; private const int TDES_IV_SIZE_BYTES = 128; public static void Main(string[] args) { int port; string host; TcpClient client; SymmetricAlgorithm symm; RSACryptoServiceProvider rsa; if (args.Length!=2) { Console.WriteLine(USAGE); return; } try { host = args[0]; port = Int32.Parse(args[1]); } catch { Console.WriteLine(USAGE); return; } try //连接 { client = new TcpClient(); client.Connect(host,port); } catch(Exception e) { Console.WriteLine(e.Message); Console.Write(e.StackTrace); return; } try { Console.WriteLine("Connected. Sending public key."); rsa = new RSACryptoServiceProvider(); rsa.KeySize = RSA_KEY_SIZE_BITS; sendPublicKey(rsa.ExportParameters(false),client); symm = new TripleDESCryptoServiceProvider(); symm.KeySize = TDES_KEY_SIZE_BITS; MemoryStream ms = getRestOfMessage(client); extractSymmetricKeyInfo(rsa, symm, ms); showSecretMessage(symm, ms); } catch(Exception e) { Console.WriteLine(e.Message); Console.Write(e.StackTrace); } finally { try { client.Close(); } catch { //错误 } } } private static void sendPublicKey( RSAParameters key, TcpClient client) { NetworkStream ns = client.GetStream(); BinaryFormatter bf = new BinaryFormatter(); bf.Serialize(ns,key); } private static MemoryStream getRestOfMessage(TcpClient client) { //获取加密的对称密钥、初始化矢量、秘密信息。对称密钥用公共RSA密钥 //加密,秘密信息用对称密钥加密 MemoryStream ms = new MemoryStream(); NetworkStream ns = client.GetStream(); byte[] buffer = new byte[1024]; int len=0; // 将NetStream 的数据写入内存流 while((len = ns.Read(buffer, 0, buffer.Length))>0) { ms.Write(buffer, 0, len); } ms.Position = 0; return ms; } private static void extractSymmetricKeyInfo( RSACryptoServiceProvider rsa, SymmetricAlgorithm symm, MemoryStream msOrig) { MemoryStream ms = new MemoryStream(); // 获取TDES密钥--它被公共RSA密钥加密,使用私有密钥解密 byte[] buffer = new byte[TDES_KEY_SIZE_BYTES]; msOrig.Read(buffer,0,buffer.Length); symm.Key = rsa.Decrypt(buffer,false); // 获取TDES初始化矢量 buffer = new byte[TDES_IV_SIZE_BYTES]; msOrig.Read(buffer, 0, buffer.Length); symm.IV = rsa.Decrypt(buffer,false); } private static void showSecretMessage( SymmetricAlgorithm symm, MemoryStream msOrig) { //内存流中的所有数据都被加密了 byte[] buffer = new byte[1024]; int len = msOrig.Read(buffer,0,buffer.Length); MemoryStream ms = new MemoryStream(); ICryptoTransform transform = symm.CreateDecryptor(symm.Key,symm.IV); CryptoStream cstream =new CryptoStream(ms, transform, CryptoStreamMode.Write); cstream.Write(buffer, 0, len); cstream.FlushFinalBlock(); // 内存流现在是解密信息,是字节的形式,将它转换为字符串 ms.Position = 0; len = ms.Read(buffer,0,(int) ms.Length); ms.Close(); string msg = Encoding.ASCII.GetString(buffer,0,len); Console.WriteLine("The host sent me this secret message:"); Console.WriteLine(msg); } } }
|