254 lines
6.7 KiB
C#
254 lines
6.7 KiB
C#
|
using ICSharpCode.SharpZipLib.GZip;
|
|||
|
using System.IO.Compression;
|
|||
|
using System.Security.Cryptography;
|
|||
|
using System.Text;
|
|||
|
|
|||
|
namespace Elisa.WebAPI.Utils;
|
|||
|
|
|||
|
public static class Crypto
|
|||
|
{
|
|||
|
static DateTime epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
|
|||
|
static MD5 md5 = System.Security.Cryptography.MD5.Create();
|
|||
|
|
|||
|
public static string Decrypt(string body, string key)
|
|||
|
{
|
|||
|
if (string.IsNullOrEmpty(body) || string.IsNullOrEmpty(key))
|
|||
|
return string.Empty;
|
|||
|
|
|||
|
if (body.Length == 1 || body.StartsWith("error:") || (body.StartsWith("{") && body.EndsWith("}")))
|
|||
|
return body;
|
|||
|
|
|||
|
try
|
|||
|
{
|
|||
|
string text = MD5(MD5(key).Substring(16));
|
|||
|
string pwd = text + MD5(text);
|
|||
|
|
|||
|
if (body.StartsWith("#"))
|
|||
|
{
|
|||
|
body = body.Substring(1);
|
|||
|
|
|||
|
return GZipDecompress(RC4(ConvertFromBase64String(body), pwd).Skip(26).ToArray<byte>());
|
|||
|
}
|
|||
|
|
|||
|
byte[] bytes = RC4(ConvertFromBase64String(body), pwd);
|
|||
|
string @string = Encoding.UTF8.GetString(bytes);
|
|||
|
|
|||
|
return (@string.Length > 26) ? @string.Substring(26) : string.Empty;
|
|||
|
}
|
|||
|
catch
|
|||
|
{
|
|||
|
}
|
|||
|
|
|||
|
return string.Empty;
|
|||
|
}
|
|||
|
|
|||
|
public static string Encrypt(string body, string key)
|
|||
|
{
|
|||
|
try
|
|||
|
{
|
|||
|
byte[] array = GZipCompress(Encoding.UTF8.GetBytes(body));
|
|||
|
string text = MD5(key);
|
|||
|
string s = MD5(text.Substring(0, 16));
|
|||
|
string text2 = MD5(text.Substring(16, 16));
|
|||
|
string pwd = text2 + MD5(text2);
|
|||
|
byte[] bytes = Encoding.UTF8.GetBytes(string.Format("{0}", Math.Round(GetCurrentSec()) + 3600.0));
|
|||
|
string s2 = MD5(array.Concat(Encoding.UTF8.GetBytes(s)).ToArray<byte>()).Substring(0, 16);
|
|||
|
byte[] array2 = new byte[array.Length + 26];
|
|||
|
|
|||
|
Array.Copy(bytes, 0, array2, 0, bytes.Length);
|
|||
|
Array.Copy(Encoding.UTF8.GetBytes(s2), 0, array2, 10, 16);
|
|||
|
Array.Copy(array, 0, array2, 26, array.Length);
|
|||
|
|
|||
|
return "#" + Convert.ToBase64String(RC4(array2, pwd));
|
|||
|
}
|
|||
|
catch
|
|||
|
{
|
|||
|
}
|
|||
|
|
|||
|
return string.Empty;
|
|||
|
}
|
|||
|
|
|||
|
public static byte[] ConvertFromBase64String(string input)
|
|||
|
{
|
|||
|
byte[] result = [];
|
|||
|
|
|||
|
try
|
|||
|
{
|
|||
|
result = Convert.FromBase64String(input);
|
|||
|
}
|
|||
|
catch
|
|||
|
{
|
|||
|
try
|
|||
|
{
|
|||
|
result = Convert.FromBase64String(input + "=");
|
|||
|
}
|
|||
|
catch
|
|||
|
{
|
|||
|
try
|
|||
|
{
|
|||
|
result = Convert.FromBase64String(input + "==");
|
|||
|
}
|
|||
|
catch
|
|||
|
{
|
|||
|
return result;
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
return result;
|
|||
|
}
|
|||
|
|
|||
|
public static double GetCurrentSec()
|
|||
|
{
|
|||
|
return (DateTime.UtcNow - epoch).TotalSeconds;
|
|||
|
}
|
|||
|
|
|||
|
public static string MD5(string input)
|
|||
|
{
|
|||
|
return MD5(Encoding.UTF8.GetBytes(input));
|
|||
|
}
|
|||
|
|
|||
|
public static string MD5(byte[] input)
|
|||
|
{
|
|||
|
byte[] array = md5.ComputeHash(input);
|
|||
|
StringBuilder stringBuilder = new StringBuilder();
|
|||
|
|
|||
|
for (int i = 0; i < array.Length; i++)
|
|||
|
stringBuilder.Append(array[i].ToString("x2"));
|
|||
|
|
|||
|
return stringBuilder.ToString();
|
|||
|
}
|
|||
|
|
|||
|
public static byte[] RC4(byte[] data, string pwd)
|
|||
|
{
|
|||
|
return RC4(data, Encoding.UTF8.GetBytes(pwd));
|
|||
|
}
|
|||
|
|
|||
|
public static byte[] RC4(byte[] data, byte[] pwd)
|
|||
|
{
|
|||
|
int[] array = new int[256];
|
|||
|
int[] array2 = new int[256];
|
|||
|
byte[] array3 = new byte[data.Length];
|
|||
|
int i;
|
|||
|
int num;
|
|||
|
|
|||
|
for (i = 0; i < 256; i++)
|
|||
|
{
|
|||
|
array[i] = (int)pwd[i % pwd.Length];
|
|||
|
array2[i] = i;
|
|||
|
}
|
|||
|
|
|||
|
for (i = (num = 0); i < 256; i++)
|
|||
|
{
|
|||
|
int num2 = array2[i];
|
|||
|
|
|||
|
num = (num + array2[i] + array[i]) % 256;
|
|||
|
array2[i] = array2[num];
|
|||
|
array2[num] = num2;
|
|||
|
}
|
|||
|
|
|||
|
int num3;
|
|||
|
num = (num3 = (i = 0));
|
|||
|
|
|||
|
while (i < data.Length)
|
|||
|
{
|
|||
|
num3++;
|
|||
|
num3 %= 256;
|
|||
|
num += array2[num3];
|
|||
|
num %= 256;
|
|||
|
|
|||
|
int num2 = array2[num3];
|
|||
|
array2[num3] = array2[num];
|
|||
|
array2[num] = num2;
|
|||
|
|
|||
|
int num4 = array2[(array2[num3] + array2[num]) % 256];
|
|||
|
array3[i] = (byte)((int)data[i] ^ num4);
|
|||
|
|
|||
|
i++;
|
|||
|
}
|
|||
|
|
|||
|
return array3;
|
|||
|
}
|
|||
|
|
|||
|
public static byte[] GZipCompress(byte[] raw)
|
|||
|
{
|
|||
|
byte[] result;
|
|||
|
|
|||
|
using (MemoryStream memoryStream = new MemoryStream())
|
|||
|
{
|
|||
|
using GZipOutputStream gzipOutputStream = new GZipOutputStream(memoryStream);
|
|||
|
|
|||
|
gzipOutputStream.IsStreamOwner = false;
|
|||
|
gzipOutputStream.Write(raw, 0, raw.Length);
|
|||
|
gzipOutputStream.Flush();
|
|||
|
gzipOutputStream.Finish();
|
|||
|
|
|||
|
result = memoryStream.ToArray();
|
|||
|
}
|
|||
|
|
|||
|
return result;
|
|||
|
}
|
|||
|
|
|||
|
public static string GZipDecompress(byte[] raw)
|
|||
|
{
|
|||
|
string result;
|
|||
|
|
|||
|
using (MemoryStream memoryStream = new MemoryStream(raw))
|
|||
|
{
|
|||
|
using Stream stream = new GZipInputStream(memoryStream);
|
|||
|
using StreamReader streamReader = new StreamReader(stream, Encoding.UTF8);
|
|||
|
|
|||
|
result = streamReader.ReadToEnd();
|
|||
|
}
|
|||
|
|
|||
|
return result;
|
|||
|
}
|
|||
|
|
|||
|
public static string CompressText(string text)
|
|||
|
{
|
|||
|
byte[] bytes = Encoding.UTF8.GetBytes(text);
|
|||
|
byte[]? inArray = null;
|
|||
|
|
|||
|
using (MemoryStream memoryStream = new MemoryStream())
|
|||
|
{
|
|||
|
using (GZipStream gzipStream = new GZipStream(memoryStream, CompressionMode.Compress))
|
|||
|
{
|
|||
|
gzipStream.Write(bytes, 0, bytes.Length);
|
|||
|
}
|
|||
|
|
|||
|
inArray = memoryStream.ToArray();
|
|||
|
}
|
|||
|
|
|||
|
return Convert.ToBase64String(inArray);
|
|||
|
}
|
|||
|
|
|||
|
public static string DecompressText(string text)
|
|||
|
{
|
|||
|
string result = string.Empty;
|
|||
|
|
|||
|
using (MemoryStream memoryStream = new MemoryStream(Convert.FromBase64String(text)))
|
|||
|
{
|
|||
|
using (GZipStream gzipStream = new GZipStream(memoryStream, CompressionMode.Decompress))
|
|||
|
{
|
|||
|
using (StreamReader streamReader = new StreamReader(gzipStream))
|
|||
|
{
|
|||
|
result = streamReader.ReadToEnd();
|
|||
|
}
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
return result;
|
|||
|
}
|
|||
|
|
|||
|
public static string ConvertMD5(string input)
|
|||
|
{
|
|||
|
byte[] array = md5.ComputeHash(Encoding.UTF8.GetBytes(input));
|
|||
|
StringBuilder stringBuilder = new StringBuilder();
|
|||
|
|
|||
|
for (int i = 0; i < array.Length; i++)
|
|||
|
stringBuilder.Append(array[i].ToString("x2"));
|
|||
|
|
|||
|
return stringBuilder.ToString();
|
|||
|
}
|
|||
|
}
|