ssh: reuse underlying connection (#251)

This commit is contained in:
nadoo 2021-04-20 15:28:52 +08:00
parent 2a7eed7667
commit ddfcaae49c
15 changed files with 46 additions and 24 deletions

2
go.mod
View File

@ -18,7 +18,7 @@ require (
github.com/xtaci/kcp-go/v5 v5.6.1
golang.org/x/crypto v0.0.0-20210415154028-4f45737414dc
golang.org/x/net v0.0.0-20210415231046-e915ea6b2b7d // indirect
golang.org/x/sys v0.0.0-20210415045647-66c3f260301c // indirect
golang.org/x/sys v0.0.0-20210419170143-37df388d1f33 // indirect
)
// Replace dependency modules with local developing copy

4
go.sum
View File

@ -154,8 +154,8 @@ golang.org/x/sys v0.0.0-20201101102859-da207088b7d1/go.mod h1:h1NjWce9XRLGQEsW7w
golang.org/x/sys v0.0.0-20201112073958-5cba982894dd/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210330210617-4fbd30eecc44/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210415045647-66c3f260301c h1:6L+uOeS3OQt/f4eFHXZcTxeZrGCuz+CLElgEBjbcTA4=
golang.org/x/sys v0.0.0-20210415045647-66c3f260301c/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210419170143-37df388d1f33 h1:zah5VTTvBlVRELjcDwGLLaWRHZJQsBtplweVYCii0KM=
golang.org/x/sys v0.0.0-20210419170143-37df388d1f33/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1 h1:v+OssWQX+hTHEmOBgwxdZxK4zHq3yOs8F9J7mk0PY8E=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=

View File

@ -53,6 +53,10 @@ func DialerFromURL(s string, dialer Dialer) (Dialer, error) {
return nil, errors.New("DialerFromURL: dialer cannot be nil")
}
if !strings.Contains(s, "://") {
s = s + "://"
}
scheme := s[:strings.Index(s, ":")]
c, ok := dialerCreators[strings.ToLower(scheme)]
if ok {

View File

@ -9,7 +9,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// NewSocks5Dialer returns a socks5 proxy dialer.

View File

@ -5,7 +5,7 @@ import (
"net"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// PktConn .

View File

@ -11,7 +11,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// NewSocks5Server returns a socks5 proxy server.

View File

@ -6,7 +6,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// NewSSDialer returns a ss proxy dialer.

View File

@ -5,7 +5,7 @@ import (
"net"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// PktConn .

View File

@ -9,7 +9,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// NewSSServer returns a ss proxy server.

View File

@ -17,7 +17,11 @@ type SSH struct {
dialer proxy.Dialer
proxy proxy.Proxy
addr string
config *ssh.ClientConfig
sshCfg *ssh.ClientConfig
sshConn ssh.Conn
sshChan <-chan ssh.NewChannel
sshReq <-chan *ssh.Request
}
func init() {
@ -58,14 +62,18 @@ func NewSSH(s string, d proxy.Dialer, p proxy.Proxy) (*SSH, error) {
config.Auth = append(config.Auth, keyAuth)
}
ssh := &SSH{
t := &SSH{
dialer: d,
proxy: p,
addr: u.Host,
config: config,
sshCfg: config,
}
return ssh, nil
if _, port, _ := net.SplitHostPort(t.addr); port == "" {
t.addr = net.JoinHostPort(t.addr, "22")
}
return t, t.initConn()
}
// NewSSHDialer returns a ssh proxy dialer.
@ -81,21 +89,31 @@ func (s *SSH) Addr() string {
return s.addr
}
// Dial connects to the address addr on the network net via the proxy.
func (s *SSH) Dial(network, addr string) (net.Conn, error) {
c, err := s.dialer.Dial(network, s.addr)
func (s *SSH) initConn() error {
c, err := s.dialer.Dial("tcp", s.addr)
if err != nil {
log.F("[ssh]: dial to %s error: %s", s.addr, err)
return nil, err
return err
}
sshc, ch, req, err := ssh.NewClientConn(c, s.addr, s.config)
s.sshConn, s.sshChan, s.sshReq, err = ssh.NewClientConn(c, s.addr, s.sshCfg)
if err != nil {
log.F("[ssh]: initial connection to %s error: %s", s.addr, err)
return nil, err
return err
}
return ssh.NewClient(sshc, ch, req).Dial(network, addr)
return nil
}
// Dial connects to the address addr on the network net via the proxy.
func (s *SSH) Dial(network, addr string) (c net.Conn, err error) {
c, err = ssh.NewClient(s.sshConn, s.sshChan, s.sshReq).Dial(network, addr)
if err != nil {
log.F("[ssh]: create conn to %s via %s error: %s, try again", addr, s.addr, err)
s.initConn()
c, err = ssh.NewClient(s.sshConn, s.sshChan, s.sshReq).Dial(network, addr)
}
return c, err
}
// DialUDP connects to the given address via the proxy.

View File

@ -9,7 +9,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
"github.com/nadoo/glider/proxy/ssr/internal"
"github.com/nadoo/glider/proxy/ssr/internal/cipher"

View File

@ -7,7 +7,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// NewClearTextDialer returns a trojan cleartext proxy dialer.

View File

@ -7,7 +7,7 @@ import (
"net"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// PktConn is a udp Packet.Conn.

View File

@ -12,7 +12,7 @@ import (
"github.com/nadoo/glider/log"
"github.com/nadoo/glider/pool"
"github.com/nadoo/glider/proxy"
"github.com/nadoo/glider/proxy/socks"
"github.com/nadoo/glider/proxy/protocol/socks"
)
// NewClearTextServer returns a trojan cleartext proxy server.