利用RSACryptoServiceProvider進行RSA加密解密

前言:

本文只介紹How to use,對於加密算法的研究不予討論。

關於私鑰的存儲,微軟給的建議是使用windows自帶的祕鑰容器,相見文檔

爲了直觀看到私鑰和公鑰,本文直接將其存入XML文件中。現實狀況則要複雜的多,還牽涉到數字簽名、數字證書等。

關於公鑰、私鑰、數字簽名、數字證書的概念,相見阮一峯大神的博客,傳送門在這裏

 

正文:html

因爲RSA不適合加密大量數據,因此能夠採用DES和RSA混合加密的方法,即先用DES加密數據,再用RSA加密DES的祕鑰。git

 

RSAHelper 類算法

public class RSAHelper
    {
        /// <summary>
        /// 讀取二進制文件
        /// </summary>
        /// <param name="path"></param>
        /// <returns></returns>
        public static byte[] GetByte(string path)
        {
            FileInfo fi = new FileInfo(path);
            List<byte> buff = new List<byte>();
            using (FileStream fs = fi.Open(FileMode.OpenOrCreate, FileAccess.ReadWrite))
            {
                BinaryReader br = new BinaryReader(fs);
                try
                {
                    while (true)
                    {
                        byte i = br.ReadByte();
                        buff.Add(i);
                    }
                }
                catch (Exception)
                {
                    br.Close();
                }
            }
            return buff.ToArray();
        }

        /// <summary>
        /// 讀取文本文件
        /// </summary>
        /// <param name="path"></param>
        /// <returns></returns>
        public static string GetText(string path)
        {
            FileInfo fi = new FileInfo(path);
            string content;
            using (FileStream fs = fi.Open(FileMode.OpenOrCreate, FileAccess.ReadWrite))
            {
                StreamReader sr = new StreamReader(fs);
                content = sr.ReadToEnd();
                sr.Close();
            }
            return content;
        }

        /// <summary>
        /// 寫入二進制文件
        /// </summary>
        /// <param name="content"></param>
        /// <param name="path"></param>
        public static void WriteByte(byte[] content, string path)
        {
            FileInfo fi = new FileInfo(path);
            using (FileStream fs = fi.Open(FileMode.OpenOrCreate, FileAccess.ReadWrite))
            {
                BinaryWriter br = new BinaryWriter(fs);
                br.Write(content);
                br.Flush();
                br.Close();
            }
        }

        /// <summary>
        /// 寫入文本文件
        /// </summary>
        /// <param name="content"></param>
        /// <param name="path"></param>
        public static void WriteText(string content, string path)
        {
            FileInfo fi = new FileInfo(path);
            using (FileStream fs = fi.Open(FileMode.OpenOrCreate, FileAccess.ReadWrite))
            {
                StreamWriter sw = new StreamWriter(fs);
                sw.Write(content);
                sw.Flush();
                sw.Close();
            }
        }

        /// <summary>
        /// RSA加密/解密
        /// </summary>
        /// <param name="data">加密/解密數據</param>
        /// <param name="key">公鑰/私鑰</param>
        /// <param name="isEncrypt">ture加密,false解密</param>
        /// <returns></returns>
        public static byte[] EncryptOrDecrypt(byte[] data, string key, bool isEncrypt)
        {
            RSACryptoServiceProvider rsaP = new RSACryptoServiceProvider();
            rsaP.FromXmlString(key);
            if (isEncrypt)// 加密
            {
                byte[] buff = rsaP.Encrypt(data, true);
                return buff;
            }
            else // 解密
            {
                byte[] buff = rsaP.Decrypt(data, true);
                return buff;
            }

        } 
    }
RSAHelper類

 

DESHelper 類windows

public class DESHelper
    {
        /// <summary>
        /// DES加密/解密
        /// </summary>
        /// <param name="data">加密/解密數據</param>
        /// <param name="key">祕鑰</param>
        /// <param name="keyIV">向量</param>
        /// <param name="isEncrypt">true加密,false解密</param>
        /// <returns></returns>
        public static byte[] EncryptOrDecrypt(byte[] data, byte[] key, byte[] keyIV, bool isEncrypt)
        {
            DESCryptoServiceProvider desP = new DESCryptoServiceProvider();
            if (isEncrypt)// 加密
            {
                desP.Key = key;
                desP.IV = keyIV;
                ICryptoTransform desencrypt = desP.CreateEncryptor(key, keyIV);
                byte[] result = desencrypt.TransformFinalBlock(data, 0, data.Length);
                return result;
            }
            else // 解密
            {
                desP.Key = key;
                desP.IV = keyIV;
                ICryptoTransform desencrypt = desP.CreateDecryptor(key, keyIV);
                byte[] result = desencrypt.TransformFinalBlock(data, 0, data.Length);
                return result;
            }
        }

        /// <summary>
        /// 建立隨機祕鑰
        /// </summary>
        /// <returns></returns>
        public static byte[] CreateKey()
        {
            DESCryptoServiceProvider desP = new DESCryptoServiceProvider();
            desP.GenerateKey();
            return desP.Key;
        }

        /// <summary>
        /// 建立隨機向量
        /// </summary>
        /// <returns></returns>
        public static byte[] CreateIV()
        {
            DESCryptoServiceProvider desP = new DESCryptoServiceProvider();
            desP.GenerateIV();
            return desP.IV;
        }
    }
DESHelper類

 

主程序代碼ide

class Program
    {
        static void Main(string[] args)
        {
            string rootPath = AppDomain.CurrentDomain.BaseDirectory;
            string RSAPath = Path.Combine(rootPath, "RSA");
            string encryptFilePath = Path.Combine(RSAPath, "加密文件.dll");
            string decryptFilePath = Path.Combine(RSAPath, "解密文件.txt");
            string publicKeyPath = Path.Combine(RSAPath, "RSA公鑰.xml");
            string privateKeyPath = Path.Combine(RSAPath, "RSA私鑰.xml");
            string DESKeyPath = Path.Combine(RSAPath, "通過RSA加密的DES祕鑰.dll");
            string DESIVPath = Path.Combine(RSAPath, "通過RSA加密的DES向量.dll");
            if (Directory.Exists(RSAPath))
            {
                Directory.Delete(RSAPath, true);
            }
            Directory.CreateDirectory(RSAPath);

            Console.WriteLine("請輸入要加密的內容:");
            string data = Console.ReadLine();

            RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
            string RSAPublic = rsa.ToXmlString(false);// RSA公鑰
            string RSAPrivate = rsa.ToXmlString(true);// RSA私鑰
            byte[] DESKey = DESHelper.CreateKey(); // DES祕鑰
            byte[] DESIV = DESHelper.CreateIV(); // DES向量
            // DES加密輸入內容
            byte[] enData = DESHelper.EncryptOrDecrypt(Encoding.Unicode.GetBytes(data), DESKey, DESIV, true);
            // 寫入加密文件
            RSAHelper.WriteByte(enData, encryptFilePath);
            // 寫入RSA公鑰
            RSAHelper.WriteText(RSAPublic, publicKeyPath);
            // 寫入RSA私鑰
            RSAHelper.WriteText(RSAPrivate, privateKeyPath);
            // 寫入通過RSA加密的DES祕鑰
            RSAHelper.WriteByte(RSAHelper.EncryptOrDecrypt(DESKey, RSAPublic, true), DESKeyPath);
            // 寫入通過RSA加密的DES向量
            RSAHelper.WriteByte(RSAHelper.EncryptOrDecrypt(DESIV, RSAPublic, true), DESIVPath);

            // 讀取RSA私鑰
            string privateKey = RSAHelper.GetText(privateKeyPath);
            // 讀取DES祕鑰並解密
            byte[] realDESKey = RSAHelper.EncryptOrDecrypt(RSAHelper.GetByte(DESKeyPath), privateKey, false);
            // 讀取DES向量並解密
            byte[] realDESIV = RSAHelper.EncryptOrDecrypt(RSAHelper.GetByte(DESIVPath), privateKey, false);
            // 讀取加密文件
            byte[] enData2 = RSAHelper.GetByte(encryptFilePath);
            // 解密文件
            byte[] deData = DESHelper.EncryptOrDecrypt(enData2, realDESKey, realDESIV, false);
            // 寫入解密文件
            RSAHelper.WriteText(Encoding.Unicode.GetString(deData), decryptFilePath);

            Console.WriteLine("加密成功!");
            Console.ReadKey();
        }
    }
主程序代碼

 

運行效果:加密

(完)spa

相關文章
相關標籤/搜索