github.com/Uhtred009/v2ray-core-1@v4.31.2+incompatible/proxy/vmess/aead/authid.go (about)

     1  package aead
     2  
     3  import (
     4  	"bytes"
     5  	"crypto/aes"
     6  	"crypto/cipher"
     7  	rand3 "crypto/rand"
     8  	"encoding/binary"
     9  	"errors"
    10  	"hash/crc32"
    11  	"io"
    12  	"math"
    13  	"time"
    14  	"v2ray.com/core/common"
    15  	antiReplayWindow "v2ray.com/core/common/antireplay"
    16  )
    17  
    18  func CreateAuthID(cmdKey []byte, time int64) [16]byte {
    19  	buf := bytes.NewBuffer(nil)
    20  	common.Must(binary.Write(buf, binary.BigEndian, time))
    21  	var zero uint32
    22  	common.Must2(io.CopyN(buf, rand3.Reader, 4))
    23  	zero = crc32.ChecksumIEEE(buf.Bytes())
    24  	common.Must(binary.Write(buf, binary.BigEndian, zero))
    25  	aesBlock := NewCipherFromKey(cmdKey)
    26  	if buf.Len() != 16 {
    27  		panic("Size unexpected")
    28  	}
    29  	var result [16]byte
    30  	aesBlock.Encrypt(result[:], buf.Bytes())
    31  	return result
    32  }
    33  
    34  func NewCipherFromKey(cmdKey []byte) cipher.Block {
    35  	aesBlock, err := aes.NewCipher(KDF16(cmdKey, KDFSaltConst_AuthIDEncryptionKey))
    36  	if err != nil {
    37  		panic(err)
    38  	}
    39  	return aesBlock
    40  }
    41  
    42  type AuthIDDecoder struct {
    43  	s cipher.Block
    44  }
    45  
    46  func NewAuthIDDecoder(cmdKey []byte) *AuthIDDecoder {
    47  	return &AuthIDDecoder{NewCipherFromKey(cmdKey)}
    48  }
    49  
    50  func (aidd *AuthIDDecoder) Decode(data [16]byte) (int64, uint32, int32, []byte) {
    51  	aidd.s.Decrypt(data[:], data[:])
    52  	var t int64
    53  	var zero uint32
    54  	var rand int32
    55  	reader := bytes.NewReader(data[:])
    56  	common.Must(binary.Read(reader, binary.BigEndian, &t))
    57  	common.Must(binary.Read(reader, binary.BigEndian, &rand))
    58  	common.Must(binary.Read(reader, binary.BigEndian, &zero))
    59  	return t, zero, rand, data[:]
    60  }
    61  
    62  func NewAuthIDDecoderHolder() *AuthIDDecoderHolder {
    63  	return &AuthIDDecoderHolder{make(map[string]*AuthIDDecoderItem), antiReplayWindow.NewAntiReplayWindow(120)}
    64  }
    65  
    66  type AuthIDDecoderHolder struct {
    67  	aidhi map[string]*AuthIDDecoderItem
    68  	apw   *antiReplayWindow.AntiReplayWindow
    69  }
    70  
    71  type AuthIDDecoderItem struct {
    72  	dec    *AuthIDDecoder
    73  	ticket interface{}
    74  }
    75  
    76  func NewAuthIDDecoderItem(key [16]byte, ticket interface{}) *AuthIDDecoderItem {
    77  	return &AuthIDDecoderItem{
    78  		dec:    NewAuthIDDecoder(key[:]),
    79  		ticket: ticket,
    80  	}
    81  }
    82  
    83  func (a *AuthIDDecoderHolder) AddUser(key [16]byte, ticket interface{}) {
    84  	a.aidhi[string(key[:])] = NewAuthIDDecoderItem(key, ticket)
    85  }
    86  
    87  func (a *AuthIDDecoderHolder) RemoveUser(key [16]byte) {
    88  	delete(a.aidhi, string(key[:]))
    89  }
    90  
    91  func (a *AuthIDDecoderHolder) Match(AuthID [16]byte) (interface{}, error) {
    92  	for _, v := range a.aidhi {
    93  
    94  		t, z, r, d := v.dec.Decode(AuthID)
    95  		if z != crc32.ChecksumIEEE(d[:12]) {
    96  			continue
    97  		}
    98  
    99  		if t < 0 {
   100  			continue
   101  		}
   102  
   103  		if math.Abs(math.Abs(float64(t))-float64(time.Now().Unix())) > 120 {
   104  			continue
   105  		}
   106  
   107  		if !a.apw.Check(AuthID[:]) {
   108  			return nil, ErrReplay
   109  		}
   110  
   111  		_ = r
   112  
   113  		return v.ticket, nil
   114  
   115  	}
   116  	return nil, ErrNotFound
   117  }
   118  
   119  var ErrNotFound = errors.New("user do not exist")
   120  
   121  var ErrReplay = errors.New("replayed request")