Browse Source

Refactor: autonomize core package

pull/76/head
xjasonlyu 4 years ago
parent
commit
ae77a8a009
  1. 2
      constant/constant.go
  2. 2
      constant/metadata.go
  3. 12
      core/adapter.go
  4. 6
      core/handler.go
  5. 10
      core/stack/handler.go
  6. 6
      core/stack/stack.go
  7. 18
      core/stack/tcp.go
  8. 22
      core/stack/udp.go
  9. 9
      engine/tunnel.go
  10. 6
      proxy/base.go
  11. 8
      proxy/direct.go
  12. 12
      proxy/proxy.go
  13. 8
      proxy/shadowsocks.go
  14. 8
      proxy/socks5.go
  15. 16
      tunnel/statistic/tracker.go
  16. 16
      tunnel/tcp.go
  17. 10
      tunnel/tunnel.go
  18. 22
      tunnel/udp.go

2
constant/constant.go

@ -1,2 +0,0 @@
// Package constant provides global constants/variables of this project.
package constant

2
common/adapter/metadata.go → constant/metadata.go

@ -1,4 +1,4 @@
package adapter
package constant
import (
"bytes"

12
common/adapter/adapter.go → core/adapter.go

@ -1,12 +1,14 @@
package adapter
package core
import (
"net"
"gvisor.dev/gvisor/pkg/tcpip/stack"
)
type TCPConn interface {
net.Conn
Metadata() *Metadata
ID() *stack.TransportEndpointID
}
type UDPPacket interface {
@ -16,12 +18,12 @@ type UDPPacket interface {
// Drop call after packet is used, could release resources in this function.
Drop()
// ID returns the transport endpoint id of packet.
ID() *stack.TransportEndpointID
// LocalAddr returns the source IP/Port of packet.
LocalAddr() net.Addr
// Metadata returns the metadata of packet.
Metadata() *Metadata
// RemoteAddr returns the destination IP/Port of packet.
RemoteAddr() net.Addr

6
core/handler.go

@ -0,0 +1,6 @@
package core
type Handler interface {
Add(TCPConn)
AddPacket(UDPPacket)
}

10
core/stack/handler.go

@ -1,10 +0,0 @@
package stack
import (
"github.com/xjasonlyu/tun2socks/common/adapter"
)
type Handler interface {
Add(adapter.TCPConn)
AddPacket(adapter.UDPPacket)
}

6
core/stack/stack.go

@ -2,6 +2,8 @@
package stack
import (
"github.com/xjasonlyu/tun2socks/core"
"gvisor.dev/gvisor/pkg/tcpip"
"gvisor.dev/gvisor/pkg/tcpip/network/ipv4"
"gvisor.dev/gvisor/pkg/tcpip/network/ipv6"
@ -14,12 +16,12 @@ import (
type Stack struct {
*stack.Stack
handler Handler
handler core.Handler
nicID tcpip.NICID
}
// New allocates a new *Stack with given options.
func New(ep stack.LinkEndpoint, handler Handler, opts ...Option) (*Stack, error) {
func New(ep stack.LinkEndpoint, handler core.Handler, opts ...Option) (*Stack, error) {
s := &Stack{
Stack: stack.New(stack.Options{
NetworkProtocols: []stack.NetworkProtocolFactory{

18
core/stack/tcp.go

@ -5,10 +5,9 @@ import (
"net"
"time"
"github.com/xjasonlyu/tun2socks/common/adapter"
"gvisor.dev/gvisor/pkg/tcpip"
"gvisor.dev/gvisor/pkg/tcpip/adapters/gonet"
"gvisor.dev/gvisor/pkg/tcpip/stack"
"gvisor.dev/gvisor/pkg/tcpip/transport/tcp"
"gvisor.dev/gvisor/pkg/waiter"
)
@ -50,15 +49,8 @@ func withTCPHandler() Option {
conn := &tcpConn{
Conn: gonet.NewTCPConn(&wq, ep),
metadata: &adapter.Metadata{
Net: adapter.TCP,
SrcIP: net.IP(id.RemoteAddress),
SrcPort: id.RemotePort,
DstIP: net.IP(id.LocalAddress),
DstPort: id.LocalPort,
},
id: &id,
}
s.handler.Add(conn)
})
s.SetTransportProtocolHandler(tcp.ProtocolNumber, tcpForwarder.HandlePacket)
@ -83,9 +75,9 @@ func setKeepalive(ep tcpip.Endpoint) error {
type tcpConn struct {
net.Conn
metadata *adapter.Metadata
id *stack.TransportEndpointID
}
func (c *tcpConn) Metadata() *adapter.Metadata {
return c.metadata
func (c *tcpConn) ID() *stack.TransportEndpointID {
return c.id
}

22
core/stack/udp.go

@ -4,8 +4,6 @@ import (
"fmt"
"net"
"github.com/xjasonlyu/tun2socks/common/adapter"
"gvisor.dev/gvisor/pkg/tcpip"
"gvisor.dev/gvisor/pkg/tcpip/buffer"
"gvisor.dev/gvisor/pkg/tcpip/header"
@ -39,18 +37,11 @@ func withUDPHandler() Option {
packet := &udpPacket{
s: s,
id: id,
id: &id,
nicID: pkt.NICID,
netHdr: pkt.Network(),
netProto: pkt.NetworkProtocolNumber,
payload: pkt.Data.ToView(),
metadata: &adapter.Metadata{
Net: adapter.UDP,
SrcIP: net.IP(id.RemoteAddress),
SrcPort: id.RemotePort,
DstIP: net.IP(id.LocalAddress),
DstPort: id.LocalPort,
},
}
s.handler.AddPacket(packet)
@ -63,12 +54,11 @@ func withUDPHandler() Option {
type udpPacket struct {
s *Stack
id stack.TransportEndpointID
id *stack.TransportEndpointID
nicID tcpip.NICID
netHdr header.Network
netProto tcpip.NetworkProtocolNumber
payload []byte
metadata *adapter.Metadata
}
func (p *udpPacket) Data() []byte {
@ -79,12 +69,12 @@ func (p *udpPacket) Drop() {
/* Release */
}
func (p *udpPacket) LocalAddr() net.Addr {
return &net.UDPAddr{IP: net.IP(p.id.LocalAddress), Port: int(p.id.LocalPort)}
func (p *udpPacket) ID() *stack.TransportEndpointID {
return p.id
}
func (p *udpPacket) Metadata() *adapter.Metadata {
return p.metadata
func (p *udpPacket) LocalAddr() net.Addr {
return &net.UDPAddr{IP: net.IP(p.id.LocalAddress), Port: int(p.id.LocalPort)}
}
func (p *udpPacket) RemoteAddr() net.Addr {

9
engine/tunnel.go

@ -1,19 +1,18 @@
package engine
import (
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/core/stack"
"github.com/xjasonlyu/tun2socks/core"
"github.com/xjasonlyu/tun2socks/tunnel"
)
var _ stack.Handler = (*fakeTunnel)(nil)
var _ core.Handler = (*fakeTunnel)(nil)
type fakeTunnel struct{}
func (*fakeTunnel) Add(conn adapter.TCPConn) {
func (*fakeTunnel) Add(conn core.TCPConn) {
tunnel.Add(conn)
}
func (*fakeTunnel) AddPacket(packet adapter.UDPPacket) {
func (*fakeTunnel) AddPacket(packet core.UDPPacket) {
tunnel.AddPacket(packet)
}

6
proxy/base.go

@ -5,7 +5,7 @@ import (
"errors"
"net"
"github.com/xjasonlyu/tun2socks/common/adapter"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/proxy/proto"
)
@ -28,10 +28,10 @@ func (b *Base) Proto() proto.Proto {
return b.proto
}
func (b *Base) DialContext(context.Context, *adapter.Metadata) (net.Conn, error) {
func (b *Base) DialContext(context.Context, *M.Metadata) (net.Conn, error) {
return nil, errors.New("not supported")
}
func (b *Base) DialUDP(*adapter.Metadata) (net.PacketConn, error) {
func (b *Base) DialUDP(*M.Metadata) (net.PacketConn, error) {
return nil, errors.New("not supported")
}

8
proxy/direct.go

@ -4,8 +4,8 @@ import (
"context"
"net"
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/component/dialer"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/proxy/proto"
)
@ -23,7 +23,7 @@ func NewDirect() *Direct {
}
}
func (d *Direct) DialContext(ctx context.Context, metadata *adapter.Metadata) (net.Conn, error) {
func (d *Direct) DialContext(ctx context.Context, metadata *M.Metadata) (net.Conn, error) {
c, err := dialer.DialContext(ctx, "tcp", metadata.DestinationAddress())
if err != nil {
return nil, err
@ -32,7 +32,7 @@ func (d *Direct) DialContext(ctx context.Context, metadata *adapter.Metadata) (n
return c, nil
}
func (d *Direct) DialUDP(_ *adapter.Metadata) (net.PacketConn, error) {
func (d *Direct) DialUDP(*M.Metadata) (net.PacketConn, error) {
pc, err := dialer.ListenPacket("udp", "")
if err != nil {
return nil, err
@ -45,7 +45,7 @@ type directPacketConn struct {
}
func (pc *directPacketConn) WriteTo(b []byte, addr net.Addr) (int, error) {
if m, ok := addr.(*adapter.Metadata); ok && m.DstIP != nil {
if m, ok := addr.(*M.Metadata); ok && m.DstIP != nil {
return pc.PacketConn.WriteTo(b, m.UDPAddr())
}

12
proxy/proxy.go

@ -6,7 +6,7 @@ import (
"net"
"time"
"github.com/xjasonlyu/tun2socks/common/adapter"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/proxy/proto"
)
@ -19,8 +19,8 @@ var (
)
type Dialer interface {
DialContext(context.Context, *adapter.Metadata) (net.Conn, error)
DialUDP(*adapter.Metadata) (net.PacketConn, error)
DialContext(context.Context, *M.Metadata) (net.Conn, error)
DialUDP(*M.Metadata) (net.PacketConn, error)
}
type Proxy interface {
@ -35,18 +35,18 @@ func SetDialer(d Dialer) {
}
// Dial uses default Dialer to dial TCP.
func Dial(metadata *adapter.Metadata) (net.Conn, error) {
func Dial(metadata *M.Metadata) (net.Conn, error) {
ctx, cancel := context.WithTimeout(context.Background(), tcpConnectTimeout)
defer cancel()
return _defaultDialer.DialContext(ctx, metadata)
}
// DialContext uses default Dialer to dial TCP with context.
func DialContext(ctx context.Context, metadata *adapter.Metadata) (net.Conn, error) {
func DialContext(ctx context.Context, metadata *M.Metadata) (net.Conn, error) {
return _defaultDialer.DialContext(ctx, metadata)
}
// DialUDP uses default Dialer to dial UDP.
func DialUDP(metadata *adapter.Metadata) (net.PacketConn, error) {
func DialUDP(metadata *M.Metadata) (net.PacketConn, error) {
return _defaultDialer.DialUDP(metadata)
}

8
proxy/shadowsocks.go

@ -6,10 +6,10 @@ import (
"fmt"
"net"
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/component/dialer"
obfs "github.com/xjasonlyu/tun2socks/component/simple-obfs"
"github.com/xjasonlyu/tun2socks/component/socks5"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/proxy/proto"
"github.com/Dreamacro/go-shadowsocks2/core"
@ -43,7 +43,7 @@ func NewShadowsocks(addr, method, password, obfsMode, obfsHost string) (*Shadows
}, nil
}
func (ss *Shadowsocks) DialContext(ctx context.Context, metadata *adapter.Metadata) (c net.Conn, err error) {
func (ss *Shadowsocks) DialContext(ctx context.Context, metadata *M.Metadata) (c net.Conn, err error) {
c, err = dialer.DialContext(ctx, "tcp", ss.Addr())
if err != nil {
return nil, fmt.Errorf("connect to %s: %w", ss.Addr(), err)
@ -69,7 +69,7 @@ func (ss *Shadowsocks) DialContext(ctx context.Context, metadata *adapter.Metada
return
}
func (ss *Shadowsocks) DialUDP(_ *adapter.Metadata) (net.PacketConn, error) {
func (ss *Shadowsocks) DialUDP(*M.Metadata) (net.PacketConn, error) {
pc, err := dialer.ListenPacket("udp", "")
if err != nil {
return nil, fmt.Errorf("listen packet: %w", err)
@ -92,7 +92,7 @@ type ssPacketConn struct {
func (pc *ssPacketConn) WriteTo(b []byte, addr net.Addr) (n int, err error) {
var packet []byte
if m, ok := addr.(*adapter.Metadata); ok {
if m, ok := addr.(*M.Metadata); ok {
packet, err = socks5.EncodeUDPPacket(m.SerializesSocksAddr(), b)
} else {
packet, err = socks5.EncodeUDPPacket(socks5.ParseAddrToSocksAddr(addr), b)

8
proxy/socks5.go

@ -7,9 +7,9 @@ import (
"io/ioutil"
"net"
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/component/dialer"
"github.com/xjasonlyu/tun2socks/component/socks5"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/proxy/proto"
)
@ -33,7 +33,7 @@ func NewSocks5(addr, user, pass string) (*Socks5, error) {
}, nil
}
func (ss *Socks5) DialContext(ctx context.Context, metadata *adapter.Metadata) (c net.Conn, err error) {
func (ss *Socks5) DialContext(ctx context.Context, metadata *M.Metadata) (c net.Conn, err error) {
c, err = dialer.DialContext(ctx, "tcp", ss.Addr())
if err != nil {
return nil, fmt.Errorf("connect to %s: %w", ss.Addr(), err)
@ -58,7 +58,7 @@ func (ss *Socks5) DialContext(ctx context.Context, metadata *adapter.Metadata) (
return
}
func (ss *Socks5) DialUDP(_ *adapter.Metadata) (_ net.PacketConn, err error) {
func (ss *Socks5) DialUDP(*M.Metadata) (_ net.PacketConn, err error) {
ctx, cancel := context.WithTimeout(context.Background(), tcpConnectTimeout)
defer cancel()
@ -132,7 +132,7 @@ type socksPacketConn struct {
func (pc *socksPacketConn) WriteTo(b []byte, addr net.Addr) (n int, err error) {
var packet []byte
if m, ok := addr.(*adapter.Metadata); ok {
if m, ok := addr.(*M.Metadata); ok {
packet, err = socks5.EncodeUDPPacket(m.SerializesSocksAddr(), b)
} else {
packet, err = socks5.EncodeUDPPacket(socks5.ParseAddrToSocksAddr(addr), b)

16
tunnel/statistic/tracker.go

@ -4,7 +4,7 @@ import (
"net"
"time"
"github.com/xjasonlyu/tun2socks/common/adapter"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/gofrs/uuid"
"go.uber.org/atomic"
@ -16,11 +16,11 @@ type tracker interface {
}
type trackerInfo struct {
Start time.Time `json:"start"`
UUID uuid.UUID `json:"id"`
Metadata *adapter.Metadata `json:"metadata"`
UploadTotal *atomic.Int64 `json:"upload"`
DownloadTotal *atomic.Int64 `json:"download"`
Start time.Time `json:"start"`
UUID uuid.UUID `json:"id"`
Metadata *M.Metadata `json:"metadata"`
UploadTotal *atomic.Int64 `json:"upload"`
DownloadTotal *atomic.Int64 `json:"download"`
}
type tcpTracker struct {
@ -30,7 +30,7 @@ type tcpTracker struct {
manager *Manager
}
func NewTCPTracker(conn net.Conn, metadata *adapter.Metadata, manager *Manager) *tcpTracker {
func NewTCPTracker(conn net.Conn, metadata *M.Metadata, manager *Manager) *tcpTracker {
id, _ := uuid.NewV4()
tt := &tcpTracker{
@ -81,7 +81,7 @@ type udpTracker struct {
manager *Manager
}
func NewUDPTracker(conn net.PacketConn, metadata *adapter.Metadata, manager *Manager) *udpTracker {
func NewUDPTracker(conn net.PacketConn, metadata *M.Metadata, manager *Manager) *udpTracker {
id, _ := uuid.NewV4()
ut := &udpTracker{

16
tunnel/tcp.go

@ -7,8 +7,9 @@ import (
"sync"
"time"
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/common/pool"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/core"
"github.com/xjasonlyu/tun2socks/log"
"github.com/xjasonlyu/tun2socks/proxy"
"github.com/xjasonlyu/tun2socks/tunnel/statistic"
@ -18,14 +19,21 @@ const (
tcpWaitTimeout = 5 * time.Second
)
func newTCPTracker(conn net.Conn, metadata *adapter.Metadata) net.Conn {
func newTCPTracker(conn net.Conn, metadata *M.Metadata) net.Conn {
return statistic.NewTCPTracker(conn, metadata, statistic.DefaultManager)
}
func handleTCP(localConn adapter.TCPConn) {
func handleTCP(localConn core.TCPConn) {
defer localConn.Close()
metadata := localConn.Metadata()
id := localConn.ID()
metadata := &M.Metadata{
Net: M.TCP,
SrcIP: net.IP(id.RemoteAddress),
SrcPort: id.RemotePort,
DstIP: net.IP(id.LocalAddress),
DstPort: id.LocalPort,
}
if !metadata.Valid() {
log.Warnf("[Metadata] not valid: %#v", metadata)
return

10
tunnel/tunnel.go

@ -3,7 +3,7 @@ package tunnel
import (
"runtime"
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/core"
"github.com/xjasonlyu/tun2socks/log"
)
@ -15,8 +15,8 @@ const (
)
var (
tcpQueue = make(chan adapter.TCPConn) /* unbuffered */
udpQueue = make(chan adapter.UDPPacket, maxUDPQueueSize)
tcpQueue = make(chan core.TCPConn) /* unbuffered */
udpQueue = make(chan core.UDPPacket, maxUDPQueueSize)
numUDPWorkers = max(runtime.NumCPU(), 4 /* at least 4 workers */)
)
@ -25,12 +25,12 @@ func init() {
}
// Add adds tcpConn to tcpQueue.
func Add(conn adapter.TCPConn) {
func Add(conn core.TCPConn) {
tcpQueue <- conn
}
// AddPacket adds udpPacket to udpQueue.
func AddPacket(packet adapter.UDPPacket) {
func AddPacket(packet core.UDPPacket) {
select {
case udpQueue <- packet:
default:

22
tunnel/udp.go

@ -7,9 +7,10 @@ import (
"strconv"
"time"
"github.com/xjasonlyu/tun2socks/common/adapter"
"github.com/xjasonlyu/tun2socks/common/pool"
"github.com/xjasonlyu/tun2socks/component/nat"
M "github.com/xjasonlyu/tun2socks/constant"
"github.com/xjasonlyu/tun2socks/core"
"github.com/xjasonlyu/tun2socks/log"
"github.com/xjasonlyu/tun2socks/proxy"
"github.com/xjasonlyu/tun2socks/tunnel/statistic"
@ -25,18 +26,25 @@ var (
natTable = nat.NewTable()
)
func newUDPTracker(conn net.PacketConn, metadata *adapter.Metadata) net.PacketConn {
func newUDPTracker(conn net.PacketConn, metadata *M.Metadata) net.PacketConn {
return statistic.NewUDPTracker(conn, metadata, statistic.DefaultManager)
}
func handleUDP(packet adapter.UDPPacket) {
metadata := packet.Metadata()
func handleUDP(packet core.UDPPacket) {
id := packet.ID()
metadata := &M.Metadata{
Net: M.UDP,
SrcIP: net.IP(id.RemoteAddress),
SrcPort: id.RemotePort,
DstIP: net.IP(id.LocalAddress),
DstPort: id.LocalPort,
}
if !metadata.Valid() {
log.Warnf("[Metadata] not valid: %#v", metadata)
return
}
generateNATKey := func(m *adapter.Metadata) string {
generateNATKey := func(m *M.Metadata) string {
return m.SourceAddress() /* Full Cone NAT Key */
}
key := generateNATKey(metadata)
@ -101,7 +109,7 @@ func handleUDP(packet adapter.UDPPacket) {
}()
}
func handleUDPToRemote(packet adapter.UDPPacket, pc net.PacketConn, remote net.Addr, drop bool) {
func handleUDPToRemote(packet core.UDPPacket, pc net.PacketConn, remote net.Addr, drop bool) {
defer func() {
if drop {
packet.Drop()
@ -115,7 +123,7 @@ func handleUDPToRemote(packet adapter.UDPPacket, pc net.PacketConn, remote net.A
log.Infof("[UDP] %s --> %s", packet.RemoteAddr(), remote)
}
func handleUDPToLocal(packet adapter.UDPPacket, pc net.PacketConn, timeout time.Duration) {
func handleUDPToLocal(packet core.UDPPacket, pc net.PacketConn, timeout time.Duration) {
buf := pool.Get(pool.MaxSegmentSize)
defer pool.Put(buf)

Loading…
Cancel
Save