|
-
- namespace shadowsocks_csharp.Encrypt
- {
- public class Rc4Encryptor
- : EncryptorBase
- {
- public Rc4Encryptor(string method, string password)
- : base(method, password)
- {
- byte[] hash = GetPasswordHash();
- _encryptTable = EncryptInitalize(hash);
- _decryptTable = EncryptInitalize(hash);
- }
-
- public override byte[] Encrypt(byte[] buf, int length)
- {
- return EncryptOutput(enc_ctx, _encryptTable, buf, length);
- }
-
- public override byte[] Decrypt(byte[] buf, int length)
- {
- return EncryptOutput(dec_ctx, _decryptTable, buf, length);
- }
-
- private readonly byte[] _encryptTable = new byte[256];
- private readonly byte[] _decryptTable = new byte[256];
-
- private Context enc_ctx = new Context();
- private Context dec_ctx = new Context();
-
- private byte[] EncryptOutput(Context ctx, byte[] s, byte[] data, int length)
- {
- byte[] result = new byte[length];
- for (int n = 0; n < length; n++)
- {
- byte b = data[n];
-
- ctx.Index1 = (ctx.Index1 + 1) & 255;
- ctx.Index2 = (ctx.Index2 + s[ctx.Index1]) & 255;
-
- Swap(s, ctx.Index1, ctx.Index2);
-
- result[n] = (byte)(b ^ s[(s[ctx.Index1] + s[ctx.Index2]) & 255]);
- }
- return result;
- }
-
- private byte[] EncryptInitalize(byte[] key)
- {
- var s = new byte[256];
-
- for (int i = 0; i < 256; i++)
- {
- s[i] = (byte)i;
- }
-
- for (int i = 0, j = 0; i < 256; i++)
- {
- j = (j + key[i % key.Length] + s[i]) & 255;
-
- Swap(s, i, j);
- }
-
- return s;
- }
-
- private static void Swap(byte[] s, int i, int j)
- {
- byte c = s[i];
-
- s[i] = s[j];
- s[j] = c;
- }
-
- class Context
- {
- public int Index1;
- public int Index2;
- }
- }
- }
|