func (this *SimpleAuthenticator) Open(buffer *alloc.Buffer) bool { len := buffer.Len() xtra := 4 - len%4 if xtra != 0 { buffer.Slice(0, len+xtra) } xorbkd(buffer.Value) if xtra != 0 { buffer.Slice(0, len) } fnvHash := fnv.New32a() fnvHash.Write(buffer.Value[4:]) if serial.BytesToUint32(buffer.Value[:4]) != fnvHash.Sum32() { return false } length := serial.BytesToUint16(buffer.Value[4:6]) if buffer.Len()-6 != int(length) { return false } buffer.SliceFrom(6) return true }
func ReadFrom(reader io.Reader, buffer *alloc.Buffer) (*alloc.Buffer, error) { if buffer == nil { buffer = alloc.NewBuffer() } nBytes, err := reader.Read(buffer.Value) buffer.Slice(0, nBytes) return buffer, err }
// ToBytes returns a VMessRequest in the form of byte array. func (this *VMessRequest) ToBytes(timestampGenerator RandomTimestampGenerator, buffer *alloc.Buffer) (*alloc.Buffer, error) { if buffer == nil { buffer = alloc.NewSmallBuffer().Clear() } timestamp := timestampGenerator.Next() idHash := IDHash(this.User.AnyValidID().Bytes()) idHash.Write(timestamp.Bytes()) hashStart := buffer.Len() buffer.Slice(0, hashStart+16) idHash.Sum(buffer.Value[hashStart:hashStart]) encryptionBegin := buffer.Len() buffer.AppendBytes(this.Version) buffer.Append(this.RequestIV) buffer.Append(this.RequestKey) buffer.AppendBytes(this.ResponseHeader, this.Option, byte(0), byte(0)) buffer.AppendBytes(this.Command) buffer.Append(this.Port.Bytes()) switch { case this.Address.IsIPv4(): buffer.AppendBytes(addrTypeIPv4) buffer.Append(this.Address.IP()) case this.Address.IsIPv6(): buffer.AppendBytes(addrTypeIPv6) buffer.Append(this.Address.IP()) case this.Address.IsDomain(): buffer.AppendBytes(addrTypeDomain, byte(len(this.Address.Domain()))) buffer.Append([]byte(this.Address.Domain())) } encryptionEnd := buffer.Len() fnv1a := fnv.New32a() fnv1a.Write(buffer.Value[encryptionBegin:encryptionEnd]) fnvHash := fnv1a.Sum32() buffer.AppendBytes(byte(fnvHash>>24), byte(fnvHash>>16), byte(fnvHash>>8), byte(fnvHash)) encryptionEnd += 4 timestampHash := md5.New() timestampHash.Write(timestamp.HashBytes()) iv := timestampHash.Sum(nil) aesStream, err := v2crypto.NewAesEncryptionStream(this.User.ID.CmdKey(), iv) if err != nil { return nil, err } aesStream.XORKeyStream(buffer.Value[encryptionBegin:encryptionEnd], buffer.Value[encryptionBegin:encryptionEnd]) return buffer, nil }
func (this *SimpleAuthenticator) Seal(buffer *alloc.Buffer) { buffer.PrependUint16(uint16(buffer.Len())) fnvHash := fnv.New32a() fnvHash.Write(buffer.Value) buffer.PrependHash(fnvHash) len := buffer.Len() xtra := 4 - len%4 if xtra != 0 { buffer.Slice(0, len+xtra) } xorfwd(buffer.Value) if xtra != 0 { buffer.Slice(0, len) } }
func (this *AuthChunkReader) Read() (*alloc.Buffer, error) { var buffer *alloc.Buffer if this.last != nil { buffer = this.last this.last = nil } else { buffer = alloc.NewBufferWithSize(4096).Clear() } if this.chunkLength == -1 { for buffer.Len() < 6 { _, err := buffer.FillFrom(this.reader) if err != nil { buffer.Release() return nil, io.ErrUnexpectedEOF } } length := serial.BytesToUint16(buffer.Value[:2]) this.chunkLength = int(length) - 4 this.validator = NewValidator(serial.BytesToUint32(buffer.Value[2:6])) buffer.SliceFrom(6) if buffer.Len() < this.chunkLength && this.chunkLength <= 2048 { _, err := buffer.FillFrom(this.reader) if err != nil { buffer.Release() return nil, io.ErrUnexpectedEOF } } } else if buffer.Len() < this.chunkLength { _, err := buffer.FillFrom(this.reader) if err != nil { buffer.Release() return nil, io.ErrUnexpectedEOF } } if this.chunkLength == 0 { buffer.Release() return nil, io.EOF } if buffer.Len() < this.chunkLength { this.validator.Consume(buffer.Value) this.chunkLength -= buffer.Len() } else { this.validator.Consume(buffer.Value[:this.chunkLength]) if !this.validator.Validate() { buffer.Release() return nil, transport.ErrCorruptedPacket } leftLength := buffer.Len() - this.chunkLength if leftLength > 0 { this.last = alloc.NewBufferWithSize(leftLength + 4096).Clear() this.last.Append(buffer.Value[this.chunkLength:]) buffer.Slice(0, this.chunkLength) } this.chunkLength = -1 this.validator = nil } return buffer, nil }