示例#1
0
func (w *VMessRequestWriter) Write(writer io.Writer, request *VMessRequest) error {
	buffer := make([]byte, 0, 300)
	buffer = append(buffer, request.Version())
	buffer = append(buffer, request.UserHash()...)

	encryptionBegin := len(buffer)

	randomLength := mrand.Intn(32) + 1
	randomContent := make([]byte, randomLength)
	_, err := rand.Read(randomContent)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(randomLength))
	buffer = append(buffer, randomContent...)

	buffer = append(buffer, request.RequestIV()...)
	buffer = append(buffer, request.RequestKey()...)
	buffer = append(buffer, request.ResponseHeader()...)
	buffer = append(buffer, request.Command())
	buffer = append(buffer, request.portBytes()...)
	buffer = append(buffer, request.targetAddressType())
	buffer = append(buffer, request.targetAddressBytes()...)

	paddingLength := blockSize - 1 - (len(buffer)-encryptionBegin)%blockSize
	if paddingLength == 0 {
		paddingLength = blockSize
	}
	paddingBuffer := make([]byte, paddingLength)
	_, err = rand.Read(paddingBuffer)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(paddingLength))
	buffer = append(buffer, paddingBuffer...)
	encryptionEnd := len(buffer)

	userId, valid := w.vUserSet.IsValidUserId(request.UserHash())
	if !valid {
		return ErrorInvalidUser
	}
	aesCipher, err := aes.NewCipher(userId.Hash([]byte("PWD")))
	if err != nil {
		return err
	}
	aesMode := cipher.NewCBCEncrypter(aesCipher, make([]byte, blockSize))
	cWriter := v2io.NewCryptionWriter(aesMode, writer)

	_, err = writer.Write(buffer[0:encryptionBegin])
	if err != nil {
		return err
	}
	_, err = cWriter.Write(buffer[encryptionBegin:encryptionEnd])
	if err != nil {
		return err
	}

	return nil
}
示例#2
0
func (w *VMessRequestWriter) Write(writer io.Writer, request *VMessRequest) error {
	buffer := make([]byte, 0, 300)

	counter := w.randomRangeInt64(time.Now().UTC().Unix(), 30)
	idHash := w.idHash.Hash(request.UserId.Bytes, counter)

	log.Debug("Writing userhash: %v", idHash)
	buffer = append(buffer, idHash...)

	encryptionBegin := len(buffer)

	randomLength := mrand.Intn(32) + 1
	randomContent := make([]byte, randomLength)
	_, err := rand.Read(randomContent)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(randomLength))
	buffer = append(buffer, randomContent...)

	buffer = append(buffer, request.Version)
	buffer = append(buffer, request.RequestIV[:]...)
	buffer = append(buffer, request.RequestKey[:]...)
	buffer = append(buffer, request.ResponseHeader[:]...)
	buffer = append(buffer, request.Command)

	portBytes := make([]byte, 2)
	binary.BigEndian.PutUint16(portBytes, request.Address.Port)
	buffer = append(buffer, portBytes...)

	switch {
	case request.Address.IsIPv4():
		buffer = append(buffer, addrTypeIPv4)
		buffer = append(buffer, request.Address.IP...)
	case request.Address.IsIPv6():
		buffer = append(buffer, addrTypeIPv6)
		buffer = append(buffer, request.Address.IP...)
	case request.Address.IsDomain():
		buffer = append(buffer, addrTypeDomain)
		buffer = append(buffer, byte(len(request.Address.Domain)))
		buffer = append(buffer, []byte(request.Address.Domain)...)
	}

	paddingLength := mrand.Intn(32) + 1
	paddingBuffer := make([]byte, paddingLength)
	_, err = rand.Read(paddingBuffer)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(paddingLength))
	buffer = append(buffer, paddingBuffer...)
	encryptionEnd := len(buffer)

	aesCipher, err := aes.NewCipher(request.UserId.CmdKey())
	if err != nil {
		return err
	}
	aesStream := cipher.NewCFBEncrypter(aesCipher, v2hash.Int64Hash(counter))
	cWriter := v2io.NewCryptionWriter(aesStream, writer)

	_, err = writer.Write(buffer[0:encryptionBegin])
	if err != nil {
		return err
	}
	_, err = cWriter.Write(buffer[encryptionBegin:encryptionEnd])
	if err != nil {
		return err
	}

	return nil
}
示例#3
0
func (w *VMessRequestWriter) Write(writer io.Writer, request *VMessRequest) error {
	buffer := make([]byte, 0, 300)
	buffer = append(buffer, request.Version)
	buffer = append(buffer, request.UserId.Hash([]byte("ASK"))...)

	encryptionBegin := len(buffer)

	randomLength := mrand.Intn(32) + 1
	randomContent := make([]byte, randomLength)
	_, err := rand.Read(randomContent)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(randomLength))
	buffer = append(buffer, randomContent...)

	buffer = append(buffer, request.RequestIV[:]...)
	buffer = append(buffer, request.RequestKey[:]...)
	buffer = append(buffer, request.ResponseHeader[:]...)
	buffer = append(buffer, request.Command)

	portBytes := make([]byte, 2)
	binary.BigEndian.PutUint16(portBytes, request.Address.Port)
	buffer = append(buffer, portBytes...)

	switch {
	case request.Address.IsIPv4():
		buffer = append(buffer, addrTypeIPv4)
		buffer = append(buffer, request.Address.IP...)
	case request.Address.IsIPv6():
		buffer = append(buffer, addrTypeIPv6)
		buffer = append(buffer, request.Address.IP...)
	case request.Address.IsDomain():
		buffer = append(buffer, addrTypeDomain)
		buffer = append(buffer, byte(len(request.Address.Domain)))
		buffer = append(buffer, []byte(request.Address.Domain)...)
	}

	paddingLength := blockSize - 1 - (len(buffer)-encryptionBegin)%blockSize
	if paddingLength == 0 {
		paddingLength = blockSize
	}
	paddingBuffer := make([]byte, paddingLength)
	_, err = rand.Read(paddingBuffer)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(paddingLength))
	buffer = append(buffer, paddingBuffer...)
	encryptionEnd := len(buffer)

	aesCipher, err := aes.NewCipher(request.UserId.Hash([]byte("PWD")))
	if err != nil {
		return err
	}
	aesMode := cipher.NewCBCEncrypter(aesCipher, make([]byte, blockSize))
	cWriter := v2io.NewCryptionWriter(aesMode, writer)

	_, err = writer.Write(buffer[0:encryptionBegin])
	if err != nil {
		return err
	}
	_, err = cWriter.Write(buffer[encryptionBegin:encryptionEnd])
	if err != nil {
		return err
	}

	return nil
}
示例#4
0
func (w *VMessRequestWriter) Write(writer io.Writer, request *VMessRequest) error {
	buffer := make([]byte, 0, 300)
	userHash, timeSec := request.UserId.TimeRangeHash(30)

	log.Debug("Writing userhash: %v", userHash)
	buffer = append(buffer, userHash...)

	encryptionBegin := len(buffer)

	randomLength := mrand.Intn(32) + 1
	randomContent := make([]byte, randomLength)
	_, err := rand.Read(randomContent)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(randomLength))
	buffer = append(buffer, randomContent...)

	buffer = append(buffer, request.Version)
	buffer = append(buffer, request.RequestIV[:]...)
	buffer = append(buffer, request.RequestKey[:]...)
	buffer = append(buffer, request.ResponseHeader[:]...)
	buffer = append(buffer, request.Command)

	portBytes := make([]byte, 2)
	binary.BigEndian.PutUint16(portBytes, request.Address.Port)
	buffer = append(buffer, portBytes...)

	switch {
	case request.Address.IsIPv4():
		buffer = append(buffer, addrTypeIPv4)
		buffer = append(buffer, request.Address.IP...)
	case request.Address.IsIPv6():
		buffer = append(buffer, addrTypeIPv6)
		buffer = append(buffer, request.Address.IP...)
	case request.Address.IsDomain():
		buffer = append(buffer, addrTypeDomain)
		buffer = append(buffer, byte(len(request.Address.Domain)))
		buffer = append(buffer, []byte(request.Address.Domain)...)
	}

	paddingLength := blockSize - 1 - (len(buffer)-encryptionBegin)%blockSize
	if paddingLength == 0 {
		paddingLength = blockSize
	}
	paddingBuffer := make([]byte, paddingLength)
	_, err = rand.Read(paddingBuffer)
	if err != nil {
		return err
	}
	buffer = append(buffer, byte(paddingLength))
	buffer = append(buffer, paddingBuffer...)
	encryptionEnd := len(buffer)

	aesCipher, err := aes.NewCipher(request.UserId.CmdKey())
	if err != nil {
		return err
	}
	aesStream := cipher.NewCFBEncrypter(aesCipher, core.TimestampHash(timeSec))
	cWriter := v2io.NewCryptionWriter(aesStream, writer)

	_, err = writer.Write(buffer[0:encryptionBegin])
	if err != nil {
		return err
	}
	_, err = cWriter.Write(buffer[encryptionBegin:encryptionEnd])
	if err != nil {
		return err
	}

	return nil
}