Buffer control for client using options TcpSendBuffer and TcpReceiveBuffer.

This commit is contained in:
notsure2 2023-05-29 16:46:36 +03:00
parent ba0e164eac
commit 93bf613a28
8 changed files with 70 additions and 18 deletions

View File

@ -201,6 +201,6 @@ func main() {
if err != nil { if err != nil {
log.Fatal(err) log.Fatal(err)
} }
client.RouteTCP(listener, localConfig.Timeout, remoteConfig.Singleplex, seshMaker) client.RouteTCP(listener, localConfig.Timeout, remoteConfig.Singleplex, localConfig.TcpSendBuffer, localConfig.TcpReceiveBuffer, seshMaker)
} }
} }

View File

@ -4,6 +4,7 @@ import (
"io" "io"
"net" "net"
"sync" "sync"
"syscall"
"time" "time"
"github.com/cbeuw/Cloak/internal/common" "github.com/cbeuw/Cloak/internal/common"
@ -95,7 +96,7 @@ func RouteUDP(bindFunc func() (*net.UDPConn, error), streamTimeout time.Duration
} }
} }
func RouteTCP(listener net.Listener, streamTimeout time.Duration, singleplex bool, newSeshFunc func() *mux.Session) { func RouteTCP(listener net.Listener, streamTimeout time.Duration, singleplex bool, sendBufferSize int, receiveBufferSize int, newSeshFunc func() *mux.Session) {
var sesh *mux.Session var sesh *mux.Session
for { for {
localConn, err := listener.Accept() localConn, err := listener.Accept()
@ -103,6 +104,29 @@ func RouteTCP(listener net.Listener, streamTimeout time.Duration, singleplex boo
log.Fatal(err) log.Fatal(err)
continue continue
} }
file, err := localConn.(*net.TCPConn).File()
if err != nil {
log.Fatal(err)
continue
}
if sendBufferSize > 0 {
log.Debugf("Setting loopback connection tcp send buffer: %d", sendBufferSize)
err := syscall.SetsockoptInt(common.Platformfd(file.Fd()), syscall.SOL_SOCKET, syscall.SO_SNDBUF, sendBufferSize)
if err != nil {
log.Errorf("setsocketopt SO_SNDBUF: %s\n", err)
}
}
if receiveBufferSize > 0 {
log.Debugf("Setting loopback connection tcp receive buffer: %d", receiveBufferSize)
err = syscall.SetsockoptInt(common.Platformfd(file.Fd()), syscall.SOL_SOCKET, syscall.SO_RCVBUF, receiveBufferSize)
if err != nil {
log.Errorf("setsocketopt SO_RCVBUF: %s\n", err)
}
}
if !singleplex && (sesh == nil || sesh.IsClosed()) { if !singleplex && (sesh == nil || sesh.IsClosed()) {
sesh = newSeshFunc() sesh = newSeshFunc()
} }

View File

@ -40,6 +40,8 @@ type RawConfig struct {
CDNWsUrlPath string // nullable CDNWsUrlPath string // nullable
StreamTimeout int // nullable StreamTimeout int // nullable
KeepAlive int // nullable KeepAlive int // nullable
LoopbackTcpSendBuffer int // nullable
LoopbackTcpReceiveBuffer int // nullable
} }
type RemoteConnConfig struct { type RemoteConnConfig struct {
@ -54,6 +56,8 @@ type LocalConnConfig struct {
LocalAddr string LocalAddr string
Timeout time.Duration Timeout time.Duration
MockDomainList []string MockDomainList []string
TcpSendBuffer int
TcpReceiveBuffer int
} }
type AuthInfo struct { type AuthInfo struct {
@ -279,5 +283,13 @@ func (raw *RawConfig) ProcessRawConfig(worldState common.WorldState) (local Loca
local.Timeout = time.Duration(raw.StreamTimeout) * time.Second local.Timeout = time.Duration(raw.StreamTimeout) * time.Second
} }
if raw.LoopbackTcpSendBuffer > 0 {
local.TcpSendBuffer = raw.LoopbackTcpSendBuffer
}
if raw.LoopbackTcpReceiveBuffer > 0 {
local.TcpReceiveBuffer = raw.LoopbackTcpReceiveBuffer
}
return return
} }

View File

@ -0,0 +1,8 @@
//go:build android
// +build android
package common
func Platformfd(fd uintptr) int {
return int(fd)
}

View File

@ -0,0 +1,8 @@
//go:build darwin
// +build darwin
package common
func Platformfd(fd uintptr) int {
return int(fd)
}

View File

@ -1,8 +1,8 @@
//go:build linux //go:build linux
// +build linux // +build linux
package server package common
func platformfd(fd uintptr) int { func Platformfd(fd uintptr) int {
return int(fd) return int(fd)
} }

View File

@ -1,10 +1,10 @@
//go:build windows //go:build windows
// +build windows // +build windows
package server package common
import "syscall" import "syscall"
func platformfd(fd uintptr) syscall.Handle { func Platformfd(fd uintptr) syscall.Handle {
return syscall.Handle(fd) return syscall.Handle(fd)
} }

View File

@ -180,7 +180,7 @@ func InitState(preParse RawConfig, worldState common.WorldState) (sta *State, er
return c.Control(func(fd uintptr) { return c.Control(func(fd uintptr) {
if preParse.LoopbackTcpSendBuffer > 0 { if preParse.LoopbackTcpSendBuffer > 0 {
log.Debugf("Setting loopback connection tcp send buffer: %d", preParse.LoopbackTcpSendBuffer) log.Debugf("Setting loopback connection tcp send buffer: %d", preParse.LoopbackTcpSendBuffer)
err := syscall.SetsockoptInt(platformfd(fd), syscall.SOL_SOCKET, syscall.SO_SNDBUF, preParse.LoopbackTcpSendBuffer) err := syscall.SetsockoptInt(common.Platformfd(fd), syscall.SOL_SOCKET, syscall.SO_SNDBUF, preParse.LoopbackTcpSendBuffer)
if err != nil { if err != nil {
log.Errorf("setsocketopt SO_SNDBUF: %s\n", err) log.Errorf("setsocketopt SO_SNDBUF: %s\n", err)
} }
@ -188,7 +188,7 @@ func InitState(preParse RawConfig, worldState common.WorldState) (sta *State, er
if preParse.LoopbackTcpReceiveBuffer > 0 { if preParse.LoopbackTcpReceiveBuffer > 0 {
log.Debugf("Setting loopback connection tcp receive buffer: %d", preParse.LoopbackTcpReceiveBuffer) log.Debugf("Setting loopback connection tcp receive buffer: %d", preParse.LoopbackTcpReceiveBuffer)
err = syscall.SetsockoptInt(platformfd(fd), syscall.SOL_SOCKET, syscall.SO_RCVBUF, preParse.LoopbackTcpReceiveBuffer) err = syscall.SetsockoptInt(common.Platformfd(fd), syscall.SOL_SOCKET, syscall.SO_RCVBUF, preParse.LoopbackTcpReceiveBuffer)
if err != nil { if err != nil {
log.Errorf("setsocketopt SO_RCVBUF: %s\n", err) log.Errorf("setsocketopt SO_RCVBUF: %s\n", err)
} }