Compare commits

...
23 Commits
Author SHA1 Message Date
xtaci 3127b2d19f lint 2016-09-06 16:29:36 +08:00
xtaci 3db63cdff6 add a max ttl for session in scavenger 2016-09-03 14:32:35 +08:00
xtaci 5154cf81de api change of smux 2016-09-02 23:18:29 +08:00
xtaci cc80029b1e adjust params 2016-09-02 17:29:55 +08:00
xtaci 23d6624745 upd 2016-09-02 17:05:44 +08:00
xtaci f38f7a8ac5 scavenge only 2016-09-02 10:55:22 +08:00
xtaci e913f96f7e Merge branch 'smux' 2016-09-02 10:54:00 +08:00
xtaci 5d0d8bd74d upd 2016-09-02 10:42:23 +08:00
xtaci 4010c83e8f upd 2016-09-01 15:02:21 +08:00
xtaci 76351dff2b upd 2016-09-01 12:59:08 +08:00
xtaci 7a5807cbf5 Revert "explict close session"
This reverts commit cb0f299263.
2016-08-31 23:24:30 +08:00
xtaci 6b26c75ea5 upd 2016-08-31 21:48:43 +08:00
xtaci 0873f349c3 upd 2016-08-31 21:46:14 +08:00
xtaci 281f8675a3 upd 2016-08-31 21:33:52 +08:00
xtaci 65512e9296 upd 2016-08-31 21:31:05 +08:00
xtaci 3ea858ed90 upd 2016-08-31 21:29:27 +08:00
xtaci 5f23781fc0 scavenger 2016-08-31 21:27:19 +08:00
xtaci 2b3573f4ea Merge branch 'master' into smux 2016-08-31 18:10:48 +08:00
xtaci cb0f299263 explict close session 2016-08-31 18:07:24 +08:00
xtaci f64bc908ee upd 2016-08-31 16:30:51 +08:00
xtaci 43c6a674ef upd 2016-08-31 15:28:43 +08:00
xtaci 1a48680a55 upd 2016-08-31 15:23:31 +08:00
xtaci dbdb5293b4 branch smux 2016-08-31 11:39:56 +08:00
4 changed files with 69 additions and 57 deletions
+3 -6
View File
@@ -5,6 +5,7 @@ import (
"os"
)
// Config for client
type Config struct {
LocalAddr string `json:"localaddr"`
RemoteAddr string `json:"remoteaddr"`
@@ -29,16 +30,12 @@ type Config struct {
KeepAlive int `json:"keepalive"`
}
func parseJsonConfig(config *Config, path string) error {
func parseJSONConfig(config *Config, path string) error {
file, err := os.Open(path) // For read access.
if err != nil {
return err
}
defer file.Close()
if err = json.NewDecoder(file).Decode(config); err != nil {
return err
}
return err
return json.NewDecoder(file).Decode(config)
}
+50 -23
View File
@@ -7,7 +7,6 @@ import (
"math/rand"
"net"
"os"
"runtime"
"time"
"golang.org/x/crypto/pbkdf2"
@@ -15,7 +14,7 @@ import (
"github.com/golang/snappy"
"github.com/urfave/cli"
kcp "github.com/xtaci/kcp-go"
"github.com/xtaci/yamux"
"github.com/xtaci/smux"
)
var (
@@ -94,7 +93,7 @@ func main() {
}
myApp := cli.NewApp()
myApp.Name = "kcptun"
myApp.Usage = "kcptun client"
myApp.Usage = "client(with SMUX)"
myApp.Version = VERSION
myApp.Flags = []cli.Flag{
cli.StringFlag{
@@ -233,7 +232,7 @@ func main() {
config.KeepAlive = c.Int("keepalive")
if c.String("c") != "" {
err := parseJsonConfig(&config, c.String("c"))
err := parseJSONConfig(&config, c.String("c"))
checkError(err)
}
@@ -299,15 +298,10 @@ func main() {
log.Println("conn:", config.Conn)
log.Println("autoexpire:", config.AutoExpire)
yconfig := &yamux.Config{
AcceptBacklog: 256,
EnableKeepAlive: true,
KeepAliveInterval: 30 * time.Second,
ConnectionWriteTimeout: 10 * time.Second,
MaxStreamWindowSize: uint32(config.SockBuf),
LogOutput: os.Stderr,
}
createConn := func() *yamux.Session {
smuxConfig := smux.DefaultConfig()
smuxConfig.MaxReceiveBuffer = config.SockBuf
createConn := func() *smux.Session {
kcpconn, err := kcp.DialWithOptions(config.RemoteAddr, block, config.DataShard, config.ParityShard)
checkError(err)
kcpconn.SetStreamMode(true)
@@ -328,22 +322,19 @@ func main() {
}
// stream multiplex
var session *yamux.Session
var session *smux.Session
if config.NoComp {
session, err = yamux.Client(kcpconn, yconfig)
session, err = smux.Client(kcpconn, smuxConfig)
} else {
session, err = yamux.Client(newCompStream(kcpconn), yconfig)
session, err = smux.Client(newCompStream(kcpconn), smuxConfig)
}
checkError(err)
runtime.SetFinalizer(session, func(s *yamux.Session) {
s.Close()
})
return session
}
numconn := uint16(config.Conn)
muxes := make([]struct {
session *yamux.Session
session *smux.Session
ttl time.Time
}, numconn)
@@ -352,6 +343,8 @@ func main() {
muxes[k].ttl = time.Now().Add(time.Duration(config.AutoExpire) * time.Second)
}
chScavenger := make(chan *smux.Session, 128)
go scavenger(chScavenger)
rr := uint16(0)
for {
p1, err := listener.AcceptTCP()
@@ -367,14 +360,15 @@ func main() {
OPEN_P2:
// do auto expiration
if config.AutoExpire > 0 && time.Now().After(muxes[idx].ttl) {
log.Println("autoexpired")
chScavenger <- muxes[idx].session
muxes[idx].session = createConn()
muxes[idx].ttl = time.Now().Add(time.Duration(config.AutoExpire) * time.Second)
}
// do session open
p2, err := muxes[idx].session.Open()
if err != nil { // yamux failure
p2, err := muxes[idx].session.OpenStream()
if err != nil { // mux failure
chScavenger <- muxes[idx].session
muxes[idx].session = createConn()
muxes[idx].ttl = time.Now().Add(time.Duration(config.AutoExpire) * time.Second)
goto OPEN_P2
@@ -385,3 +379,36 @@ func main() {
}
myApp.Run(os.Args)
}
type scavengeSession struct {
session *smux.Session
ttl time.Time
}
const (
maxScavengeTTL = 10 * time.Minute
)
func scavenger(ch chan *smux.Session) {
ticker := time.NewTicker(30 * time.Second)
defer ticker.Stop()
var sessionList []scavengeSession
for {
select {
case sess := <-ch:
sessionList = append(sessionList, scavengeSession{sess, time.Now()})
case <-ticker.C:
var newList []scavengeSession
for k := range sessionList {
s := sessionList[k]
if s.session.NumStreams() == 0 || s.session.IsClosed() || time.Since(s.ttl) > maxScavengeTTL {
log.Println("session scavenged")
s.session.Close()
} else {
newList = append(newList, sessionList[k])
}
}
sessionList = newList
}
}
}
+3 -6
View File
@@ -5,6 +5,7 @@ import (
"os"
)
// Config for server
type Config struct {
Listen string `json:"listen"`
Target string `json:"target"`
@@ -27,16 +28,12 @@ type Config struct {
KeepAlive int `json:"keepalive"`
}
func parseJsonConfig(config *Config, path string) error {
func parseJSONConfig(config *Config, path string) error {
file, err := os.Open(path) // For read access.
if err != nil {
return err
}
defer file.Close()
if err = json.NewDecoder(file).Decode(config); err != nil {
return err
}
return err
return json.NewDecoder(file).Decode(config)
}
+13 -22
View File
@@ -14,7 +14,7 @@ import (
"github.com/golang/snappy"
"github.com/urfave/cli"
kcp "github.com/xtaci/kcp-go"
"github.com/xtaci/yamux"
"github.com/xtaci/smux"
)
var (
@@ -53,35 +53,34 @@ func newCompStream(conn net.Conn) *compStream {
}
// handle multiplex-ed connection
func handleMux(conn io.ReadWriteCloser, target string, config *yamux.Config) {
func handleMux(conn io.ReadWriteCloser, config *Config) {
// stream multiplex
mux, err := yamux.Server(conn, config)
smuxConfig := smux.DefaultConfig()
smuxConfig.MaxReceiveBuffer = config.SockBuf
mux, err := smux.Server(conn, smuxConfig)
if err != nil {
log.Println(err)
return
}
defer mux.Close()
for {
p1, err := mux.Accept()
p1, err := mux.AcceptStream()
if err != nil {
log.Println(err)
return
}
sockbuf := int(config.MaxStreamWindowSize)
p2, err := net.DialTimeout("tcp", target, 5*time.Second)
p2, err := net.DialTimeout("tcp", config.Target, 5*time.Second)
if err != nil {
p1.Close()
log.Println(err)
continue
}
if err := p2.(*net.TCPConn).SetReadBuffer(sockbuf); err != nil {
if err := p2.(*net.TCPConn).SetReadBuffer(config.SockBuf); err != nil {
log.Println("TCP SetReadBuffer:", err)
}
if err := p2.(*net.TCPConn).SetWriteBuffer(sockbuf); err != nil {
if err := p2.(*net.TCPConn).SetWriteBuffer(config.SockBuf); err != nil {
log.Println("TCP SetWriteBuffer:", err)
}
go handleClient(p1, p2)
}
}
@@ -127,7 +126,7 @@ func main() {
}
myApp := cli.NewApp()
myApp.Name = "kcptun"
myApp.Usage = "kcptun server"
myApp.Usage = "server(with SMUX)"
myApp.Version = VERSION
myApp.Flags = []cli.Flag{
cli.StringFlag{
@@ -255,7 +254,7 @@ func main() {
if c.String("c") != "" {
//Now only support json config file
err := parseJsonConfig(&config, c.String("c"))
err := parseJSONConfig(&config, c.String("c"))
checkError(err)
}
@@ -325,14 +324,6 @@ func main() {
if err := lis.SetWriteBuffer(config.SockBuf); err != nil {
log.Println("SetWriteBuffer:", err)
}
yconfig := &yamux.Config{
AcceptBacklog: 256,
EnableKeepAlive: true,
KeepAliveInterval: 30 * time.Second,
ConnectionWriteTimeout: 10 * time.Second,
MaxStreamWindowSize: uint32(config.SockBuf),
LogOutput: os.Stderr,
}
for {
if conn, err := lis.AcceptKCP(); err == nil {
log.Println("remote address:", conn.RemoteAddr())
@@ -344,9 +335,9 @@ func main() {
conn.SetKeepAlive(config.KeepAlive)
if config.NoComp {
go handleMux(conn, config.Target, yconfig)
go handleMux(conn, &config)
} else {
go handleMux(newCompStream(conn), config.Target, yconfig)
go handleMux(newCompStream(conn), &config)
}
} else {
log.Printf("%+v", err)