1
0
mirror of https://github.com/v2fly/v2ray-core.git synced 2025-01-17 23:06:30 -05:00

support none cipher in shadowsocks

This commit is contained in:
Darien Raymond 2017-11-29 22:19:04 +01:00
parent fd8db49dc9
commit cb68575444
No known key found for this signature in database
GPG Key ID: 7251FFA14BB18169
4 changed files with 104 additions and 69 deletions

View File

@ -44,8 +44,8 @@ func createChacha20Poly1305(key []byte) cipher.AEAD {
return chacha20 return chacha20
} }
func (v *Account) GetCipher() (Cipher, error) { func (a *Account) GetCipher() (Cipher, error) {
switch v.CipherType { switch a.CipherType {
case CipherType_AES_128_CFB: case CipherType_AES_128_CFB:
return &AesCfb{KeyBytes: 16}, nil return &AesCfb{KeyBytes: 16}, nil
case CipherType_AES_256_CFB: case CipherType_AES_256_CFB:
@ -72,31 +72,25 @@ func (v *Account) GetCipher() (Cipher, error) {
IVBytes: 32, IVBytes: 32,
AEADAuthCreator: createChacha20Poly1305, AEADAuthCreator: createChacha20Poly1305,
}, nil }, nil
case CipherType_NONE:
return NoneCipher{}, nil
default: default:
return nil, newError("Unsupported cipher.") return nil, newError("Unsupported cipher.")
} }
} }
func (v *Account) AsAccount() (protocol.Account, error) { func (a *Account) AsAccount() (protocol.Account, error) {
cipher, err := v.GetCipher() cipher, err := a.GetCipher()
if err != nil { if err != nil {
return nil, newError("failed to get cipher").Base(err) return nil, newError("failed to get cipher").Base(err)
} }
return &ShadowsocksAccount{ return &ShadowsocksAccount{
Cipher: cipher, Cipher: cipher,
Key: v.GetCipherKey(), Key: PasswordToCipherKey([]byte(a.Password), cipher.KeySize()),
OneTimeAuth: v.Ota, OneTimeAuth: a.Ota,
}, nil }, nil
} }
func (v *Account) GetCipherKey() []byte {
ct, err := v.GetCipher()
if err != nil {
return nil
}
return PasswordToCipherKey(v.Password, ct.KeySize())
}
type Cipher interface { type Cipher interface {
KeySize() int KeySize() int
IVSize() int IVSize() int
@ -261,17 +255,40 @@ func (v *ChaCha20) DecodePacket(key []byte, b *buf.Buffer) error {
return nil return nil
} }
func PasswordToCipherKey(password string, keySize int) []byte { type NoneCipher struct{}
pwdBytes := []byte(password)
func (NoneCipher) KeySize() int { return 0 }
func (NoneCipher) IVSize() int { return 0 }
func (NoneCipher) IsAEAD() bool {
return true // to avoid OTA
}
func (NoneCipher) NewDecryptionReader(key []byte, iv []byte, reader io.Reader) (buf.Reader, error) {
return buf.NewReader(reader), nil
}
func (NoneCipher) NewEncryptionWriter(key []byte, iv []byte, writer io.Writer) (buf.Writer, error) {
return buf.NewWriter(writer), nil
}
func (NoneCipher) EncodePacket(key []byte, b *buf.Buffer) error {
return nil
}
func (NoneCipher) DecodePacket(key []byte, b *buf.Buffer) error {
return nil
}
func PasswordToCipherKey(password []byte, keySize int) []byte {
key := make([]byte, 0, keySize) key := make([]byte, 0, keySize)
md5Sum := md5.Sum(pwdBytes) md5Sum := md5.Sum(password)
key = append(key, md5Sum[:]...) key = append(key, md5Sum[:]...)
for len(key) < keySize { for len(key) < keySize {
md5Hash := md5.New() md5Hash := md5.New()
md5Hash.Write(md5Sum[:]) md5Hash.Write(md5Sum[:])
md5Hash.Write(pwdBytes) md5Hash.Write(password)
md5Hash.Sum(md5Sum[:0]) md5Hash.Sum(md5Sum[:0])
key = append(key, md5Sum[:]...) key = append(key, md5Sum[:]...)

View File

@ -28,6 +28,7 @@ const (
CipherType_AES_128_GCM CipherType = 5 CipherType_AES_128_GCM CipherType = 5
CipherType_AES_256_GCM CipherType = 6 CipherType_AES_256_GCM CipherType = 6
CipherType_CHACHA20_POLY1305 CipherType = 7 CipherType_CHACHA20_POLY1305 CipherType = 7
CipherType_NONE CipherType = 8
) )
var CipherType_name = map[int32]string{ var CipherType_name = map[int32]string{
@ -39,6 +40,7 @@ var CipherType_name = map[int32]string{
5: "AES_128_GCM", 5: "AES_128_GCM",
6: "AES_256_GCM", 6: "AES_256_GCM",
7: "CHACHA20_POLY1305", 7: "CHACHA20_POLY1305",
8: "NONE",
} }
var CipherType_value = map[string]int32{ var CipherType_value = map[string]int32{
"UNKNOWN": 0, "UNKNOWN": 0,
@ -49,6 +51,7 @@ var CipherType_value = map[string]int32{
"AES_128_GCM": 5, "AES_128_GCM": 5,
"AES_256_GCM": 6, "AES_256_GCM": 6,
"CHACHA20_POLY1305": 7, "CHACHA20_POLY1305": 7,
"NONE": 8,
} }
func (x CipherType) String() string { func (x CipherType) String() string {
@ -163,35 +166,35 @@ func init() {
func init() { proto.RegisterFile("v2ray.com/core/proxy/shadowsocks/config.proto", fileDescriptor0) } func init() { proto.RegisterFile("v2ray.com/core/proxy/shadowsocks/config.proto", fileDescriptor0) }
var fileDescriptor0 = []byte{ var fileDescriptor0 = []byte{
// 470 bytes of a gzipped FileDescriptorProto // 477 bytes of a gzipped FileDescriptorProto
0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x84, 0x91, 0xd1, 0x8e, 0xd2, 0x40, 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0x84, 0x91, 0x51, 0x8f, 0x93, 0x40,
0x14, 0x86, 0xb7, 0x80, 0x80, 0xa7, 0xa8, 0xdd, 0x49, 0x4c, 0x08, 0xd9, 0x44, 0xc2, 0x15, 0x6e, 0x14, 0x85, 0x97, 0xb6, 0xb6, 0xf5, 0x52, 0x95, 0x9d, 0xc4, 0xa4, 0x69, 0x36, 0xb1, 0xe9, 0x53,
0xe2, 0x14, 0xba, 0xae, 0xf1, 0xb6, 0x8c, 0xac, 0xbb, 0x51, 0x81, 0x14, 0x56, 0xa3, 0x37, 0x4d, 0xdd, 0xc4, 0xa1, 0x65, 0x5d, 0xe3, 0x2b, 0x45, 0xd6, 0xdd, 0xa8, 0xb4, 0xa1, 0x5d, 0x8d, 0xbe,
0x77, 0x3a, 0x4a, 0x23, 0xed, 0x4c, 0x66, 0xda, 0x5d, 0xfb, 0x20, 0xbe, 0x84, 0x6f, 0xe6, 0x5b, 0x10, 0x76, 0x18, 0x2d, 0xb1, 0x30, 0x93, 0x19, 0xd8, 0x95, 0x5f, 0xe3, 0xbb, 0xff, 0xcc, 0x7f,
0x98, 0x4e, 0x81, 0x6d, 0xbc, 0x60, 0xef, 0x7a, 0x4e, 0xff, 0xff, 0xef, 0x7f, 0xbe, 0xc2, 0xab, 0x61, 0x18, 0xda, 0x2e, 0xf1, 0xa1, 0xfb, 0xc6, 0xbd, 0x9c, 0x73, 0x38, 0xf7, 0x03, 0x5e, 0xdd,
0x5b, 0x47, 0x06, 0x39, 0xa6, 0x3c, 0xb6, 0x29, 0x97, 0xcc, 0x16, 0x92, 0xff, 0xca, 0x6d, 0xb5, 0x5a, 0x22, 0x2c, 0x30, 0x61, 0x89, 0x49, 0x98, 0xa0, 0x26, 0x17, 0xec, 0x57, 0x61, 0xca, 0x75,
0x0e, 0x42, 0x7e, 0xa7, 0x38, 0xfd, 0xa9, 0x6c, 0xca, 0x93, 0xef, 0xd1, 0x0f, 0x2c, 0x24, 0x4f, 0x18, 0xb1, 0x3b, 0xc9, 0xc8, 0x4f, 0x69, 0x12, 0x96, 0x7e, 0x8f, 0x7f, 0x60, 0x2e, 0x58, 0xc6,
0x39, 0x3a, 0xd9, 0xc9, 0x25, 0xc3, 0x5a, 0x8a, 0x2b, 0xd2, 0xde, 0xcb, 0xff, 0xc2, 0x28, 0x8f, 0xd0, 0xc9, 0x4e, 0x2e, 0x28, 0x56, 0x52, 0x5c, 0x93, 0x0e, 0x5e, 0xfe, 0x17, 0x46, 0x58, 0x92,
0x63, 0x9e, 0xd8, 0xda, 0x4a, 0xf9, 0xc6, 0xce, 0x14, 0x93, 0x65, 0x50, 0x6f, 0xf4, 0x80, 0x54, 0xb0, 0xd4, 0x54, 0x56, 0xc2, 0x36, 0x66, 0x2e, 0xa9, 0xa8, 0x82, 0x06, 0x93, 0x07, 0xa4, 0x92,
0x31, 0x79, 0xcb, 0xa4, 0xaf, 0x04, 0xa3, 0xa5, 0x63, 0xf0, 0xd7, 0x80, 0x96, 0x4b, 0x29, 0xcf, 0x8a, 0x5b, 0x2a, 0x02, 0xc9, 0x29, 0xa9, 0x1c, 0xa3, 0xbf, 0x1a, 0x74, 0x6c, 0x42, 0x58, 0x9e,
0x92, 0x14, 0xf5, 0xa0, 0x2d, 0x02, 0xa5, 0xee, 0xb8, 0x0c, 0xbb, 0x46, 0xdf, 0x18, 0x3e, 0xf6, 0x66, 0x68, 0x00, 0x5d, 0x1e, 0x4a, 0x79, 0xc7, 0x44, 0xd4, 0xd7, 0x86, 0xda, 0xf8, 0xb1, 0xbf,
0xf6, 0x33, 0xba, 0x02, 0x93, 0x46, 0x62, 0xcd, 0xa4, 0x9f, 0xe6, 0x82, 0x75, 0x6b, 0x7d, 0x63, 0x9f, 0xd1, 0x15, 0xe8, 0x24, 0xe6, 0x6b, 0x2a, 0x82, 0xac, 0xe0, 0xb4, 0xdf, 0x18, 0x6a, 0xe3,
0xf8, 0xd4, 0x19, 0xe2, 0x43, 0xc5, 0x31, 0xd1, 0x86, 0x55, 0x2e, 0x98, 0x07, 0x74, 0xff, 0x8c, 0xa7, 0xd6, 0x18, 0x1f, 0x2a, 0x8e, 0x1d, 0x65, 0x58, 0x15, 0x9c, 0xfa, 0x40, 0xf6, 0xcf, 0xc8,
0x08, 0xd4, 0x79, 0x1a, 0x74, 0xeb, 0x3a, 0x62, 0x7c, 0x38, 0x62, 0x5b, 0x0d, 0xcf, 0x13, 0xb6, 0x81, 0x26, 0xcb, 0xc2, 0x7e, 0x53, 0x45, 0x4c, 0x0f, 0x47, 0x6c, 0xab, 0xe1, 0x79, 0x4a, 0x57,
0x8a, 0x62, 0xe6, 0x66, 0xe9, 0xda, 0x2b, 0xdc, 0x03, 0x07, 0xcc, 0xca, 0x0e, 0xb5, 0xa1, 0xe1, 0x71, 0x42, 0xed, 0x3c, 0x5b, 0xfb, 0xa5, 0x7b, 0x64, 0x81, 0x5e, 0xdb, 0xa1, 0x2e, 0xb4, 0xec,
0x66, 0x29, 0xb7, 0x8e, 0x50, 0x07, 0xda, 0xef, 0x22, 0x15, 0xdc, 0x6c, 0x58, 0x68, 0x19, 0xc8, 0x3c, 0x63, 0xc6, 0x11, 0xea, 0x41, 0xf7, 0x5d, 0x2c, 0xc3, 0x9b, 0x0d, 0x8d, 0x0c, 0x0d, 0xe9,
0x84, 0xd6, 0x34, 0x29, 0x87, 0xda, 0x80, 0x41, 0x67, 0xa9, 0x01, 0x10, 0x0d, 0x1f, 0xbd, 0x00, 0xd0, 0x71, 0xd3, 0x6a, 0x68, 0x8c, 0x28, 0xf4, 0x96, 0x0a, 0x80, 0xa3, 0xe0, 0xa3, 0x17, 0xa0,
0x33, 0x0b, 0x85, 0xcf, 0x4a, 0x81, 0x3e, 0xb9, 0xed, 0x41, 0x16, 0x8a, 0xad, 0x05, 0xbd, 0x86, 0xe7, 0x11, 0x0f, 0x68, 0x25, 0x50, 0x27, 0x77, 0x7d, 0xc8, 0x23, 0xbe, 0xb5, 0xa0, 0xd7, 0xd0,
0x46, 0x01, 0x57, 0x5f, 0x6b, 0x3a, 0xfd, 0x6a, 0xd5, 0x92, 0x2c, 0xde, 0x91, 0xc5, 0xd7, 0x8a, 0x2a, 0xe1, 0xaa, 0x6b, 0x75, 0x6b, 0x58, 0xaf, 0x5a, 0x91, 0xc5, 0x3b, 0xb2, 0xf8, 0x5a, 0x52,
0x49, 0x4f, 0xab, 0x07, 0x1e, 0x74, 0xc8, 0x26, 0x62, 0x49, 0xba, 0xfd, 0xcc, 0x04, 0x9a, 0x25, 0xe1, 0x2b, 0xf5, 0xc8, 0x87, 0x9e, 0xb3, 0x89, 0x69, 0x9a, 0x6d, 0x3f, 0x33, 0x83, 0x76, 0xc5,
0xf7, 0xae, 0xd1, 0xaf, 0x0f, 0x4d, 0xe7, 0xf4, 0x50, 0x4e, 0x59, 0x70, 0x9a, 0x84, 0x82, 0x47, 0xbd, 0xaf, 0x0d, 0x9b, 0x63, 0xdd, 0x3a, 0x3d, 0x94, 0x53, 0x15, 0x74, 0xd3, 0x88, 0xb3, 0x38,
0x49, 0xea, 0x6d, 0x9d, 0xa7, 0xbf, 0x0d, 0x80, 0x7b, 0x9c, 0xc5, 0x59, 0xd7, 0xb3, 0x0f, 0xb3, 0xcd, 0xfc, 0xad, 0xf3, 0xf4, 0xb7, 0x06, 0x70, 0x8f, 0xb3, 0x3c, 0xeb, 0xda, 0xfb, 0xe0, 0xcd,
0xf9, 0x97, 0x99, 0x75, 0x84, 0x9e, 0x81, 0xe9, 0x4e, 0x97, 0xfe, 0xd8, 0x79, 0xeb, 0x93, 0x8b, 0xbf, 0x78, 0xc6, 0x11, 0x7a, 0x06, 0xba, 0xed, 0x2e, 0x83, 0xa9, 0xf5, 0x36, 0x70, 0x2e, 0x66,
0x89, 0x65, 0xec, 0x16, 0xce, 0xf9, 0x1b, 0xbd, 0xa8, 0x15, 0x4c, 0xc8, 0xa5, 0x4b, 0x2e, 0x5d, 0x86, 0xb6, 0x5b, 0x58, 0xe7, 0x6f, 0xd4, 0xa2, 0x51, 0x32, 0x71, 0x2e, 0x6d, 0xe7, 0xd2, 0xb6,
0x67, 0x64, 0xd5, 0xd1, 0x31, 0x3c, 0xd9, 0x4d, 0xfe, 0xd5, 0x74, 0x75, 0x61, 0x35, 0xaa, 0x11, 0x26, 0x46, 0x13, 0x1d, 0xc3, 0x93, 0xdd, 0x14, 0x5c, 0xb9, 0xab, 0x0b, 0xa3, 0x55, 0x8f, 0x78,
0xef, 0xc9, 0x27, 0xeb, 0x51, 0x35, 0xa2, 0x58, 0x34, 0xd1, 0x73, 0x38, 0xde, 0x9b, 0x16, 0xf3, 0xef, 0x7c, 0x32, 0x1e, 0xd5, 0x23, 0xca, 0x45, 0x1b, 0x3d, 0x87, 0xe3, 0xbd, 0x69, 0x31, 0xff,
0x8f, 0x5f, 0xc7, 0x67, 0xa3, 0x73, 0xab, 0x35, 0x59, 0x40, 0x9f, 0xf2, 0xf8, 0xe0, 0x3f, 0x5c, 0xf8, 0x75, 0x7a, 0x36, 0x39, 0x37, 0x3a, 0x25, 0x77, 0x6f, 0xee, 0xb9, 0x46, 0x77, 0xb6, 0x80,
0x18, 0xdf, 0xcc, 0xca, 0xf8, 0xa7, 0x76, 0xf2, 0xd9, 0xf1, 0x82, 0x1c, 0x93, 0x42, 0xbd, 0xd0, 0x21, 0x61, 0xc9, 0xc1, 0xbf, 0xb9, 0xd0, 0xbe, 0xe9, 0xb5, 0xf1, 0x4f, 0xe3, 0xe4, 0xb3, 0xe5,
0xea, 0xe5, 0xfd, 0xeb, 0x9b, 0xa6, 0x46, 0x71, 0xf6, 0x2f, 0x00, 0x00, 0xff, 0xff, 0x37, 0x7d, 0x87, 0x05, 0x76, 0x4a, 0xf5, 0x42, 0xa9, 0x97, 0xf7, 0xaf, 0x6f, 0xda, 0x0a, 0xca, 0xd9, 0xbf,
0x8e, 0xab, 0x43, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0x02, 0xd5, 0x9f, 0x8c, 0x4d, 0x03, 0x00, 0x00,
} }

View File

@ -29,6 +29,7 @@ enum CipherType {
AES_128_GCM = 5; AES_128_GCM = 5;
AES_256_GCM = 6; AES_256_GCM = 6;
CHACHA20_POLY1305 = 7; CHACHA20_POLY1305 = 7;
NONE = 8;
} }
message ServerConfig { message ServerConfig {

View File

@ -33,11 +33,14 @@ func ReadTCPSession(user *protocol.User, reader io.Reader) (*protocol.RequestHea
defer buffer.Release() defer buffer.Release()
ivLen := account.Cipher.IVSize() ivLen := account.Cipher.IVSize()
var iv []byte
if ivLen > 0 {
if err := buffer.AppendSupplier(buf.ReadFullFrom(reader, ivLen)); err != nil { if err := buffer.AppendSupplier(buf.ReadFullFrom(reader, ivLen)); err != nil {
return nil, nil, newError("failed to read IV").Base(err) return nil, nil, newError("failed to read IV").Base(err)
} }
iv := append([]byte(nil), buffer.BytesTo(ivLen)...) iv = append([]byte(nil), buffer.BytesTo(ivLen)...)
}
r, err := account.Cipher.NewDecryptionReader(account.Key, iv, reader) r, err := account.Cipher.NewDecryptionReader(account.Key, iv, reader)
if err != nil { if err != nil {
@ -145,12 +148,15 @@ func WriteTCPRequest(request *protocol.RequestHeader, writer io.Writer) (buf.Wri
request.Option.Clear(RequestOptionOneTimeAuth) request.Option.Clear(RequestOptionOneTimeAuth)
} }
iv := make([]byte, account.Cipher.IVSize()) var iv []byte
if account.Cipher.IVSize() > 0 {
iv = make([]byte, account.Cipher.IVSize())
common.Must2(rand.Read(iv)) common.Must2(rand.Read(iv))
_, err = writer.Write(iv) _, err = writer.Write(iv)
if err != nil { if err != nil {
return nil, newError("failed to write IV") return nil, newError("failed to write IV")
} }
}
w, err := account.Cipher.NewEncryptionWriter(account.Key, iv, writer) w, err := account.Cipher.NewEncryptionWriter(account.Key, iv, writer)
if err != nil { if err != nil {
@ -207,11 +213,14 @@ func ReadTCPResponse(user *protocol.User, reader io.Reader) (buf.Reader, error)
} }
account := rawAccount.(*ShadowsocksAccount) account := rawAccount.(*ShadowsocksAccount)
iv := make([]byte, account.Cipher.IVSize()) var iv []byte
if account.Cipher.IVSize() > 0 {
iv = make([]byte, account.Cipher.IVSize())
_, err = io.ReadFull(reader, iv) _, err = io.ReadFull(reader, iv)
if err != nil { if err != nil {
return nil, newError("failed to read IV").Base(err) return nil, newError("failed to read IV").Base(err)
} }
}
return account.Cipher.NewDecryptionReader(account.Key, iv, reader) return account.Cipher.NewDecryptionReader(account.Key, iv, reader)
} }
@ -224,12 +233,15 @@ func WriteTCPResponse(request *protocol.RequestHeader, writer io.Writer) (buf.Wr
} }
account := rawAccount.(*ShadowsocksAccount) account := rawAccount.(*ShadowsocksAccount)
iv := make([]byte, account.Cipher.IVSize()) var iv []byte
if account.Cipher.IVSize() > 0 {
iv = make([]byte, account.Cipher.IVSize())
common.Must2(rand.Read(iv)) common.Must2(rand.Read(iv))
_, err = writer.Write(iv) _, err = writer.Write(iv)
if err != nil { if err != nil {
return nil, newError("failed to write IV.").Base(err) return nil, newError("failed to write IV.").Base(err)
} }
}
return account.Cipher.NewEncryptionWriter(account.Key, iv, writer) return account.Cipher.NewEncryptionWriter(account.Key, iv, writer)
} }
@ -244,7 +256,9 @@ func EncodeUDPPacket(request *protocol.RequestHeader, payload []byte) (*buf.Buff
buffer := buf.New() buffer := buf.New()
ivLen := account.Cipher.IVSize() ivLen := account.Cipher.IVSize()
if ivLen > 0 {
common.Must(buffer.Reset(buf.ReadFullFrom(rand.Reader, ivLen))) common.Must(buffer.Reset(buf.ReadFullFrom(rand.Reader, ivLen)))
}
iv := buffer.Bytes() iv := buffer.Bytes()
switch request.Address.Family() { switch request.Address.Family() {
@ -286,7 +300,7 @@ func DecodeUDPPacket(user *protocol.User, payload *buf.Buffer) (*protocol.Reques
var iv []byte var iv []byte
var authenticator *Authenticator var authenticator *Authenticator
if !account.Cipher.IsAEAD() { if !account.Cipher.IsAEAD() && account.Cipher.IVSize() > 0 {
// Keep track of IV as it gets removed from payload in DecodePacket. // Keep track of IV as it gets removed from payload in DecodePacket.
iv = make([]byte, account.Cipher.IVSize()) iv = make([]byte, account.Cipher.IVSize())
copy(iv, payload.BytesTo(account.Cipher.IVSize())) copy(iv, payload.BytesTo(account.Cipher.IVSize()))