frame.go 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121
  1. package mux
  2. import (
  3. "errors"
  4. "v2ray.com/core/common/buf"
  5. "v2ray.com/core/common/net"
  6. "v2ray.com/core/common/serial"
  7. )
  8. type SessionStatus byte
  9. const (
  10. SessionStatusNew SessionStatus = 0x01
  11. SessionStatusKeep SessionStatus = 0x02
  12. SessionStatusEnd SessionStatus = 0x03
  13. )
  14. type TargetNetwork byte
  15. const (
  16. TargetNetworkTCP TargetNetwork = 0x01
  17. TargetnetworkUDP TargetNetwork = 0x02
  18. )
  19. type AddressType byte
  20. const (
  21. AddressTypeIPv4 AddressType = 0x01
  22. AddressTypeDomain AddressType = 0x02
  23. AddressTypeIPv6 AddressType = 0x03
  24. )
  25. type FrameMetadata struct {
  26. SessionId uint16
  27. SessionStatus SessionStatus
  28. Target net.Destination
  29. }
  30. func (f FrameMetadata) AsSupplier() buf.Supplier {
  31. return func(b []byte) (int, error) {
  32. b = serial.Uint16ToBytes(uint16(0), b) // place holder for length
  33. b = serial.Uint16ToBytes(f.SessionId, b)
  34. b = append(b, byte(f.SessionStatus), 0 /* reserved */)
  35. length := 4
  36. if f.SessionStatus == SessionStatusNew {
  37. switch f.Target.Network {
  38. case net.Network_TCP:
  39. b = append(b, byte(TargetNetworkTCP))
  40. case net.Network_UDP:
  41. b = append(b, byte(TargetnetworkUDP))
  42. }
  43. length++
  44. b = serial.Uint16ToBytes(f.Target.Port.Value(), b)
  45. length += 2
  46. addr := f.Target.Address
  47. switch addr.Family() {
  48. case net.AddressFamilyIPv4:
  49. b = append(b, byte(AddressTypeIPv4))
  50. b = append(b, addr.IP()...)
  51. length += 5
  52. case net.AddressFamilyIPv6:
  53. b = append(b, byte(AddressTypeIPv6))
  54. b = append(b, addr.IP()...)
  55. length += 17
  56. case net.AddressFamilyDomain:
  57. nDomain := len(addr.Domain())
  58. b = append(b, byte(nDomain))
  59. b = append(b, addr.Domain()...)
  60. length += nDomain + 1
  61. }
  62. }
  63. return length + 2, nil
  64. }
  65. }
  66. func ReadFrameFrom(b []byte) (*FrameMetadata, error) {
  67. if len(b) < 4 {
  68. return nil, errors.New("Proxyman|Mux: Insufficient buffer.")
  69. }
  70. f := &FrameMetadata{
  71. SessionId: serial.BytesToUint16(b[:2]),
  72. SessionStatus: SessionStatus(b[2]),
  73. }
  74. b = b[4:]
  75. if f.SessionStatus == SessionStatusNew {
  76. network := TargetNetwork(b[0])
  77. port := net.PortFromBytes(b[1:3])
  78. addrType := AddressType(b[3])
  79. b = b[4:]
  80. var addr net.Address
  81. switch addrType {
  82. case AddressTypeIPv4:
  83. addr = net.IPAddress(b[0:4])
  84. b = b[4:]
  85. case AddressTypeIPv6:
  86. addr = net.IPAddress(b[0:16])
  87. b = b[16:]
  88. case AddressTypeDomain:
  89. nDomain := int(b[0])
  90. addr = net.DomainAddress(string(b[1 : 1+nDomain]))
  91. b = b[nDomain+1:]
  92. }
  93. switch network {
  94. case TargetNetworkTCP:
  95. f.Target = net.TCPDestination(addr, port)
  96. case TargetnetworkUDP:
  97. f.Target = net.UDPDestination(addr, port)
  98. }
  99. }
  100. return f, nil
  101. }