C# RSA加密、解密不受加密内容长度限制,自适应加、解密。
public class RSAHelper
{
private readonly static int[] KeySizes = { 512, 1024, 2048, 8192 };
/// <summary>
/// 生成密钥
/// <param name="PrivateKey">私钥</param>
/// <param name="PublicKey">公钥</param>
/// <param name="KeySize">密钥长度:512,1024,2048,4096,8192</param>
/// </summary>
public static void Generator(out string PrivateKey, out string PublicKey, int KeySize = 2048)
{
if (!KeySizes.Any(t => t == KeySize))
KeySize = 2048;
using RSACryptoServiceProvider rsa = new RSACryptoServiceProvider(KeySize);
//将RSA算法的私钥导出到字符串PrivateKey中 参数为true表示导出私钥 true 表示同时包含 RSA 公钥和私钥;false 表示仅包含公钥。
PrivateKey = rsa.ToXmlString(true);
// 将RSA算法的公钥导出到字符串PublicKey中 参数为false表示不导出私钥 true 表示同时包含 RSA 公钥和私钥;false 表示仅包含公钥。
PublicKey = rsa.ToXmlString(false);
}
/// <summary>
/// RSA加密 将公钥导入到RSA对象中,准备加密
/// 待加密的字节数不能超过密钥的长度值除以 8 再减去 11(即:RSACryptoServiceProvider.KeySize / 8 - 11),
/// 而加密后得到密文的字节数,正好是密钥的长度值除以 8(即:RSACryptoServiceProvider.KeySize / 8)。
/// </summary>
/// <param name="PublicKey">公钥</param>
/// <param name="encryptstring">待加密的字符串</param>
public static string RSAEncrypt(string PublicKey, string encryptstring)
{
using RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
byte[] data = (new UnicodeEncoding()).GetBytes(encryptstring); //要加密的数据
rsa.FromXmlString(PublicKey);
int bufferSize = (rsa.KeySize >> 3) - 11;
string result = string.Empty;
if (data.Length > bufferSize)
result = RSAEncryptLong(rsa, data, bufferSize);
else
result = RSAEncryptNormal(rsa, data);
return result;
}
private static string RSAEncryptLong(RSACryptoServiceProvider rsa, byte[] data, int bufferSize)
{
byte[] buffer = new byte[bufferSize];
using MemoryStream msInput = new MemoryStream(data);
using MemoryStream msOutput = new MemoryStream();
int readLen = msInput.Read(buffer, 0, bufferSize);
while (readLen > 0)
{
byte[] dataToEnc = new byte[readLen];
Array.Copy(buffer, 0, dataToEnc, 0, readLen);
byte[] encData = rsa.Encrypt(dataToEnc, false);
msOutput.Write(encData, 0, encData.Length);
readLen = msInput.Read(buffer, 0, bufferSize);
}
byte[] result = msOutput.ToArray(); //得到加密结果
return ByteSToBase64String(result);
}
private static string RSAEncryptNormal(RSACryptoServiceProvider rsa, byte[] data)
{
byte[] encrypt = rsa.Encrypt(data, false);
return ByteSToBase64String(encrypt);
}
private static string ByteSToBase64String(byte[] encrypt)
{
return Convert.ToBase64String(encrypt);
}
/// <summary>
/// RSA解密 将私钥导入RSA中,准备解密
/// </summary>
/// <param name="PrivateKey">私钥</param>
/// <param name="decryptstring">待解密的字符串</param>
public static string RSADecrypt(string PrivateKey, string decryptstring)
{
using RSACryptoServiceProvider rsa = new RSACryptoServiceProvider();
byte[] dataEnc = Convert.FromBase64String(decryptstring); //加载密文
rsa.FromXmlString(PrivateKey);
int keySize = rsa.KeySize >> 3;
string result = string.Empty;
if (dataEnc.Length > keySize)
result = RSADecryptLong(rsa, dataEnc, keySize);
else
result = RSADecryptNormal(rsa, dataEnc);
return result;
}
private static string RSADecryptNormal(RSACryptoServiceProvider rsa, byte[] dataEnc)
{
byte[] DypherTextBArray = rsa.Decrypt(dataEnc, false);
return (new UnicodeEncoding()).GetString(DypherTextBArray);
}
private static string RSADecryptLong(RSACryptoServiceProvider rsa, byte[] dataEnc, int keySize)
{
byte[] buffer = new byte[keySize];
using MemoryStream msInput = new MemoryStream(dataEnc);
using MemoryStream msOutput = new MemoryStream();
int readLen = msInput.Read(buffer, 0, keySize);
while (readLen > 0)
{
byte[] dataToDec = new byte[readLen];
Array.Copy(buffer, 0, dataToDec, 0, readLen);
byte[] decData = rsa.Decrypt(dataToDec, false);
msOutput.Write(decData, 0, decData.Length);
readLen = msInput.Read(buffer, 0, keySize);
}
byte[] result = msOutput.ToArray(); //得到解密结果
return (new UnicodeEncoding()).GetString(result);
}
}