add port range support for service

This commit is contained in:
ginuerzh
2024-07-08 22:38:21 +08:00
parent 96f4d7bf5c
commit c1d0887a9b
73 changed files with 1915 additions and 316 deletions

View File

@ -34,7 +34,6 @@ type dnsHandler struct {
hop hop.Hop
exchangers map[string]exchanger.Exchanger
cache *resolver_util.Cache
router *chain.Router
hostMapper hosts.HostMapper
md metadata
options handler.Options
@ -60,11 +59,7 @@ func (h *dnsHandler) Init(md md.Metadata) (err error) {
h.cache = resolver_util.NewCache().WithLogger(log)
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(log))
}
h.hostMapper = h.router.Options().HostMapper
h.hostMapper = h.options.Router.Options().HostMapper
if h.hop == nil {
var nodes []*chain.Node
@ -88,7 +83,7 @@ func (h *dnsHandler) Init(md md.Metadata) (err error) {
}
ex, err := exchanger.NewExchanger(
addr,
exchanger.RouterOption(h.router),
exchanger.RouterOption(h.options.Router),
exchanger.TimeoutOption(h.md.timeout),
exchanger.LoggerOption(log),
)
@ -102,7 +97,7 @@ func (h *dnsHandler) Init(md md.Metadata) (err error) {
if len(h.exchangers) == 0 {
ex, err := exchanger.NewExchanger(
defaultNameserver,
exchanger.RouterOption(h.router),
exchanger.RouterOption(h.options.Router),
exchanger.TimeoutOption(h.md.timeout),
exchanger.LoggerOption(log),
)

View File

@ -37,7 +37,6 @@ func init() {
type forwardHandler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
}
@ -58,11 +57,6 @@ func (h *forwardHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -157,7 +151,7 @@ func (h *forwardHandler) Handle(ctx context.Context, conn net.Conn, opts ...hand
log.Debugf("%s >> %s", conn.RemoteAddr(), addr)
cc, err := h.router.Dial(ctx, network, addr)
cc, err := h.options.Router.Dial(ctx, network, addr)
if err != nil {
log.Error(err)
// TODO: the router itself may be failed due to the failed node in the router,
@ -277,7 +271,7 @@ func (h *forwardHandler) handleHTTP(ctx context.Context, rw io.ReadWriter, remot
}
}
cc, err = h.router.Dial(ctx, "tcp", target.Addr)
cc, err = h.options.Router.Dial(ctx, "tcp", target.Addr)
if err != nil {
// TODO: the router itself may be failed due to the failed node in the router,
// the dead marker may be a wrong operation.

View File

@ -38,7 +38,6 @@ func init() {
type forwardHandler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
}
@ -59,11 +58,6 @@ func (h *forwardHandler) Init(md mdata.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -156,7 +150,7 @@ func (h *forwardHandler) Handle(ctx context.Context, conn net.Conn, opts ...hand
log.Debugf("%s >> %s", conn.RemoteAddr(), target.Addr)
cc, err := h.router.Dial(ctx, network, target.Addr)
cc, err := h.options.Router.Dial(ctx, network, target.Addr)
if err != nil {
log.Error(err)
// TODO: the router itself may be failed due to the failed node in the router,
@ -277,7 +271,7 @@ func (h *forwardHandler) handleHTTP(ctx context.Context, rw io.ReadWriter, remot
}
}
cc, err = h.router.Dial(ctx, "tcp", target.Addr)
cc, err = h.options.Router.Dial(ctx, "tcp", target.Addr)
if err != nil {
// TODO: the router itself may be failed due to the failed node in the router,
// the dead marker may be a wrong operation.

View File

@ -18,7 +18,6 @@ import (
"time"
"github.com/asaskevich/govalidator"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
traffic "github.com/go-gost/core/limiter/traffic"
"github.com/go-gost/core/logger"
@ -37,7 +36,6 @@ func init() {
}
type httpHandler struct {
router *chain.Router
md metadata
options handler.Options
stats *stats_util.HandlerStats
@ -61,11 +59,6 @@ func (h *httpHandler) Init(md md.Metadata) error {
return err
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
ctx, cancel := context.WithCancel(context.Background())
h.cancel = cancel
@ -215,7 +208,7 @@ func (h *httpHandler) handleRequest(ctx context.Context, conn net.Conn, req *htt
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: addr})
}
cc, err := h.router.Dial(ctx, network, addr)
cc, err := h.options.Router.Dial(ctx, network, addr)
if err != nil {
resp.StatusCode = http.StatusServiceUnavailable

View File

@ -51,7 +51,7 @@ func (h *httpHandler) handleUDP(ctx context.Context, conn net.Conn, log logger.L
}
// obtain a udp connection
c, err := h.router.Dial(ctx, "udp", "") // UDP association
c, err := h.options.Router.Dial(ctx, "udp", "") // UDP association
if err != nil {
log.Error(err)
return err

View File

@ -18,7 +18,6 @@ import (
"strings"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/limiter/traffic"
"github.com/go-gost/core/logger"
@ -38,7 +37,6 @@ func init() {
}
type http2Handler struct {
router *chain.Router
md metadata
options handler.Options
stats *stats_util.HandlerStats
@ -62,11 +60,6 @@ func (h *http2Handler) Init(md md.Metadata) error {
return err
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
ctx, cancel := context.WithCancel(context.Background())
h.cancel = cancel
@ -188,7 +181,7 @@ func (h *http2Handler) roundTrip(ctx context.Context, w http.ResponseWriter, req
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: addr})
}
cc, err := h.router.Dial(ctx, "tcp", addr)
cc, err := h.options.Router.Dial(ctx, "tcp", addr)
if err != nil {
log.Error(err)
w.WriteHeader(http.StatusServiceUnavailable)

View File

@ -24,7 +24,6 @@ func init() {
type http3Handler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
}
@ -45,11 +44,6 @@ func (h *http3Handler) Init(md md.Metadata) error {
return err
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return nil
}
@ -147,7 +141,7 @@ func (h *http3Handler) roundTrip(ctx context.Context, w http.ResponseWriter, req
TLSHandshakeTimeout: 10 * time.Second,
ExpectContinueTimeout: 1 * time.Second,
DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
conn, err := h.router.Dial(ctx, network, target.Addr)
conn, err := h.options.Router.Dial(ctx, network, target.Addr)
if err != nil {
log.Error(err)
// TODO: the router itself may be failed due to the failed node in the router,

View File

@ -15,7 +15,6 @@ import (
"time"
"github.com/go-gost/core/bypass"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/logger"
md "github.com/go-gost/core/metadata"
@ -32,7 +31,6 @@ func init() {
}
type redirectHandler struct {
router *chain.Router
md metadata
options handler.Options
}
@ -53,11 +51,6 @@ func (h *redirectHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -129,7 +122,7 @@ func (h *redirectHandler) Handle(ctx context.Context, conn net.Conn, opts ...han
return nil
}
cc, err := h.router.Dial(ctx, dstAddr.Network(), dstAddr.String())
cc, err := h.options.Router.Dial(ctx, dstAddr.Network(), dstAddr.String())
if err != nil {
log.Error(err)
return err
@ -170,13 +163,13 @@ func (h *redirectHandler) handleHTTP(ctx context.Context, rw io.ReadWriter, radd
return nil
}
cc, err := h.router.Dial(ctx, "tcp", host)
cc, err := h.options.Router.Dial(ctx, "tcp", host)
if err != nil {
log.Error(err)
}
if cc == nil {
cc, err = h.router.Dial(ctx, "tcp", dstAddr.String())
cc, err = h.options.Router.Dial(ctx, "tcp", dstAddr.String())
if err != nil {
log.Error(err)
return err
@ -245,14 +238,14 @@ func (h *redirectHandler) handleHTTPS(ctx context.Context, rw io.ReadWriter, rad
return nil
}
cc, err = h.router.Dial(ctx, "tcp", host)
cc, err = h.options.Router.Dial(ctx, "tcp", host)
if err != nil {
log.Error(err)
}
}
if cc == nil {
cc, err = h.router.Dial(ctx, "tcp", dstAddr.String())
cc, err = h.options.Router.Dial(ctx, "tcp", dstAddr.String())
if err != nil {
log.Error(err)
return err

View File

@ -6,7 +6,6 @@ import (
"net"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
md "github.com/go-gost/core/metadata"
netpkg "github.com/go-gost/x/internal/net"
@ -18,7 +17,6 @@ func init() {
}
type redirectHandler struct {
router *chain.Router
md metadata
options handler.Options
}
@ -39,11 +37,6 @@ func (h *redirectHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -80,7 +73,7 @@ func (h *redirectHandler) Handle(ctx context.Context, conn net.Conn, opts ...han
return nil
}
cc, err := h.router.Dial(ctx, dstAddr.Network(), dstAddr.String())
cc, err := h.options.Router.Dial(ctx, dstAddr.Network(), dstAddr.String())
if err != nil {
log.Error(err)
return err

View File

@ -66,7 +66,7 @@ func (h *relayHandler) handleConnect(ctx context.Context, conn net.Conn, network
case "serial":
cc, err = serial.OpenPort(serial.ParseConfigFromAddr(address))
default:
cc, err = h.router.Dial(ctx, network, address)
cc, err = h.options.Router.Dial(ctx, network, address)
}
if err != nil {
resp.Status = relay.StatusNetworkUnreachable

View File

@ -38,7 +38,7 @@ func (h *relayHandler) handleForward(ctx context.Context, conn net.Conn, network
log.Debugf("%s >> %s", conn.RemoteAddr(), target.Addr)
cc, err := h.router.Dial(ctx, network, target.Addr)
cc, err := h.options.Router.Dial(ctx, network, target.Addr)
if err != nil {
// TODO: the router itself may be failed due to the failed node in the router,
// the dead marker may be a wrong operation.

View File

@ -7,7 +7,6 @@ import (
"strconv"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/hop"
md "github.com/go-gost/core/metadata"
@ -30,7 +29,6 @@ func init() {
type relayHandler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
stats *stats_util.HandlerStats
@ -54,11 +52,6 @@ func (h *relayHandler) Init(md md.Metadata) (err error) {
return err
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
ctx, cancel := context.WithCancel(context.Background())
h.cancel = cancel

View File

@ -25,7 +25,6 @@ func init() {
type serialHandler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
recorder recorder.RecorderObject
@ -47,11 +46,7 @@ func (h *serialHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
if opts := h.router.Options(); opts != nil {
if opts := h.options.Router.Options(); opts != nil {
for _, ro := range opts.Recorders {
if ro.Record == xrecorder.RecorderServiceHandlerSerial {
h.recorder = ro
@ -97,7 +92,7 @@ func (h *serialHandler) Handle(ctx context.Context, conn net.Conn, opts ...handl
return h.forwardSerial(ctx, conn, target, log)
}
cc, err := h.router.Dial(ctx, "tcp", "@")
cc, err := h.options.Router.Dial(ctx, "tcp", "@")
if err != nil {
log.Error(err)
return err
@ -121,8 +116,8 @@ func (h *serialHandler) forwardSerial(ctx context.Context, conn net.Conn, target
cfg := serial.ParseConfigFromAddr(conn.LocalAddr().String())
cfg.Name = target.Addr
if opts := h.router.Options(); opts != nil && opts.Chain != nil {
port, err = h.router.Dial(ctx, "serial", serial.AddrFromConfig(cfg))
if opts := h.options.Router.Options(); opts != nil && opts.Chain != nil {
port, err = h.options.Router.Dial(ctx, "serial", serial.AddrFromConfig(cfg))
} else {
cfg.ReadTimeout = h.md.timeout
port, err = serial.OpenPort(cfg)

View File

@ -16,7 +16,6 @@ import (
"time"
"github.com/go-gost/core/bypass"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/logger"
md "github.com/go-gost/core/metadata"
@ -32,7 +31,6 @@ func init() {
}
type sniHandler struct {
router *chain.Router
md metadata
options handler.Options
}
@ -55,11 +53,6 @@ func (h *sniHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return nil
}
@ -128,7 +121,7 @@ func (h *sniHandler) handleHTTP(ctx context.Context, rw io.ReadWriter, raddr net
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: host})
}
cc, err := h.router.Dial(ctx, "tcp", host)
cc, err := h.options.Router.Dial(ctx, "tcp", host)
if err != nil {
log.Error(err)
return err
@ -196,7 +189,7 @@ func (h *sniHandler) handleHTTPS(ctx context.Context, rw io.ReadWriter, raddr ne
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: host})
}
cc, err := h.router.Dial(ctx, "tcp", host)
cc, err := h.options.Router.Dial(ctx, "tcp", host)
if err != nil {
log.Error(err)
return err

View File

@ -6,7 +6,6 @@ import (
"net"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/limiter/traffic"
"github.com/go-gost/core/logger"
@ -32,7 +31,6 @@ func init() {
}
type socks4Handler struct {
router *chain.Router
md metadata
options handler.Options
stats *stats_util.HandlerStats
@ -56,11 +54,6 @@ func (h *socks4Handler) Init(md md.Metadata) (err error) {
return err
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
ctx, cancel := context.WithCancel(context.Background())
h.cancel = cancel
@ -154,7 +147,7 @@ func (h *socks4Handler) handleConnect(ctx context.Context, conn net.Conn, req *g
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: addr})
}
cc, err := h.router.Dial(ctx, "tcp", addr)
cc, err := h.options.Router.Dial(ctx, "tcp", addr)
if err != nil {
resp := gosocks4.NewReply(gosocks4.Failed, nil)
log.Trace(resp)

View File

@ -35,7 +35,7 @@ func (h *socks5Handler) handleConnect(ctx context.Context, conn net.Conn, networ
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: address})
}
cc, err := h.router.Dial(ctx, network, address)
cc, err := h.options.Router.Dial(ctx, network, address)
if err != nil {
resp := gosocks5.NewReply(gosocks5.NetUnreachable, nil)
log.Trace(resp)

View File

@ -6,7 +6,6 @@ import (
"net"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
md "github.com/go-gost/core/metadata"
"github.com/go-gost/gosocks5"
@ -27,7 +26,6 @@ func init() {
type socks5Handler struct {
selector gosocks5.Selector
router *chain.Router
md metadata
options handler.Options
stats *stats_util.HandlerStats
@ -51,11 +49,6 @@ func (h *socks5Handler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
h.selector = &serverSelector{
Authenticator: h.options.Auther,
TLSConfig: h.options.TLSConfig,

View File

@ -59,7 +59,7 @@ func (h *socks5Handler) handleUDP(ctx context.Context, conn net.Conn, log logger
log.Debugf("bind on %s OK", cc.LocalAddr())
// obtain a udp connection
c, err := h.router.Dial(ctx, "udp", "") // UDP association
c, err := h.options.Router.Dial(ctx, "udp", "") // UDP association
if err != nil {
log.Error(err)
return err

View File

@ -37,7 +37,7 @@ func (h *socks5Handler) handleUDPTun(ctx context.Context, conn net.Conn, network
}
// obtain a udp connection
c, err := h.router.Dial(ctx, "udp", "") // UDP association
c, err := h.options.Router.Dial(ctx, "udp", "") // UDP association
if err != nil {
log.Error(err)
return err

View File

@ -6,7 +6,6 @@ import (
"net"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
md "github.com/go-gost/core/metadata"
"github.com/go-gost/gosocks5"
@ -23,7 +22,6 @@ func init() {
type ssHandler struct {
cipher core.Cipher
router *chain.Router
md metadata
options handler.Options
}
@ -52,11 +50,6 @@ func (h *ssHandler) Init(md md.Metadata) (err error) {
}
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -111,7 +104,7 @@ func (h *ssHandler) Handle(ctx context.Context, conn net.Conn, opts ...handler.H
ctx = ctxvalue.ContextWithHash(ctx, &ctxvalue.Hash{Source: addr.String()})
}
cc, err := h.router.Dial(ctx, "tcp", addr.String())
cc, err := h.options.Router.Dial(ctx, "tcp", addr.String())
if err != nil {
return err
}

View File

@ -6,7 +6,6 @@ import (
"net"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/common/bufpool"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/logger"
@ -23,7 +22,6 @@ func init() {
type ssuHandler struct {
cipher core.Cipher
router *chain.Router
md metadata
options handler.Options
}
@ -53,11 +51,6 @@ func (h *ssuHandler) Init(md md.Metadata) (err error) {
}
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -97,7 +90,7 @@ func (h *ssuHandler) Handle(ctx context.Context, conn net.Conn, opts ...handler.
}
// obtain a udp connection
c, err := h.router.Dial(ctx, "udp", "") // UDP association
c, err := h.options.Router.Dial(ctx, "udp", "") // UDP association
if err != nil {
log.Error(err)
return err

View File

@ -9,7 +9,6 @@ import (
"strconv"
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/logger"
md "github.com/go-gost/core/metadata"
@ -29,7 +28,6 @@ func init() {
}
type forwardHandler struct {
router *chain.Router
md metadata
options handler.Options
}
@ -50,11 +48,6 @@ func (h *forwardHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return nil
}
@ -97,7 +90,7 @@ func (h *forwardHandler) handleDirectForward(ctx context.Context, conn *sshd_uti
return nil
}
cc, err := h.router.Dial(ctx, "tcp", targetAddr)
cc, err := h.options.Router.Dial(ctx, "tcp", targetAddr)
if err != nil {
return err
}

View File

@ -33,7 +33,6 @@ type tapHandler struct {
routes sync.Map
exit chan struct{}
cipher core.Cipher
router *chain.Router
md metadata
options handler.Options
}
@ -64,11 +63,6 @@ func (h *tapHandler) Init(md md.Metadata) (err error) {
}
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -135,7 +129,7 @@ func (h *tapHandler) handleLoop(ctx context.Context, conn net.Conn, addr net.Add
var pc net.PacketConn
if addr != nil {
cc, err := h.router.Dial(ctx, addr.Network(), "")
cc, err := h.options.Router.Dial(ctx, addr.Network(), "")
if err != nil {
return err
}

View File

@ -35,7 +35,7 @@ func (h *tunHandler) handleClient(ctx context.Context, conn net.Conn, raddr stri
for {
err := func() error {
cc, err := h.router.Dial(ctx, "udp", raddr)
cc, err := h.options.Router.Dial(ctx, "udp", raddr)
if err != nil {
return err
}

View File

@ -29,7 +29,6 @@ func init() {
type tunHandler struct {
hop hop.Hop
routes sync.Map
router *chain.Router
md metadata
options handler.Options
}
@ -50,11 +49,6 @@ func (h *tunHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}

View File

@ -8,8 +8,8 @@ import (
"time"
"github.com/go-gost/core/chain"
"github.com/go-gost/core/hop"
"github.com/go-gost/core/handler"
"github.com/go-gost/core/hop"
"github.com/go-gost/core/logger"
md "github.com/go-gost/core/metadata"
xnet "github.com/go-gost/x/internal/net"
@ -22,7 +22,6 @@ func init() {
type unixHandler struct {
hop hop.Hop
router *chain.Router
md metadata
options handler.Options
}
@ -43,11 +42,6 @@ func (h *unixHandler) Init(md md.Metadata) (err error) {
return
}
h.router = h.options.Router
if h.router == nil {
h.router = chain.NewRouter(chain.LoggerRouterOption(h.options.Logger))
}
return
}
@ -80,7 +74,7 @@ func (h *unixHandler) Handle(ctx context.Context, conn net.Conn, opts ...handler
return h.forwardUnix(ctx, conn, target, log)
}
cc, err := h.router.Dial(ctx, "tcp", "@")
cc, err := h.options.Router.Dial(ctx, "tcp", "@")
if err != nil {
log.Error(err)
return err
@ -101,8 +95,8 @@ func (h *unixHandler) forwardUnix(ctx context.Context, conn net.Conn, target *ch
log.Debugf("%s >> %s", conn.LocalAddr(), target.Addr)
var cc io.ReadWriteCloser
if opts := h.router.Options(); opts != nil && opts.Chain != nil {
cc, err = h.router.Dial(ctx, "unix", target.Addr)
if opts := h.options.Router.Options(); opts != nil && opts.Chain != nil {
cc, err = h.options.Router.Dial(ctx, "unix", target.Addr)
} else {
cc, err = (&net.Dialer{}).DialContext(ctx, "unix", target.Addr)
}