mirror of
https://github.com/XTLS/Xray-core.git
synced 2026-05-14 18:09:05 +00:00
Add brutal
This commit is contained in:
@@ -75,6 +75,12 @@ func (mb MultiBuffer) Copy(b []byte) int {
|
||||
return total
|
||||
}
|
||||
|
||||
func (mb MultiBuffer) Bytes() []byte {
|
||||
b := make([]byte, mb.Len())
|
||||
mb.Copy(b)
|
||||
return b
|
||||
}
|
||||
|
||||
// ReadFrom reads all content from reader until EOF.
|
||||
func ReadFrom(reader io.Reader) (MultiBuffer, error) {
|
||||
mb := make(MultiBuffer, 0, 16)
|
||||
|
||||
@@ -2,6 +2,7 @@ package mux
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/binary"
|
||||
goerrors "errors"
|
||||
"io"
|
||||
"sync"
|
||||
@@ -9,6 +10,7 @@ import (
|
||||
|
||||
"github.com/xtls/xray-core/common"
|
||||
"github.com/xtls/xray-core/common/buf"
|
||||
"github.com/xtls/xray-core/common/dice"
|
||||
"github.com/xtls/xray-core/common/errors"
|
||||
"github.com/xtls/xray-core/common/net"
|
||||
"github.com/xtls/xray-core/common/protocol"
|
||||
@@ -171,6 +173,7 @@ func (f *DialingWorkerFactory) Create() (*ClientWorker, error) {
|
||||
type ClientStrategy struct {
|
||||
MaxConcurrency uint32
|
||||
MaxReuseTimes uint32
|
||||
BrutalBPS uint64
|
||||
}
|
||||
|
||||
type ClientWorker struct {
|
||||
@@ -198,6 +201,9 @@ func NewClientWorker(stream transport.Link, s ClientStrategy) (*ClientWorker, er
|
||||
|
||||
go c.fetchOutput()
|
||||
go c.monitor()
|
||||
if s.BrutalBPS > 0 {
|
||||
go c.sendSetBrutal(s.BrutalBPS)
|
||||
}
|
||||
|
||||
return c, nil
|
||||
}
|
||||
@@ -417,3 +423,24 @@ func (m *ClientWorker) fetchOutput() {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (m *ClientWorker) sendSetBrutal(sendBPS uint64) {
|
||||
meta := FrameMetadata{
|
||||
SessionID: 91,
|
||||
SessionStatus: SessionStatusSetBrutal,
|
||||
}
|
||||
meta.Option.Set(OptionData)
|
||||
frame := buf.New()
|
||||
common.Must(meta.WriteTo(frame))
|
||||
lengthByte := frame.Extend(2)
|
||||
speedByte := frame.Extend(int32(200 + dice.Roll(200)))
|
||||
binary.BigEndian.PutUint64(speedByte, sendBPS)
|
||||
binary.BigEndian.PutUint16(lengthByte, uint16(len(speedByte)))
|
||||
errors.LogError(context.Background(), "Start sending SetBrutal frame with speed: ", sendBPS)
|
||||
err := m.link.Writer.WriteMultiBuffer(buf.MultiBuffer{frame})
|
||||
if err != nil {
|
||||
frame.Release()
|
||||
errors.LogError(context.Background(), "failed to send SetBrutal frame: ", err)
|
||||
}
|
||||
errors.LogInfo(context.Background(), "SetBrutal frame sent successfully")
|
||||
}
|
||||
|
||||
@@ -21,6 +21,8 @@ const (
|
||||
SessionStatusKeep SessionStatus = 0x02
|
||||
SessionStatusEnd SessionStatus = 0x03
|
||||
SessionStatusKeepAlive SessionStatus = 0x04
|
||||
|
||||
SessionStatusSetBrutal SessionStatus = 0x91
|
||||
)
|
||||
|
||||
const (
|
||||
|
||||
@@ -2,6 +2,7 @@ package mux
|
||||
|
||||
import (
|
||||
"context"
|
||||
"encoding/binary"
|
||||
"io"
|
||||
"time"
|
||||
|
||||
@@ -16,6 +17,7 @@ import (
|
||||
"github.com/xtls/xray-core/core"
|
||||
"github.com/xtls/xray-core/features/routing"
|
||||
"github.com/xtls/xray-core/transport"
|
||||
"github.com/xtls/xray-core/transport/internet/brutal"
|
||||
"github.com/xtls/xray-core/transport/pipe"
|
||||
)
|
||||
|
||||
@@ -333,6 +335,40 @@ func (w *ServerWorker) handleStatusEnd(meta *FrameMetadata, reader *buf.Buffered
|
||||
return nil
|
||||
}
|
||||
|
||||
// note: do not return error, just log it
|
||||
func (w *ServerWorker) HandleSetBrutal(ctx context.Context, meta *FrameMetadata, reader *buf.BufferedReader) error {
|
||||
if meta.Option.Has(OptionData) == false {
|
||||
errors.LogError(ctx, "SetBrutal frame missing data")
|
||||
return nil
|
||||
}
|
||||
chunkReader := NewStreamReader(reader)
|
||||
data, err := chunkReader.ReadMultiBuffer()
|
||||
if err != nil {
|
||||
errors.LogError(ctx, "unexpected error when reading brutal data: ", err)
|
||||
}
|
||||
speed := binary.BigEndian.Uint64(data.Bytes())
|
||||
|
||||
inbound := session.InboundFromContext(ctx)
|
||||
if inbound == nil || inbound.Conn == nil {
|
||||
errors.LogError(ctx, "no inbound connection found for brutal set")
|
||||
return nil
|
||||
}
|
||||
conn := inbound.Conn
|
||||
tcpConn, ok := conn.(*net.TCPConn)
|
||||
if !ok {
|
||||
errors.LogError(ctx, "brutal can only be set on TCP connections")
|
||||
return nil
|
||||
}
|
||||
err = brutal.SetBrutal(tcpConn, speed)
|
||||
if err != nil {
|
||||
errors.LogError(ctx, "failed to set brutal: ", err)
|
||||
return nil
|
||||
} else {
|
||||
errors.LogInfo(ctx, "successfully set brutal speed: ", speed)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (w *ServerWorker) handleFrame(ctx context.Context, reader *buf.BufferedReader) error {
|
||||
var meta FrameMetadata
|
||||
err := meta.Unmarshal(reader, session.IsReverseMuxFromContext(ctx))
|
||||
@@ -349,6 +385,8 @@ func (w *ServerWorker) handleFrame(ctx context.Context, reader *buf.BufferedRead
|
||||
err = w.handleStatusNew(session.ContextWithIsReverseMux(ctx, false), &meta, reader)
|
||||
case SessionStatusKeep:
|
||||
err = w.handleStatusKeep(&meta, reader)
|
||||
case SessionStatusSetBrutal:
|
||||
err = w.HandleSetBrutal(ctx, &meta, reader)
|
||||
default:
|
||||
status := meta.SessionStatus
|
||||
return errors.New("unknown status: ", status).AtError()
|
||||
|
||||
Reference in New Issue
Block a user