add tunnel handler and connector

This commit is contained in:
ginuerzh
2023-10-15 15:39:25 +08:00
parent 033151a770
commit 497915f465
24 changed files with 1375 additions and 63 deletions

View File

@ -2,6 +2,8 @@ package relay
import (
"context"
"crypto/md5"
"encoding/hex"
"fmt"
"net"
"time"
@ -181,7 +183,7 @@ func (h *relayHandler) bindUDP(ctx context.Context, conn net.Conn, network, addr
return nil
}
func (h *relayHandler) handleBindTunnel(ctx context.Context, conn net.Conn, network string, tunnelID relay.TunnelID, log logger.Logger) (err error) {
func (h *relayHandler) handleBindTunnel(ctx context.Context, conn net.Conn, network, address string, tunnelID relay.TunnelID, log logger.Logger) (err error) {
resp := relay.Response{
Version: relay.Version1,
Status: relay.StatusOK,
@ -198,9 +200,11 @@ func (h *relayHandler) handleBindTunnel(ctx context.Context, conn net.Conn, netw
connectorID = relay.NewUDPConnectorID(uuid[:])
}
addr := ":0"
if h.ep != nil {
addr = h.ep.Addr().String()
addr := address
if host, port, _ := net.SplitHostPort(addr); host == "" {
v := md5.Sum([]byte(tunnelID.String()))
host = hex.EncodeToString(v[:8])
addr = net.JoinHostPort(host, port)
}
af := &relay.AddrFeature{}
err = af.ParseFrom(addr)
@ -221,10 +225,11 @@ func (h *relayHandler) handleBindTunnel(ctx context.Context, conn net.Conn, netw
}
h.pool.Add(tunnelID, NewConnector(connectorID, session))
log.Debugf("tunnel %s connector %s/%s established", tunnelID, connectorID, network)
if h.recorder.Recorder != nil {
h.recorder.Recorder.Record(ctx, tunnelID[:])
if h.md.ingress != nil {
h.md.ingress.Set(ctx, addr, tunnelID.String())
}
log.Debugf("%s/%s: tunnel=%s, connector=%s established", address, network, tunnelID, connectorID)
return
}

View File

@ -143,15 +143,12 @@ func (h *relayHandler) handleConnectTunnel(ctx context.Context, conn net.Conn, n
tid = parseTunnelID(ingress.Get(ctx, host))
}
// client is not an public entrypoint.
if h.md.entryPointID.IsZero() || !tunnelID.Equal(h.md.entryPointID) {
if !tid.Equal(tunnelID) && !h.md.directTunnel {
resp.Status = relay.StatusHostUnreachable
resp.WriteTo(conn)
err := fmt.Errorf("no route to host %s", host)
log.Error(err)
return err
}
if !tid.Equal(tunnelID) && !h.md.directTunnel {
resp.Status = relay.StatusHostUnreachable
resp.WriteTo(conn)
err := fmt.Errorf("no route to host %s", host)
log.Error(err)
return err
}
cc, _, err := getTunnelConn(network, h.pool, tid, 3, log)

View File

@ -13,12 +13,10 @@ import (
"github.com/go-gost/core/hop"
"github.com/go-gost/core/listener"
md "github.com/go-gost/core/metadata"
"github.com/go-gost/core/recorder"
"github.com/go-gost/core/service"
"github.com/go-gost/relay"
xnet "github.com/go-gost/x/internal/net"
auth_util "github.com/go-gost/x/internal/util/auth"
xrecorder "github.com/go-gost/x/recorder"
"github.com/go-gost/x/registry"
xservice "github.com/go-gost/x/service"
)
@ -35,13 +33,12 @@ func init() {
}
type relayHandler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
ep service.Service
pool *ConnectorPool
recorder recorder.RecorderObject
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
ep service.Service
pool *ConnectorPool
}
func NewHandler(opts ...handler.Option) handler.Handler {
@ -66,15 +63,6 @@ func (h *relayHandler) Init(md md.Metadata) (err error) {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
if opts := h.router.Options(); opts != nil {
for _, ro := range opts.Recorders {
if ro.Record == xrecorder.RecorderServiceHandlerRelayTunnelEndpoint {
h.recorder = ro
break
}
}
}
if err = h.initEntryPoint(); err != nil {
return
}
@ -248,7 +236,7 @@ func (h *relayHandler) Handle(ctx context.Context, conn net.Conn, opts ...handle
return h.handleConnect(ctx, conn, network, address, log)
case relay.CmdBind:
if !tunnelID.IsZero() {
return h.handleBindTunnel(ctx, conn, network, tunnelID, log)
return h.handleBindTunnel(ctx, conn, network, address, tunnelID, log)
}
defer conn.Close()

View File

@ -9,7 +9,6 @@ import (
"github.com/go-gost/core/logger"
mdata "github.com/go-gost/core/metadata"
mdutil "github.com/go-gost/core/metadata/util"
"github.com/go-gost/relay"
xingress "github.com/go-gost/x/ingress"
"github.com/go-gost/x/registry"
)
@ -22,7 +21,6 @@ type metadata struct {
hash string
directTunnel bool
entryPoint string
entryPointID relay.TunnelID
entryPointProxyProtocol int
ingress ingress.Ingress
}
@ -53,7 +51,6 @@ func (h *relayHandler) parseMetadata(md mdata.Metadata) (err error) {
h.md.directTunnel = mdutil.GetBool(md, "tunnel.direct")
h.md.entryPoint = mdutil.GetString(md, entryPoint)
h.md.entryPointID = parseTunnelID(mdutil.GetString(md, entryPointID))
h.md.entryPointProxyProtocol = mdutil.GetInt(md, entryPointProxyProtocol)
h.md.ingress = registry.IngressRegistry().Get(mdutil.GetString(md, "ingress"))