Shadowsocks.Protocolpull/3084/head
@@ -42,7 +42,7 @@ namespace Shadowsocks.Protocol.Shadowsocks | |||||
public async Task ConvertUplink(IDuplexPipe client, IDuplexPipe server) | public async Task ConvertUplink(IDuplexPipe client, IDuplexPipe server) | ||||
{ | { | ||||
var up = cryptoParameter.GetCrypto(); | |||||
using var up = cryptoParameter.GetCrypto(); | |||||
var pmp = new ProtocolMessagePipe(server); | var pmp = new ProtocolMessagePipe(server); | ||||
var salt = new SaltMessage(16, true); | var salt = new SaltMessage(16, true); | ||||
await pmp.WriteAsync(salt); | await pmp.WriteAsync(salt); | ||||
@@ -77,7 +77,7 @@ namespace Shadowsocks.Protocol.Shadowsocks | |||||
public async Task ConvertDownlink(IDuplexPipe client, IDuplexPipe server) | public async Task ConvertDownlink(IDuplexPipe client, IDuplexPipe server) | ||||
{ | { | ||||
var down = cryptoParameter.GetCrypto(); | |||||
using var down = cryptoParameter.GetCrypto(); | |||||
var pmp = new ProtocolMessagePipe(server); | var pmp = new ProtocolMessagePipe(server); | ||||
var salt = await pmp.ReadAsync(new SaltMessage(cryptoParameter.KeySize)); | var salt = await pmp.ReadAsync(new SaltMessage(cryptoParameter.KeySize)); | ||||
@@ -1,38 +1,13 @@ | |||||
using System; | |||||
using System.Security.Cryptography; | |||||
using CryptoBase; | |||||
namespace Shadowsocks.Protocol.Shadowsocks.Crypto | namespace Shadowsocks.Protocol.Shadowsocks.Crypto | ||||
{ | { | ||||
class AeadAesGcmCrypto : ICrypto | |||||
public class AeadAesGcmCrypto : AeadCrypto | |||||
{ | { | ||||
AesGcm aes; | |||||
CryptoParameter parameter; | |||||
public AeadAesGcmCrypto(CryptoParameter parameter) | |||||
public AeadAesGcmCrypto(CryptoParameter parameter) : base(parameter) | |||||
{ | { | ||||
this.parameter = parameter; | |||||
} | } | ||||
public void Init(byte[] key, byte[] iv) => aes = new AesGcm(key); | |||||
public int Decrypt(ReadOnlySpan<byte> nonce, Span<byte> plain, ReadOnlySpan<byte> cipher) | |||||
{ | |||||
aes.Decrypt( | |||||
nonce, | |||||
cipher[0..^parameter.TagSize], | |||||
cipher[^parameter.TagSize..], | |||||
plain[0..(cipher.Length - parameter.TagSize)]); | |||||
return cipher.Length - parameter.TagSize; | |||||
} | |||||
public int Encrypt(ReadOnlySpan<byte> nonce, ReadOnlySpan<byte> plain, Span<byte> cipher) | |||||
{ | |||||
aes.Encrypt( | |||||
nonce, | |||||
plain, | |||||
cipher[0..plain.Length], | |||||
cipher.Slice(plain.Length, parameter.TagSize)); | |||||
return plain.Length + parameter.TagSize; | |||||
} | |||||
public override void Init(byte[] key, byte[] iv) => crypto = AEADCryptoCreate.AesGcm(key); | |||||
} | } | ||||
} | } |
@@ -0,0 +1,13 @@ | |||||
using CryptoBase; | |||||
namespace Shadowsocks.Protocol.Shadowsocks.Crypto | |||||
{ | |||||
public class AeadChaCha20Poly1305Crypto : AeadCrypto | |||||
{ | |||||
public AeadChaCha20Poly1305Crypto(CryptoParameter parameter) : base(parameter) | |||||
{ | |||||
} | |||||
public override void Init(byte[] key, byte[] iv) => crypto = AEADCryptoCreate.ChaCha20Poly1305(key); | |||||
} | |||||
} |
@@ -0,0 +1,41 @@ | |||||
using CryptoBase.Abstractions.SymmetricCryptos; | |||||
using System; | |||||
namespace Shadowsocks.Protocol.Shadowsocks.Crypto | |||||
{ | |||||
public abstract class AeadCrypto : ICrypto | |||||
{ | |||||
protected IAEADCrypto? crypto; | |||||
private readonly CryptoParameter _parameter; | |||||
protected AeadCrypto(CryptoParameter parameter) | |||||
{ | |||||
_parameter = parameter; | |||||
} | |||||
public abstract void Init(byte[] key, byte[] iv); | |||||
public int Decrypt(ReadOnlySpan<byte> nonce, Span<byte> plain, ReadOnlySpan<byte> cipher) | |||||
{ | |||||
crypto!.Decrypt( | |||||
nonce, | |||||
cipher[..^_parameter.TagSize], | |||||
cipher[^_parameter.TagSize..], | |||||
plain[..(cipher.Length - _parameter.TagSize)]); | |||||
return cipher.Length - _parameter.TagSize; | |||||
} | |||||
public int Encrypt(ReadOnlySpan<byte> nonce, ReadOnlySpan<byte> plain, Span<byte> cipher) | |||||
{ | |||||
crypto!.Encrypt( | |||||
nonce, | |||||
plain, | |||||
cipher.Slice(0, plain.Length), | |||||
cipher.Slice(plain.Length, _parameter.TagSize)); | |||||
return plain.Length + _parameter.TagSize; | |||||
} | |||||
public void Dispose() => crypto?.Dispose(); | |||||
} | |||||
} |
@@ -0,0 +1,13 @@ | |||||
using CryptoBase; | |||||
namespace Shadowsocks.Protocol.Shadowsocks.Crypto | |||||
{ | |||||
public class AeadXChaCha20Poly1305Crypto : AeadCrypto | |||||
{ | |||||
public AeadXChaCha20Poly1305Crypto(CryptoParameter parameter) : base(parameter) | |||||
{ | |||||
} | |||||
public override void Init(byte[] key, byte[] iv) => crypto = AEADCryptoCreate.XChaCha20Poly1305(key); | |||||
} | |||||
} |
@@ -7,6 +7,8 @@ namespace Shadowsocks.Protocol.Shadowsocks.Crypto | |||||
{ | { | ||||
static Dictionary<string, CryptoParameter> parameters = new Dictionary<string, CryptoParameter> | static Dictionary<string, CryptoParameter> parameters = new Dictionary<string, CryptoParameter> | ||||
{ | { | ||||
["xchacha20-ietf-poly1305"] = new CryptoParameter { KeySize = 32, NonceSize = 24, TagSize = 16, Crypto = typeof(AeadXChaCha20Poly1305Crypto) }, | |||||
["chacha20-ietf-poly1305"] = new CryptoParameter { KeySize = 32, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadChaCha20Poly1305Crypto) }, | |||||
["aes-256-gcm"] = new CryptoParameter { KeySize = 32, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadAesGcmCrypto) }, | ["aes-256-gcm"] = new CryptoParameter { KeySize = 32, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadAesGcmCrypto) }, | ||||
["aes-192-gcm"] = new CryptoParameter { KeySize = 24, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadAesGcmCrypto) }, | ["aes-192-gcm"] = new CryptoParameter { KeySize = 24, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadAesGcmCrypto) }, | ||||
["aes-128-gcm"] = new CryptoParameter { KeySize = 16, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadAesGcmCrypto) }, | ["aes-128-gcm"] = new CryptoParameter { KeySize = 16, NonceSize = 12, TagSize = 16, Crypto = typeof(AeadAesGcmCrypto) }, | ||||
@@ -6,7 +6,6 @@ namespace Shadowsocks.Protocol.Shadowsocks.Crypto | |||||
{ | { | ||||
public UnsafeNoneCrypto(CryptoParameter parameter) | public UnsafeNoneCrypto(CryptoParameter parameter) | ||||
{ | { | ||||
} | } | ||||
public int Decrypt(ReadOnlySpan<byte> nonce, Span<byte> plain, ReadOnlySpan<byte> cipher) | public int Decrypt(ReadOnlySpan<byte> nonce, Span<byte> plain, ReadOnlySpan<byte> cipher) | ||||
@@ -24,5 +23,9 @@ namespace Shadowsocks.Protocol.Shadowsocks.Crypto | |||||
public void Init(byte[] key, byte[] iv) | public void Init(byte[] key, byte[] iv) | ||||
{ | { | ||||
} | } | ||||
public void Dispose() | |||||
{ | |||||
} | |||||
} | } | ||||
} | } |
@@ -3,7 +3,7 @@ using System; | |||||
namespace Shadowsocks.Protocol.Shadowsocks | namespace Shadowsocks.Protocol.Shadowsocks | ||||
{ | { | ||||
// stream cipher simply ignore nonce | // stream cipher simply ignore nonce | ||||
public interface ICrypto | |||||
public interface ICrypto : IDisposable | |||||
{ | { | ||||
void Init(byte[] key, byte[] iv); | void Init(byte[] key, byte[] iv); | ||||
int Encrypt(ReadOnlySpan<byte> nonce, ReadOnlySpan<byte> plain, Span<byte> cipher); | int Encrypt(ReadOnlySpan<byte> nonce, ReadOnlySpan<byte> plain, Span<byte> cipher); | ||||
@@ -24,7 +24,7 @@ namespace Shadowsocks.Protocol.Shadowsocks | |||||
public async Task ConvertUplink(IDuplexPipe client, IDuplexPipe server) | public async Task ConvertUplink(IDuplexPipe client, IDuplexPipe server) | ||||
{ | { | ||||
var up = parameter.GetCrypto(); | |||||
using var up = parameter.GetCrypto(); | |||||
var pmp = new ProtocolMessagePipe(server); | var pmp = new ProtocolMessagePipe(server); | ||||
var key = CryptoUtils.SSKDF(password, parameter.KeySize); | var key = CryptoUtils.SSKDF(password, parameter.KeySize); | ||||
@@ -54,7 +54,7 @@ namespace Shadowsocks.Protocol.Shadowsocks | |||||
public async Task ConvertDownlink(IDuplexPipe client, IDuplexPipe server) | public async Task ConvertDownlink(IDuplexPipe client, IDuplexPipe server) | ||||
{ | { | ||||
var down = parameter.GetCrypto(); | |||||
using var down = parameter.GetCrypto(); | |||||
var pmp = new ProtocolMessagePipe(server); | var pmp = new ProtocolMessagePipe(server); | ||||
var salt = await pmp.ReadAsync(new SaltMessage(parameter.NonceSize)); | var salt = await pmp.ReadAsync(new SaltMessage(parameter.NonceSize)); | ||||