1
0
mirror of https://github.com/v2fly/v2ray-core.git synced 2024-12-22 01:57:12 -05:00

compact buffers

This commit is contained in:
Darien Raymond 2018-12-27 16:36:48 +01:00
parent 012a2d6f57
commit fc92b6295a
No known key found for this signature in database
GPG Key ID: 7251FFA14BB18169
3 changed files with 50 additions and 33 deletions

View File

@ -3,6 +3,7 @@ package buf
import ( import (
"io" "io"
"v2ray.com/core/common"
"v2ray.com/core/common/errors" "v2ray.com/core/common/errors"
"v2ray.com/core/common/serial" "v2ray.com/core/common/serial"
) )
@ -121,6 +122,30 @@ func SplitBytes(mb MultiBuffer, b []byte) (MultiBuffer, int) {
return mb, totalBytes return mb, totalBytes
} }
// Compact returns another MultiBuffer by merging all content of the given one together.
func Compact(mb MultiBuffer) MultiBuffer {
if len(mb) == 0 {
return mb
}
mb2 := make(MultiBuffer, 0, len(mb))
last := mb[0]
for i := 1; i < len(mb); i++ {
curr := mb[i]
if last.Len()+curr.Len() > Size {
mb2 = append(mb2, last)
last = curr
} else {
common.Must2(last.ReadFrom(curr))
curr.Release()
}
}
mb2 = append(mb2, last)
return mb2
}
// SplitFirst splits the first Buffer from the beginning of the MultiBuffer. // SplitFirst splits the first Buffer from the beginning of the MultiBuffer.
func SplitFirst(mb MultiBuffer) (MultiBuffer, *Buffer) { func SplitFirst(mb MultiBuffer) (MultiBuffer, *Buffer) {
if len(mb) == 0 { if len(mb) == 0 {

View File

@ -171,33 +171,17 @@ func (c *interConn) ReadMultiBuffer() (buf.MultiBuffer, error) {
} }
func (c *interConn) WriteMultiBuffer(mb buf.MultiBuffer) error { func (c *interConn) WriteMultiBuffer(mb buf.MultiBuffer) error {
if mb.IsEmpty() { mb = buf.Compact(mb)
return nil
}
if len(mb) == 1 {
_, err := c.Write(mb[0].Bytes())
buf.ReleaseMulti(mb)
return err
}
b := getBuffer()
defer putBuffer(b)
reader := buf.MultiBufferContainer{
MultiBuffer: mb,
}
defer reader.Close()
for { for {
nBytes, err := reader.Read(b[:1200]) mb2, b := buf.SplitFirst(mb)
if err != nil { mb = mb2
if b == nil {
break break
} }
if nBytes == 0 {
continue if err := buf.WriteAllBytes(c, b.Bytes()); err != nil {
} buf.ReleaseMulti(mb)
if _, err := c.Write(b[:nBytes]); err != nil {
return err return err
} }
} }

View File

@ -20,7 +20,6 @@ var (
type connection struct { type connection struct {
conn *websocket.Conn conn *websocket.Conn
reader io.Reader reader io.Reader
mergingWriter *buf.BufferedWriter
remoteAddr net.Addr remoteAddr net.Addr
} }
@ -70,13 +69,22 @@ func (c *connection) Write(b []byte) (int, error) {
} }
func (c *connection) WriteMultiBuffer(mb buf.MultiBuffer) error { func (c *connection) WriteMultiBuffer(mb buf.MultiBuffer) error {
if c.mergingWriter == nil { mb = buf.Compact(mb)
c.mergingWriter = buf.NewBufferedWriter(&buf.BufferToBytesWriter{Writer: c})
for {
mb2, b := buf.SplitFirst(mb)
mb = mb2
if b == nil {
break
} }
if err := c.mergingWriter.WriteMultiBuffer(mb); err != nil {
if err := buf.WriteAllBytes(c, b.Bytes()); err != nil {
buf.ReleaseMulti(mb)
return err return err
} }
return c.mergingWriter.Flush() }
return nil
} }
func (c *connection) Close() error { func (c *connection) Close() error {