mirror of
https://github.com/SagerNet/sing-box.git
synced 2026-04-14 04:38:28 +10:00
ccm,ocm: fix reverse session shutdown race
This commit is contained in:
@@ -50,6 +50,7 @@ type externalCredential struct {
|
||||
reverse bool
|
||||
reverseSession *yamux.Session
|
||||
reverseAccess sync.RWMutex
|
||||
closed bool
|
||||
reverseContext context.Context
|
||||
reverseCancel context.CancelFunc
|
||||
connectorDialer N.Dialer
|
||||
@@ -542,12 +543,16 @@ func (c *externalCredential) httpTransport() *http.Client {
|
||||
}
|
||||
|
||||
func (c *externalCredential) close() {
|
||||
var session *yamux.Session
|
||||
c.reverseAccess.Lock()
|
||||
if c.reverseCancel != nil {
|
||||
c.reverseCancel()
|
||||
if !c.closed {
|
||||
c.closed = true
|
||||
if c.reverseCancel != nil {
|
||||
c.reverseCancel()
|
||||
}
|
||||
session = c.reverseSession
|
||||
c.reverseSession = nil
|
||||
}
|
||||
session := c.reverseSession
|
||||
c.reverseSession = nil
|
||||
c.reverseAccess.Unlock()
|
||||
if session != nil {
|
||||
session.Close()
|
||||
@@ -567,14 +572,19 @@ func (c *externalCredential) getReverseSession() *yamux.Session {
|
||||
return c.reverseSession
|
||||
}
|
||||
|
||||
func (c *externalCredential) setReverseSession(session *yamux.Session) {
|
||||
func (c *externalCredential) setReverseSession(session *yamux.Session) bool {
|
||||
c.reverseAccess.Lock()
|
||||
if c.closed {
|
||||
c.reverseAccess.Unlock()
|
||||
return false
|
||||
}
|
||||
old := c.reverseSession
|
||||
c.reverseSession = session
|
||||
c.reverseAccess.Unlock()
|
||||
if old != nil {
|
||||
old.Close()
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (c *externalCredential) clearReverseSession(session *yamux.Session) {
|
||||
@@ -593,6 +603,10 @@ func (c *externalCredential) getReverseContext() context.Context {
|
||||
|
||||
func (c *externalCredential) resetReverseContext() {
|
||||
c.reverseAccess.Lock()
|
||||
if c.closed {
|
||||
c.reverseAccess.Unlock()
|
||||
return
|
||||
}
|
||||
c.reverseCancel()
|
||||
c.reverseContext, c.reverseCancel = context.WithCancel(context.Background())
|
||||
c.reverseAccess.Unlock()
|
||||
|
||||
@@ -110,7 +110,10 @@ func (s *Service) handleReverseConnect(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
receiverCredential.setReverseSession(session)
|
||||
if !receiverCredential.setReverseSession(session) {
|
||||
session.Close()
|
||||
return
|
||||
}
|
||||
s.logger.Info("reverse connection established for ", receiverCredential.tagName(), " from ", r.RemoteAddr)
|
||||
|
||||
go func() {
|
||||
|
||||
@@ -52,6 +52,7 @@ type externalCredential struct {
|
||||
reverse bool
|
||||
reverseSession *yamux.Session
|
||||
reverseAccess sync.RWMutex
|
||||
closed bool
|
||||
reverseContext context.Context
|
||||
reverseCancel context.CancelFunc
|
||||
connectorDialer N.Dialer
|
||||
@@ -595,12 +596,16 @@ func (c *externalCredential) ocmGetBaseURL() string {
|
||||
}
|
||||
|
||||
func (c *externalCredential) close() {
|
||||
var session *yamux.Session
|
||||
c.reverseAccess.Lock()
|
||||
if c.reverseCancel != nil {
|
||||
c.reverseCancel()
|
||||
if !c.closed {
|
||||
c.closed = true
|
||||
if c.reverseCancel != nil {
|
||||
c.reverseCancel()
|
||||
}
|
||||
session = c.reverseSession
|
||||
c.reverseSession = nil
|
||||
}
|
||||
session := c.reverseSession
|
||||
c.reverseSession = nil
|
||||
c.reverseAccess.Unlock()
|
||||
if session != nil {
|
||||
session.Close()
|
||||
@@ -620,14 +625,19 @@ func (c *externalCredential) getReverseSession() *yamux.Session {
|
||||
return c.reverseSession
|
||||
}
|
||||
|
||||
func (c *externalCredential) setReverseSession(session *yamux.Session) {
|
||||
func (c *externalCredential) setReverseSession(session *yamux.Session) bool {
|
||||
c.reverseAccess.Lock()
|
||||
if c.closed {
|
||||
c.reverseAccess.Unlock()
|
||||
return false
|
||||
}
|
||||
old := c.reverseSession
|
||||
c.reverseSession = session
|
||||
c.reverseAccess.Unlock()
|
||||
if old != nil {
|
||||
old.Close()
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (c *externalCredential) clearReverseSession(session *yamux.Session) {
|
||||
@@ -646,6 +656,10 @@ func (c *externalCredential) getReverseContext() context.Context {
|
||||
|
||||
func (c *externalCredential) resetReverseContext() {
|
||||
c.reverseAccess.Lock()
|
||||
if c.closed {
|
||||
c.reverseAccess.Unlock()
|
||||
return
|
||||
}
|
||||
c.reverseCancel()
|
||||
c.reverseContext, c.reverseCancel = context.WithCancel(context.Background())
|
||||
c.reverseAccess.Unlock()
|
||||
|
||||
@@ -110,7 +110,10 @@ func (s *Service) handleReverseConnect(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
receiverCredential.setReverseSession(session)
|
||||
if !receiverCredential.setReverseSession(session) {
|
||||
session.Close()
|
||||
return
|
||||
}
|
||||
s.logger.Info("reverse connection established for ", receiverCredential.tagName(), " from ", r.RemoteAddr)
|
||||
|
||||
go func() {
|
||||
|
||||
Reference in New Issue
Block a user