chore: direct append data to bufio.Reader's internal buffer as much as possible
This commit is contained in:
parent
fe7c1a2cdb
commit
832dae3421
3 changed files with 43 additions and 2 deletions
|
@ -84,9 +84,9 @@ func (c *BufferedConn) ReadCached() *buf.Buffer { // call in sing/common/bufio.C
|
|||
length := c.r.Buffered()
|
||||
b, _ := c.r.Peek(length)
|
||||
_, _ = c.r.Discard(length)
|
||||
c.r = nil // drop bufio.Reader to let gc can clean up its internal buf
|
||||
return buf.As(b)
|
||||
}
|
||||
c.r = nil // drop bufio.Reader to let gc can clean up its internal buf
|
||||
return nil
|
||||
}
|
||||
|
||||
|
|
34
common/net/bufconn_unsafe.go
Normal file
34
common/net/bufconn_unsafe.go
Normal file
|
@ -0,0 +1,34 @@
|
|||
package net
|
||||
|
||||
import (
|
||||
"io"
|
||||
"unsafe"
|
||||
)
|
||||
|
||||
// bufioReader copy from stdlib bufio/bufio.go
|
||||
// This structure has remained unchanged from go1.5 to go1.21.
|
||||
type bufioReader struct {
|
||||
buf []byte
|
||||
rd io.Reader // reader provided by the client
|
||||
r, w int // buf read and write positions
|
||||
err error
|
||||
lastByte int // last byte read for UnreadByte; -1 means invalid
|
||||
lastRuneSize int // size of last rune read for UnreadRune; -1 means invalid
|
||||
}
|
||||
|
||||
func (c *BufferedConn) AppendData(buf []byte) (ok bool) {
|
||||
b := (*bufioReader)(unsafe.Pointer(c.r))
|
||||
pos := len(b.buf) - b.w - len(buf)
|
||||
if pos >= -b.r { // len(b.buf)-(b.w - b.r) >= len(buf)
|
||||
if pos < 0 { // len(b.buf)-b.w < len(buf)
|
||||
// Slide existing data to beginning.
|
||||
copy(b.buf, b.buf[b.r:b.w])
|
||||
b.w -= b.r
|
||||
b.r = 0
|
||||
}
|
||||
|
||||
b.w += copy(b.buf[b.w:], buf)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
|
@ -554,7 +554,14 @@ func StreamUpgradedWebsocketConn(w http.ResponseWriter, r *http.Request) (net.Co
|
|||
}
|
||||
|
||||
if edBuf := decodeXray0rtt(r.Header); len(edBuf) > 0 {
|
||||
conn = N.NewCachedConn(conn, edBuf)
|
||||
appendOk := false
|
||||
if bufConn, ok := conn.(*N.BufferedConn); ok {
|
||||
appendOk = bufConn.AppendData(edBuf)
|
||||
}
|
||||
if !appendOk {
|
||||
conn = N.NewCachedConn(conn, edBuf)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return conn, nil
|
||||
|
|
Loading…
Reference in a new issue