transport_test.go 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430
  1. package scenarios
  2. import (
  3. "crypto/rand"
  4. "os"
  5. "runtime"
  6. "sync"
  7. "testing"
  8. "time"
  9. "v2ray.com/core/transport/internet/headers/wechat"
  10. "v2ray.com/core"
  11. "v2ray.com/core/app/log"
  12. "v2ray.com/core/app/proxyman"
  13. "v2ray.com/core/common/compare"
  14. clog "v2ray.com/core/common/log"
  15. "v2ray.com/core/common/net"
  16. "v2ray.com/core/common/protocol"
  17. "v2ray.com/core/common/serial"
  18. "v2ray.com/core/common/uuid"
  19. "v2ray.com/core/proxy/dokodemo"
  20. "v2ray.com/core/proxy/freedom"
  21. "v2ray.com/core/proxy/vmess"
  22. "v2ray.com/core/proxy/vmess/inbound"
  23. "v2ray.com/core/proxy/vmess/outbound"
  24. "v2ray.com/core/testing/servers/tcp"
  25. "v2ray.com/core/transport/internet"
  26. "v2ray.com/core/transport/internet/domainsocket"
  27. "v2ray.com/core/transport/internet/headers/http"
  28. "v2ray.com/core/transport/internet/quic"
  29. tcptransport "v2ray.com/core/transport/internet/tcp"
  30. . "v2ray.com/ext/assert"
  31. )
  32. func TestHttpConnectionHeader(t *testing.T) {
  33. assert := With(t)
  34. tcpServer := tcp.Server{
  35. MsgProcessor: xor,
  36. }
  37. dest, err := tcpServer.Start()
  38. assert(err, IsNil)
  39. defer tcpServer.Close()
  40. userID := protocol.NewID(uuid.New())
  41. serverPort := tcp.PickPort()
  42. serverConfig := &core.Config{
  43. Inbound: []*core.InboundHandlerConfig{
  44. {
  45. ReceiverSettings: serial.ToTypedMessage(&proxyman.ReceiverConfig{
  46. PortRange: net.SinglePortRange(serverPort),
  47. Listen: net.NewIPOrDomain(net.LocalHostIP),
  48. StreamSettings: &internet.StreamConfig{
  49. TransportSettings: []*internet.TransportConfig{
  50. {
  51. Protocol: internet.TransportProtocol_TCP,
  52. Settings: serial.ToTypedMessage(&tcptransport.Config{
  53. HeaderSettings: serial.ToTypedMessage(&http.Config{}),
  54. }),
  55. },
  56. },
  57. },
  58. }),
  59. ProxySettings: serial.ToTypedMessage(&inbound.Config{
  60. User: []*protocol.User{
  61. {
  62. Account: serial.ToTypedMessage(&vmess.Account{
  63. Id: userID.String(),
  64. }),
  65. },
  66. },
  67. }),
  68. },
  69. },
  70. Outbound: []*core.OutboundHandlerConfig{
  71. {
  72. ProxySettings: serial.ToTypedMessage(&freedom.Config{}),
  73. },
  74. },
  75. }
  76. clientPort := tcp.PickPort()
  77. clientConfig := &core.Config{
  78. Inbound: []*core.InboundHandlerConfig{
  79. {
  80. ReceiverSettings: serial.ToTypedMessage(&proxyman.ReceiverConfig{
  81. PortRange: net.SinglePortRange(clientPort),
  82. Listen: net.NewIPOrDomain(net.LocalHostIP),
  83. }),
  84. ProxySettings: serial.ToTypedMessage(&dokodemo.Config{
  85. Address: net.NewIPOrDomain(dest.Address),
  86. Port: uint32(dest.Port),
  87. NetworkList: &net.NetworkList{
  88. Network: []net.Network{net.Network_TCP},
  89. },
  90. }),
  91. },
  92. },
  93. Outbound: []*core.OutboundHandlerConfig{
  94. {
  95. ProxySettings: serial.ToTypedMessage(&outbound.Config{
  96. Receiver: []*protocol.ServerEndpoint{
  97. {
  98. Address: net.NewIPOrDomain(net.LocalHostIP),
  99. Port: uint32(serverPort),
  100. User: []*protocol.User{
  101. {
  102. Account: serial.ToTypedMessage(&vmess.Account{
  103. Id: userID.String(),
  104. }),
  105. },
  106. },
  107. },
  108. },
  109. }),
  110. SenderSettings: serial.ToTypedMessage(&proxyman.SenderConfig{
  111. StreamSettings: &internet.StreamConfig{
  112. TransportSettings: []*internet.TransportConfig{
  113. {
  114. Protocol: internet.TransportProtocol_TCP,
  115. Settings: serial.ToTypedMessage(&tcptransport.Config{
  116. HeaderSettings: serial.ToTypedMessage(&http.Config{}),
  117. }),
  118. },
  119. },
  120. },
  121. }),
  122. },
  123. },
  124. }
  125. servers, err := InitializeServerConfigs(serverConfig, clientConfig)
  126. assert(err, IsNil)
  127. conn, err := net.DialTCP("tcp", nil, &net.TCPAddr{
  128. IP: []byte{127, 0, 0, 1},
  129. Port: int(clientPort),
  130. })
  131. assert(err, IsNil)
  132. payload := "dokodemo request."
  133. nBytes, err := conn.Write([]byte(payload))
  134. assert(err, IsNil)
  135. assert(nBytes, Equals, len(payload))
  136. response := readFrom(conn, time.Second*2, len(payload))
  137. assert(response, Equals, xor([]byte(payload)))
  138. assert(conn.Close(), IsNil)
  139. CloseAllServers(servers)
  140. }
  141. func TestDomainSocket(t *testing.T) {
  142. if runtime.GOOS == "windows" {
  143. t.Skip("Not supported on windows")
  144. return
  145. }
  146. assert := With(t)
  147. tcpServer := tcp.Server{
  148. MsgProcessor: xor,
  149. }
  150. dest, err := tcpServer.Start()
  151. assert(err, IsNil)
  152. defer tcpServer.Close()
  153. const dsPath = "/tmp/ds_scenario"
  154. os.Remove(dsPath)
  155. userID := protocol.NewID(uuid.New())
  156. serverPort := tcp.PickPort()
  157. serverConfig := &core.Config{
  158. Inbound: []*core.InboundHandlerConfig{
  159. {
  160. ReceiverSettings: serial.ToTypedMessage(&proxyman.ReceiverConfig{
  161. PortRange: net.SinglePortRange(serverPort),
  162. Listen: net.NewIPOrDomain(net.LocalHostIP),
  163. StreamSettings: &internet.StreamConfig{
  164. Protocol: internet.TransportProtocol_DomainSocket,
  165. TransportSettings: []*internet.TransportConfig{
  166. {
  167. Protocol: internet.TransportProtocol_DomainSocket,
  168. Settings: serial.ToTypedMessage(&domainsocket.Config{
  169. Path: dsPath,
  170. }),
  171. },
  172. },
  173. },
  174. }),
  175. ProxySettings: serial.ToTypedMessage(&inbound.Config{
  176. User: []*protocol.User{
  177. {
  178. Account: serial.ToTypedMessage(&vmess.Account{
  179. Id: userID.String(),
  180. }),
  181. },
  182. },
  183. }),
  184. },
  185. },
  186. Outbound: []*core.OutboundHandlerConfig{
  187. {
  188. ProxySettings: serial.ToTypedMessage(&freedom.Config{}),
  189. },
  190. },
  191. }
  192. clientPort := tcp.PickPort()
  193. clientConfig := &core.Config{
  194. Inbound: []*core.InboundHandlerConfig{
  195. {
  196. ReceiverSettings: serial.ToTypedMessage(&proxyman.ReceiverConfig{
  197. PortRange: net.SinglePortRange(clientPort),
  198. Listen: net.NewIPOrDomain(net.LocalHostIP),
  199. }),
  200. ProxySettings: serial.ToTypedMessage(&dokodemo.Config{
  201. Address: net.NewIPOrDomain(dest.Address),
  202. Port: uint32(dest.Port),
  203. NetworkList: &net.NetworkList{
  204. Network: []net.Network{net.Network_TCP},
  205. },
  206. }),
  207. },
  208. },
  209. Outbound: []*core.OutboundHandlerConfig{
  210. {
  211. ProxySettings: serial.ToTypedMessage(&outbound.Config{
  212. Receiver: []*protocol.ServerEndpoint{
  213. {
  214. Address: net.NewIPOrDomain(net.LocalHostIP),
  215. Port: uint32(serverPort),
  216. User: []*protocol.User{
  217. {
  218. Account: serial.ToTypedMessage(&vmess.Account{
  219. Id: userID.String(),
  220. }),
  221. },
  222. },
  223. },
  224. },
  225. }),
  226. SenderSettings: serial.ToTypedMessage(&proxyman.SenderConfig{
  227. StreamSettings: &internet.StreamConfig{
  228. Protocol: internet.TransportProtocol_DomainSocket,
  229. TransportSettings: []*internet.TransportConfig{
  230. {
  231. Protocol: internet.TransportProtocol_DomainSocket,
  232. Settings: serial.ToTypedMessage(&domainsocket.Config{
  233. Path: dsPath,
  234. }),
  235. },
  236. },
  237. },
  238. }),
  239. },
  240. },
  241. }
  242. servers, err := InitializeServerConfigs(serverConfig, clientConfig)
  243. assert(err, IsNil)
  244. conn, err := net.DialTCP("tcp", nil, &net.TCPAddr{
  245. IP: []byte{127, 0, 0, 1},
  246. Port: int(clientPort),
  247. })
  248. assert(err, IsNil)
  249. payload := "dokodemo request."
  250. nBytes, err := conn.Write([]byte(payload))
  251. assert(err, IsNil)
  252. assert(nBytes, Equals, len(payload))
  253. response := readFrom(conn, time.Second*2, len(payload))
  254. assert(response, Equals, xor([]byte(payload)))
  255. assert(conn.Close(), IsNil)
  256. CloseAllServers(servers)
  257. }
  258. func TestVMessQuic(t *testing.T) {
  259. assert := With(t)
  260. tcpServer := tcp.Server{
  261. MsgProcessor: xor,
  262. }
  263. dest, err := tcpServer.Start()
  264. assert(err, IsNil)
  265. defer tcpServer.Close()
  266. userID := protocol.NewID(uuid.New())
  267. serverPort := tcp.PickPort()
  268. serverConfig := &core.Config{
  269. App: []*serial.TypedMessage{
  270. serial.ToTypedMessage(&log.Config{
  271. ErrorLogLevel: clog.Severity_Debug,
  272. ErrorLogType: log.LogType_Console,
  273. }),
  274. },
  275. Inbound: []*core.InboundHandlerConfig{
  276. {
  277. ReceiverSettings: serial.ToTypedMessage(&proxyman.ReceiverConfig{
  278. PortRange: net.SinglePortRange(serverPort),
  279. Listen: net.NewIPOrDomain(net.LocalHostIP),
  280. StreamSettings: &internet.StreamConfig{
  281. ProtocolName: "quic",
  282. TransportSettings: []*internet.TransportConfig{
  283. {
  284. ProtocolName: "quic",
  285. Settings: serial.ToTypedMessage(&quic.Config{
  286. Header: serial.ToTypedMessage(&wechat.VideoConfig{}),
  287. }),
  288. },
  289. },
  290. },
  291. }),
  292. ProxySettings: serial.ToTypedMessage(&inbound.Config{
  293. User: []*protocol.User{
  294. {
  295. Account: serial.ToTypedMessage(&vmess.Account{
  296. Id: userID.String(),
  297. AlterId: 64,
  298. }),
  299. },
  300. },
  301. }),
  302. },
  303. },
  304. Outbound: []*core.OutboundHandlerConfig{
  305. {
  306. ProxySettings: serial.ToTypedMessage(&freedom.Config{}),
  307. },
  308. },
  309. }
  310. clientPort := tcp.PickPort()
  311. clientConfig := &core.Config{
  312. App: []*serial.TypedMessage{
  313. serial.ToTypedMessage(&log.Config{
  314. ErrorLogLevel: clog.Severity_Debug,
  315. ErrorLogType: log.LogType_Console,
  316. }),
  317. },
  318. Inbound: []*core.InboundHandlerConfig{
  319. {
  320. ReceiverSettings: serial.ToTypedMessage(&proxyman.ReceiverConfig{
  321. PortRange: net.SinglePortRange(clientPort),
  322. Listen: net.NewIPOrDomain(net.LocalHostIP),
  323. }),
  324. ProxySettings: serial.ToTypedMessage(&dokodemo.Config{
  325. Address: net.NewIPOrDomain(dest.Address),
  326. Port: uint32(dest.Port),
  327. NetworkList: &net.NetworkList{
  328. Network: []net.Network{net.Network_TCP},
  329. },
  330. }),
  331. },
  332. },
  333. Outbound: []*core.OutboundHandlerConfig{
  334. {
  335. SenderSettings: serial.ToTypedMessage(&proxyman.SenderConfig{
  336. StreamSettings: &internet.StreamConfig{
  337. ProtocolName: "quic",
  338. TransportSettings: []*internet.TransportConfig{
  339. {
  340. ProtocolName: "quic",
  341. Settings: serial.ToTypedMessage(&quic.Config{
  342. Header: serial.ToTypedMessage(&wechat.VideoConfig{}),
  343. }),
  344. },
  345. },
  346. },
  347. }),
  348. ProxySettings: serial.ToTypedMessage(&outbound.Config{
  349. Receiver: []*protocol.ServerEndpoint{
  350. {
  351. Address: net.NewIPOrDomain(net.LocalHostIP),
  352. Port: uint32(serverPort),
  353. User: []*protocol.User{
  354. {
  355. Account: serial.ToTypedMessage(&vmess.Account{
  356. Id: userID.String(),
  357. AlterId: 64,
  358. SecuritySettings: &protocol.SecurityConfig{
  359. Type: protocol.SecurityType_AES128_GCM,
  360. },
  361. }),
  362. },
  363. },
  364. },
  365. },
  366. }),
  367. },
  368. },
  369. }
  370. servers, err := InitializeServerConfigs(serverConfig, clientConfig)
  371. if err != nil {
  372. t.Fatal("Failed to initialize all servers: ", err.Error())
  373. }
  374. defer CloseAllServers(servers)
  375. var wg sync.WaitGroup
  376. for i := 0; i < 10; i++ {
  377. wg.Add(1)
  378. go func() {
  379. defer wg.Done()
  380. conn, err := net.DialTCP("tcp", nil, &net.TCPAddr{
  381. IP: []byte{127, 0, 0, 1},
  382. Port: int(clientPort),
  383. })
  384. assert(err, IsNil)
  385. defer conn.Close() // nolint: errcheck
  386. payload := make([]byte, 10240*1024)
  387. rand.Read(payload)
  388. nBytes, err := conn.Write([]byte(payload))
  389. assert(err, IsNil)
  390. assert(nBytes, Equals, len(payload))
  391. response := readFrom(conn, time.Second*40, 10240*1024)
  392. if err := compare.BytesEqualWithDetail(response, xor([]byte(payload))); err != nil {
  393. t.Error(err)
  394. }
  395. }()
  396. }
  397. wg.Wait()
  398. }