Compare commits

...

4 commits

Author SHA1 Message Date
2dust
01d35456bd Update AesUtils.cs
Some checks are pending
release / build (Release) (push) Waiting to run
2024-11-26 20:07:41 +08:00
cryptochecktool
672b8c48ac
AesUtils重新修改 (#6165)
* Create AesUtils.cs

新增AesUtils,替换掉DesUtils,提高安全性。
细节:
1.使用AES代替DES
2.正确使用IV调用方式
3.使用SHA256代替MD5进行密钥派生
4.使用PBKDF进行迭代生成密钥。

* Update AesUtils.cs

1.将默认密钥规则设置为与DES一致
2.经过本地测试
2024-11-26 19:54:46 +08:00
2dust
ac1a357740 Delete AesUtils.cs 2024-11-26 19:52:22 +08:00
2dust
504f8d09a6 Tun enable in macos when opening the app 2024-11-26 16:33:19 +08:00
2 changed files with 50 additions and 65 deletions

View file

@ -1,5 +1,3 @@
using System;
using System.IO;
using System.Security.Cryptography;
using System.Text;
@ -10,106 +8,94 @@ namespace ServiceLib.Common
private const int KeySize = 256; // AES-256
private const int IvSize = 16; // AES block size
private const int Iterations = 10000;
private static readonly byte[] Salt = Encoding.ASCII.GetBytes("saltysalt".PadRight(16, ' '));//google浏览器默认盐值
private static readonly byte[] Salt = Encoding.ASCII.GetBytes("saltysalt".PadRight(16, ' ')); // google浏览器默认盐值
private static readonly string DefaultPassword = Utils.GetMd5(Utils.GetHomePath() + "AesUtils");
/// <summary>
/// Encrypt
/// </summary>
/// <param name="text">Plain text</param>
/// <param name="password">Password for key derivation</param>
/// <param name="password">Password for key derivation or direct key in ASCII bytes</param>
/// <returns>Base64 encoded cipher text with IV</returns>
public static string Encrypt(string text, string password)
public static string Encrypt(string text, string? password = null)
{
if (string.IsNullOrEmpty(text))
return string.Empty;
if (string.IsNullOrEmpty(password))
throw new ArgumentNullException("Password cannot be null.");
var plaintext = Encoding.UTF8.GetBytes(text);
var key = GetKey(password);
var iv = GenerateIv();
byte[] plaintext = Encoding.UTF8.GetBytes(text);
byte[] key = GetDefaultKey(password);
byte[] iv = GenerateIv();
using var aes = Aes.Create();
aes.Key = key;
aes.IV = iv;
using (Aes aes = Aes.Create())
using var ms = new MemoryStream();
ms.Write(iv, 0, iv.Length);
using (var cs = new CryptoStream(ms, aes.CreateEncryptor(), CryptoStreamMode.Write))
{
aes.Key = key;
aes.IV = iv;
using (MemoryStream ms = new MemoryStream())
{
ms.Write(iv, 0, iv.Length);
using (CryptoStream cs = new CryptoStream(ms, aes.CreateEncryptor(), CryptoStreamMode.Write))
{
cs.Write(plaintext, 0, plaintext.Length);
cs.FlushFinalBlock();
}
byte[] cipherTextWithIv = ms.ToArray();
return Convert.ToBase64String(cipherTextWithIv);
}
cs.Write(plaintext, 0, plaintext.Length);
cs.FlushFinalBlock();
}
var cipherTextWithIv = ms.ToArray();
return Convert.ToBase64String(cipherTextWithIv);
}
/// <summary>
/// Decrypt
/// </summary>
/// <param name="cipherTextWithIv">Base64 encoded cipher text with IV</param>
/// <param name="password">Password for key derivation</param>
/// <param name="password">Password for key derivation or direct key in ASCII bytes</param>
/// <returns>Plain text</returns>
public static string Decrypt(string cipherTextWithIv, string password)
public static string Decrypt(string cipherTextWithIv, string? password = null)
{
if (string.IsNullOrEmpty(cipherTextWithIv))
return string.Empty;
if (string.IsNullOrEmpty(password))
throw new ArgumentNullException("Password cannot be null.");
var cipherTextWithIvBytes = Convert.FromBase64String(cipherTextWithIv);
var key = GetKey(password);
byte[] cipherTextWithIvBytes = Convert.FromBase64String(cipherTextWithIv);
byte[] key = GetDefaultKey(password);
byte[] iv = new byte[IvSize];
var iv = new byte[IvSize];
Buffer.BlockCopy(cipherTextWithIvBytes, 0, iv, 0, IvSize);
byte[] cipherText = new byte[cipherTextWithIvBytes.Length - IvSize];
Buffer.BlockCopy(cipherTextWithIvBytes, IvSize, cipherText, 0, cipherText.Length - IvSize);
var cipherText = new byte[cipherTextWithIvBytes.Length - IvSize];
Buffer.BlockCopy(cipherTextWithIvBytes, IvSize, cipherText, 0, cipherText.Length);
using (Aes aes = Aes.Create())
using var aes = Aes.Create();
aes.Key = key;
aes.IV = iv;
using var ms = new MemoryStream();
using (var cs = new CryptoStream(ms, aes.CreateDecryptor(), CryptoStreamMode.Write))
{
aes.Key = key;
aes.IV = iv;
using (MemoryStream ms = new MemoryStream())
{
using (CryptoStream cs = new CryptoStream(ms, aes.CreateDecryptor(), CryptoStreamMode.Write))
{
cs.Write(cipherText, 0, cipherText.Length);
cs.FlushFinalBlock();
}
byte[] plainText = ms.ToArray();
return Encoding.UTF8.GetString(plainText);
}
cs.Write(cipherText, 0, cipherText.Length);
cs.FlushFinalBlock();
}
var plainText = ms.ToArray();
return Encoding.UTF8.GetString(plainText);
}
private static byte[] GetDefaultKey(string password)
private static byte[] GetKey(string? password)
{
using (Rfc2898DeriveBytes pbkdf2 = new Rfc2898DeriveBytes(password, Salt, Iterations, HashAlgorithmName.SHA256))
if (password.IsNullOrEmpty())
{
return pbkdf2.GetBytes(KeySize / 8);
password = DefaultPassword;
}
using var pbkdf2 = new Rfc2898DeriveBytes(password, Salt, Iterations, HashAlgorithmName.SHA256);
return pbkdf2.GetBytes(KeySize / 8);
}
private static byte[] GenerateIv()
{
using (RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider())
{
byte[] iv = new byte[IvSize];
rng.GetBytes(iv);
return iv;
}
var randomNumber = new byte[IvSize];
using var rng = RandomNumberGenerator.Create();
rng.GetBytes(randomNumber);
return randomNumber;
}
}
}
}

View file

@ -439,8 +439,7 @@ namespace ServiceLib.ViewModels
}
else if (Utils.IsOSX())
{
//TODO
return false;
return _config.TunModeItem.LinuxSudoPwd.IsNotEmpty();
}
return false;
}