freedom.go 1.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758
  1. package freedom
  2. import (
  3. "net"
  4. "github.com/v2ray/v2ray-core"
  5. "github.com/v2ray/v2ray-core/common/log"
  6. v2net "github.com/v2ray/v2ray-core/common/net"
  7. )
  8. type FreedomConnection struct {
  9. dest *v2net.Destination
  10. }
  11. func NewFreedomConnection(dest *v2net.Destination) *FreedomConnection {
  12. return &FreedomConnection{
  13. dest: dest,
  14. }
  15. }
  16. func (vconn *FreedomConnection) Start(ray core.OutboundRay) error {
  17. input := ray.OutboundInput()
  18. output := ray.OutboundOutput()
  19. conn, err := net.Dial(vconn.dest.Network(), vconn.dest.Address().String())
  20. log.Info("Freedom: Opening connection to %s", vconn.dest.String())
  21. if err != nil {
  22. close(output)
  23. return log.Error("Freedom: Failed to open connection: %s : %v", vconn.dest.String(), err)
  24. }
  25. readFinish := make(chan bool)
  26. writeFinish := make(chan bool)
  27. go vconn.DumpInput(conn, input, writeFinish)
  28. go vconn.DumpOutput(conn, output, readFinish)
  29. go vconn.CloseConn(conn, readFinish, writeFinish)
  30. return nil
  31. }
  32. func (vconn *FreedomConnection) DumpInput(conn net.Conn, input <-chan []byte, finish chan<- bool) {
  33. v2net.ChanToWriter(conn, input)
  34. finish <- true
  35. }
  36. func (vconn *FreedomConnection) DumpOutput(conn net.Conn, output chan<- []byte, finish chan<- bool) {
  37. v2net.ReaderToChan(output, conn)
  38. close(output)
  39. finish <- true
  40. }
  41. func (vconn *FreedomConnection) CloseConn(conn net.Conn, readFinish <-chan bool, writeFinish <-chan bool) {
  42. <-writeFinish
  43. if tcpConn, ok := conn.(*net.TCPConn); ok {
  44. tcpConn.CloseWrite()
  45. }
  46. <-readFinish
  47. conn.Close()
  48. }