Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 9 additions & 0 deletions common/singbridge/tls.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package singbridge
import (
"context"
"crypto/tls"
"time"

singtls "github.com/sagernet/sing/common/tls"

Expand Down Expand Up @@ -50,6 +51,14 @@ func (c *tlsConfigWrapper) Client(_ net.Conn) (singtls.Conn, error) {
panic("invalid")
}

func (c *tlsConfigWrapper) HandshakeTimeout() time.Duration {
panic("invalid")
}

func (c *tlsConfigWrapper) SetHandshakeTimeout(_ time.Duration) {
panic("invalid")
}

func (c *tlsConfigWrapper) Clone() singtls.Config {
panic("invalid")
}
3 changes: 2 additions & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,12 @@ require (
github.com/pires/go-proxyproto v0.15.0
github.com/quic-go/quic-go v0.60.0
github.com/refraction-networking/utls v1.8.3-0.20260623165621-880e27d8b0e5
github.com/sagernet/sing v0.8.11
github.com/sagernet/sing v0.8.12-0.20260702081104-2ded2af32d3d
github.com/sagernet/sing-mux v0.3.5
github.com/sagernet/sing-quic v0.6.3
github.com/sagernet/sing-shadowsocks v0.2.9
github.com/sagernet/sing-shadowsocks2 v0.2.2
github.com/sagernet/sing-snell v0.0.0-20260710094516-a4e97ee24beb
github.com/seiflotfy/cuckoofilter v0.0.0-20240715131351-a2f2c23f1771
github.com/stretchr/testify v1.11.1
github.com/v2fly/BrowserBridge v0.0.0-20210430233438-0570fc1d7d08
Expand Down
6 changes: 4 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -225,8 +225,8 @@ github.com/russross/blackfriday/v2 v2.0.1/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQD
github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts=
github.com/sagernet/quic-go v0.59.0-sing-box-mod.4 h1:6qvrUW79S+CrPwWz6cMePXohgjHoKxLo3c+MDhNwc3o=
github.com/sagernet/quic-go v0.59.0-sing-box-mod.4/go.mod h1:OqILvS182CyOol5zNNo6bguvOGgXzV459+chpRaUC+4=
github.com/sagernet/sing v0.8.11 h1:AKZRvjFPHtAXwGCjOJrzAQPiZxr8mobhuSUqkHf+VQw=
github.com/sagernet/sing v0.8.11/go.mod h1:olXxWQNqRW/l2Q6JI3b2Qmz8iQnIFlOeeH8bx6JhgUA=
github.com/sagernet/sing v0.8.12-0.20260702081104-2ded2af32d3d h1:BhsQU0Iug1tU4xR52cjm8Sc+LBo+KwdyLTRn3ie9moo=
github.com/sagernet/sing v0.8.12-0.20260702081104-2ded2af32d3d/go.mod h1:olXxWQNqRW/l2Q6JI3b2Qmz8iQnIFlOeeH8bx6JhgUA=
github.com/sagernet/sing-mux v0.3.5 h1:RHnhVEc+SFqkrK4xMygYjDwwLhzp2Bj3lztSukONfhI=
github.com/sagernet/sing-mux v0.3.5/go.mod h1:QvlKMyNBNrQoyX4x+gq028uPbLM2XeRpWtDsWBJbFSk=
github.com/sagernet/sing-quic v0.6.3 h1:0wSPqCNJsC7CadB5GZS1aPkyU27aRwHPd5SlsijbBNw=
Expand All @@ -235,6 +235,8 @@ github.com/sagernet/sing-shadowsocks v0.2.9 h1:Paep5zCszRKsEn8587O0MnhFWKJwDW1Y4
github.com/sagernet/sing-shadowsocks v0.2.9/go.mod h1:TE/Z6401Pi8tgr0nBZcM/xawAI6u3F6TTbz4nH/qw+8=
github.com/sagernet/sing-shadowsocks2 v0.2.2 h1:GUN6ttP3NSJL/bFJJZZezp9/o6DQdG9qWyQdRvOy2LY=
github.com/sagernet/sing-shadowsocks2 v0.2.2/go.mod h1:ZAYv1VFjvnMK4QQJltuvoN52biUN76TdNwzyDjSRrzc=
github.com/sagernet/sing-snell v0.0.0-20260710094516-a4e97ee24beb h1:VvU2/PZqP5tbKTDq0BxkhRO8ZnKI4UJzziakgBiP2Qg=
github.com/sagernet/sing-snell v0.0.0-20260710094516-a4e97ee24beb/go.mod h1:PcwzX/Xvqky0EP3kGt8OCjYb3R1pydenPHNQZcPZmXY=
github.com/sagernet/smux v1.5.50-sing-box-mod.1 h1:XkJcivBC9V4wBjiGXIXZ229aZCU1hzcbp6kSkkyQ478=
github.com/sagernet/smux v1.5.50-sing-box-mod.1/go.mod h1:NjhsCEWedJm7eFLyhuBgIEzwfhRmytrUoiLluxs5Sk8=
github.com/sean-/seed v0.0.0-20170313163322-e2103e2c3529/go.mod h1:DxrIzT+xaE7yg65j358z/aeFdxmN0P9QXhEzd20vsDc=
Expand Down
37 changes: 37 additions & 0 deletions infra/conf/v4/snell.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
package v4

import (
"github.com/golang/protobuf/proto"

"github.com/exclavenetwork/exclave-core/v5/infra/conf/cfgcommon"
"github.com/exclavenetwork/exclave-core/v5/proxy/snell"
)

type SnellClientConfig struct {
Address *cfgcommon.Address `json:"address"`
Port uint16 `json:"port"`
PSK string `json:"psk"`
UserKey string `json:"userKey"`
Version uint32 `json:"version"`
Reuse bool `json:"reuse"`
ObfsMode string `json:"obfsMode"`
ObfsHost string `json:"obfsHost"`
Mode string `json:"mode"`
}

func (c *SnellClientConfig) Build() (proto.Message, error) {
if c.Address == nil {
return nil, newError("missing server address")
}
return &snell.ClientConfig{
Address: c.Address.Build(),
Port: uint32(c.Port),
Psk: c.PSK,
UserKey: c.UserKey,
Version: c.Version,
Reuse: c.Reuse,
ObfsMode: c.ObfsMode,
ObfsHost: c.ObfsHost,
Mode: c.Mode,
}, nil
}
1 change: 1 addition & 0 deletions infra/conf/v4/v2ray.go
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,7 @@ var (
"tuic": func() interface{} { return new(TuicClientConfig) },
"juicity": func() interface{} { return new(JuicityClientConfig) },
"mieru": func() interface{} { return new(MieruClientConfig) },
"snell": func() interface{} { return new(SnellClientConfig) },
"trusttunnel": func() interface{} { return new(TrustTunnelClientConfig) },
}, "protocol", "settings")
)
Expand Down
1 change: 1 addition & 0 deletions main/distro/all/all.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,7 @@ import (
_ "github.com/exclavenetwork/exclave-core/v5/proxy/hysteria2"
_ "github.com/exclavenetwork/exclave-core/v5/proxy/juicity"
_ "github.com/exclavenetwork/exclave-core/v5/proxy/mieru"
_ "github.com/exclavenetwork/exclave-core/v5/proxy/snell"
_ "github.com/exclavenetwork/exclave-core/v5/proxy/tuic"
_ "github.com/exclavenetwork/exclave-core/v5/proxy/wireguard"

Expand Down
194 changes: 194 additions & 0 deletions proxy/snell/config.pb.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,194 @@
package snell

import (
net "github.com/exclavenetwork/exclave-core/v5/common/net"
_ "github.com/exclavenetwork/exclave-core/v5/common/protoext"
protoreflect "google.golang.org/protobuf/reflect/protoreflect"
protoimpl "google.golang.org/protobuf/runtime/protoimpl"
reflect "reflect"
sync "sync"
unsafe "unsafe"
)

const (
// Verify that this generated code is sufficiently up-to-date.
_ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion)
// Verify that runtime/protoimpl is sufficiently up-to-date.
_ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20)
)

type ClientConfig struct {
state protoimpl.MessageState `protogen:"open.v1"`
Address *net.IPOrDomain `protobuf:"bytes,1,opt,name=address,proto3" json:"address,omitempty"`
Port uint32 `protobuf:"varint,2,opt,name=port,proto3" json:"port,omitempty"`
Psk string `protobuf:"bytes,3,opt,name=psk,proto3" json:"psk,omitempty"`
Version uint32 `protobuf:"varint,4,opt,name=version,proto3" json:"version,omitempty"`
UserKey string `protobuf:"bytes,5,opt,name=user_key,json=userKey,proto3" json:"user_key,omitempty"`
Reuse bool `protobuf:"varint,6,opt,name=reuse,proto3" json:"reuse,omitempty"`
ObfsMode string `protobuf:"bytes,7,opt,name=obfs_mode,json=obfsMode,proto3" json:"obfs_mode,omitempty"`
ObfsHost string `protobuf:"bytes,8,opt,name=obfs_host,json=obfsHost,proto3" json:"obfs_host,omitempty"`
Mode string `protobuf:"bytes,9,opt,name=mode,proto3" json:"mode,omitempty"`
unknownFields protoimpl.UnknownFields
sizeCache protoimpl.SizeCache
}

func (x *ClientConfig) Reset() {
*x = ClientConfig{}
mi := &file_proxy_snell_config_proto_msgTypes[0]
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
ms.StoreMessageInfo(mi)
}

func (x *ClientConfig) String() string {
return protoimpl.X.MessageStringOf(x)
}

func (*ClientConfig) ProtoMessage() {}

func (x *ClientConfig) ProtoReflect() protoreflect.Message {
mi := &file_proxy_snell_config_proto_msgTypes[0]
if x != nil {
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
if ms.LoadMessageInfo() == nil {
ms.StoreMessageInfo(mi)
}
return ms
}
return mi.MessageOf(x)
}

// Deprecated: Use ClientConfig.ProtoReflect.Descriptor instead.
func (*ClientConfig) Descriptor() ([]byte, []int) {
return file_proxy_snell_config_proto_rawDescGZIP(), []int{0}
}

func (x *ClientConfig) GetAddress() *net.IPOrDomain {
if x != nil {
return x.Address
}
return nil
}

func (x *ClientConfig) GetPort() uint32 {
if x != nil {
return x.Port
}
return 0
}

func (x *ClientConfig) GetPsk() string {
if x != nil {
return x.Psk
}
return ""
}

func (x *ClientConfig) GetVersion() uint32 {
if x != nil {
return x.Version
}
return 0
}

func (x *ClientConfig) GetUserKey() string {
if x != nil {
return x.UserKey
}
return ""
}

func (x *ClientConfig) GetReuse() bool {
if x != nil {
return x.Reuse
}
return false
}

func (x *ClientConfig) GetObfsMode() string {
if x != nil {
return x.ObfsMode
}
return ""
}

func (x *ClientConfig) GetObfsHost() string {
if x != nil {
return x.ObfsHost
}
return ""
}

func (x *ClientConfig) GetMode() string {
if x != nil {
return x.Mode
}
return ""
}

var File_proxy_snell_config_proto protoreflect.FileDescriptor

const file_proxy_snell_config_proto_rawDesc = "" +
"\n" +
"\x18proxy/snell/config.proto\x12\x18exclave.core.proxy.snell\x1a common/protoext/extensions.proto\x1a\x18common/net/address.proto\"\xa3\x02\n" +
"\fClientConfig\x12=\n" +
"\aaddress\x18\x01 \x01(\v2#.exclave.core.common.net.IPOrDomainR\aaddress\x12\x12\n" +
"\x04port\x18\x02 \x01(\rR\x04port\x12\x10\n" +
"\x03psk\x18\x03 \x01(\tR\x03psk\x12\x18\n" +
"\aversion\x18\x04 \x01(\rR\aversion\x12\x19\n" +
"\buser_key\x18\x05 \x01(\tR\auserKey\x12\x14\n" +
"\x05reuse\x18\x06 \x01(\bR\x05reuse\x12\x1b\n" +
"\tobfs_mode\x18\a \x01(\tR\bobfsMode\x12\x1b\n" +
"\tobfs_host\x18\b \x01(\tR\bobfsHost\x12\x12\n" +
"\x04mode\x18\t \x01(\tR\x04mode:\x15\x82\xb5\x18\x11\n" +
"\boutbound\x12\x05snellB\x88\x01\n" +
"2com.github.exclavenetwork.exclave.core.proxy.snellP\x01Z5github.com/exclavenetwork/exclave-core/v5/proxy/snell\xaa\x02\x18Exclave.Core.Proxy.Snellb\x06proto3"

var (
file_proxy_snell_config_proto_rawDescOnce sync.Once
file_proxy_snell_config_proto_rawDescData []byte
)

func file_proxy_snell_config_proto_rawDescGZIP() []byte {
file_proxy_snell_config_proto_rawDescOnce.Do(func() {
file_proxy_snell_config_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_proxy_snell_config_proto_rawDesc), len(file_proxy_snell_config_proto_rawDesc)))
})
return file_proxy_snell_config_proto_rawDescData
}

var file_proxy_snell_config_proto_msgTypes = make([]protoimpl.MessageInfo, 1)
var file_proxy_snell_config_proto_goTypes = []any{
(*ClientConfig)(nil), // 0: exclave.core.proxy.snell.ClientConfig
(*net.IPOrDomain)(nil), // 1: exclave.core.common.net.IPOrDomain
}
var file_proxy_snell_config_proto_depIdxs = []int32{
1, // 0: exclave.core.proxy.snell.ClientConfig.address:type_name -> exclave.core.common.net.IPOrDomain
1, // [1:1] is the sub-list for method output_type
1, // [1:1] is the sub-list for method input_type
1, // [1:1] is the sub-list for extension type_name
1, // [1:1] is the sub-list for extension extendee
0, // [0:1] is the sub-list for field type_name
}

func init() { file_proxy_snell_config_proto_init() }
func file_proxy_snell_config_proto_init() {
if File_proxy_snell_config_proto != nil {
return
}
type x struct{}
out := protoimpl.TypeBuilder{
File: protoimpl.DescBuilder{
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
RawDescriptor: unsafe.Slice(unsafe.StringData(file_proxy_snell_config_proto_rawDesc), len(file_proxy_snell_config_proto_rawDesc)),
NumEnums: 0,
NumMessages: 1,
NumExtensions: 0,
NumServices: 0,
},
GoTypes: file_proxy_snell_config_proto_goTypes,
DependencyIndexes: file_proxy_snell_config_proto_depIdxs,
MessageInfos: file_proxy_snell_config_proto_msgTypes,
}.Build()
File_proxy_snell_config_proto = out.File
file_proxy_snell_config_proto_goTypes = nil
file_proxy_snell_config_proto_depIdxs = nil
}
25 changes: 25 additions & 0 deletions proxy/snell/config.proto
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
syntax = "proto3";

package exclave.core.proxy.snell;
option csharp_namespace = "Exclave.Core.Proxy.Snell";
option go_package = "github.com/exclavenetwork/exclave-core/v5/proxy/snell";
option java_package = "com.github.exclavenetwork.exclave.core.proxy.snell";
option java_multiple_files = true;

import "common/protoext/extensions.proto";
import "common/net/address.proto";

message ClientConfig {
option (exclave.core.common.protoext.message_opt).type = "outbound";
option (exclave.core.common.protoext.message_opt).short_name = "snell";

exclave.core.common.net.IPOrDomain address = 1;
uint32 port = 2;
string psk = 3;
uint32 version = 4;
string user_key = 5;
bool reuse = 6;
string obfs_mode = 7;
string obfs_host = 8;
string mode = 9;
}
9 changes: 9 additions & 0 deletions proxy/snell/errors.generated.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package snell

import "github.com/exclavenetwork/exclave-core/v5/common/errors"

type errPathObjHolder struct{}

func newError(values ...interface{}) *errors.Error {
return errors.New(values...).WithPathObj(errPathObjHolder{})
}
Loading