fix: fix Shadowsocks 2022 compatibility
This commit is contained in:
@@ -1,6 +1,7 @@
|
|||||||
package singbox
|
package singbox
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/base64"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log/slog"
|
"log/slog"
|
||||||
"net"
|
"net"
|
||||||
@@ -152,27 +153,27 @@ func buildRoutes(panelRoutes []panel.RouteRule, custom []map[string]any) M {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Standard blocks for private/loopback
|
// Standard blocks for private/loopback
|
||||||
rules = append(rules, M{
|
// rules = append(rules, M{
|
||||||
"outbound": "block",
|
// "outbound": "block",
|
||||||
"ip_cidr": []string{
|
// "ip_cidr": []string{
|
||||||
"10.0.0.0/8",
|
// "10.0.0.0/8",
|
||||||
"100.64.0.0/10",
|
// "100.64.0.0/10",
|
||||||
"127.0.0.0/8",
|
// "127.0.0.0/8",
|
||||||
"169.254.0.0/16",
|
// "169.254.0.0/16",
|
||||||
"172.16.0.0/12",
|
// "172.16.0.0/12",
|
||||||
"192.0.0.0/24",
|
// "192.0.0.0/24",
|
||||||
"192.168.0.0/16",
|
// "192.168.0.0/16",
|
||||||
"198.18.0.0/15",
|
// "198.18.0.0/15",
|
||||||
"fc00::/7",
|
// "fc00::/7",
|
||||||
"fe80::/10",
|
// "fe80::/10",
|
||||||
"::1/128",
|
// "::1/128",
|
||||||
},
|
// },
|
||||||
}, M{
|
// }, M{
|
||||||
"outbound": "block",
|
// "outbound": "block",
|
||||||
"domain": []string{
|
// "domain": []string{
|
||||||
"geoip:private",
|
// "geoip:private",
|
||||||
},
|
// },
|
||||||
})
|
// })
|
||||||
|
|
||||||
// Panel-defined routes (usually specific blocks/proxies)
|
// Panel-defined routes (usually specific blocks/proxies)
|
||||||
for _, pr := range panelRoutes {
|
for _, pr := range panelRoutes {
|
||||||
@@ -378,20 +379,48 @@ func buildMieru(base M, nc *panel.NodeConfig, users []panel.User) M {
|
|||||||
return base
|
return base
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ss2022Config struct {
|
||||||
|
method string
|
||||||
|
size int
|
||||||
|
}
|
||||||
|
|
||||||
|
var ss2022Methods = map[string]ss2022Config{
|
||||||
|
"2022-blake3-aes-128-gcm": {"2022-blake3-aes-128-gcm", 16},
|
||||||
|
"2022-blake3-aes-256-gcm": {"2022-blake3-aes-256-gcm", 32},
|
||||||
|
"2022-blake3-chacha20-poly1305": {"2022-blake3-chacha20-poly1305", 32},
|
||||||
|
}
|
||||||
|
|
||||||
func buildShadowsocks(base M, nc *panel.NodeConfig, users []panel.User) M {
|
func buildShadowsocks(base M, nc *panel.NodeConfig, users []panel.User) M {
|
||||||
base["type"] = "shadowsocks"
|
base["type"] = "shadowsocks"
|
||||||
base["method"] = nc.Cipher
|
base["method"] = nc.Cipher
|
||||||
|
|
||||||
if strings.HasPrefix(nc.Cipher, "2022-blake3-") {
|
ss2022, isSS2022 := ss2022Methods[nc.Cipher]
|
||||||
|
if isSS2022 {
|
||||||
base["password"] = nc.ServerKey
|
base["password"] = nc.ServerKey
|
||||||
}
|
}
|
||||||
|
|
||||||
userList := make([]M, 0, len(users))
|
userList := make([]M, len(users))
|
||||||
for _, u := range users {
|
var rawBuf []byte
|
||||||
userList = append(userList, M{
|
if isSS2022 {
|
||||||
|
rawBuf = make([]byte, ss2022.size)
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := range users {
|
||||||
|
u := &users[i]
|
||||||
|
user := M{
|
||||||
"name": u.UUID,
|
"name": u.UUID,
|
||||||
"password": u.UUID,
|
"password": u.UUID,
|
||||||
})
|
}
|
||||||
|
|
||||||
|
if isSS2022 {
|
||||||
|
// Reuse buffer and clear it to maintain SS2022 key integrity
|
||||||
|
for j := range rawBuf {
|
||||||
|
rawBuf[j] = 0
|
||||||
|
}
|
||||||
|
copy(rawBuf, u.UUID)
|
||||||
|
user["password"] = base64.StdEncoding.EncodeToString(rawBuf)
|
||||||
|
}
|
||||||
|
userList[i] = user
|
||||||
}
|
}
|
||||||
base["users"] = userList
|
base["users"] = userList
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package xray
|
package xray
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/base64"
|
||||||
"fmt"
|
"fmt"
|
||||||
"log/slog"
|
"log/slog"
|
||||||
"strings"
|
"strings"
|
||||||
@@ -285,9 +286,22 @@ func buildTrojan(base M, nc *panel.NodeConfig, users []panel.User, certFile, key
|
|||||||
return base
|
return base
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type ss2022Config struct {
|
||||||
|
method string
|
||||||
|
size int
|
||||||
|
}
|
||||||
|
|
||||||
|
var ss2022Methods = map[string]ss2022Config{
|
||||||
|
"2022-blake3-aes-128-gcm": {"2022-blake3-aes-128-gcm", 16},
|
||||||
|
"2022-blake3-aes-256-gcm": {"2022-blake3-aes-256-gcm", 32},
|
||||||
|
"2022-blake3-chacha20-poly1305": {"2022-blake3-chacha20-poly1305", 32},
|
||||||
|
}
|
||||||
|
|
||||||
func buildShadowsocks(base M, nc *panel.NodeConfig, users []panel.User) M {
|
func buildShadowsocks(base M, nc *panel.NodeConfig, users []panel.User) M {
|
||||||
|
ss2022, isSS2022 := ss2022Methods[nc.Cipher]
|
||||||
|
|
||||||
// Single-user mode for traditional ciphers
|
// Single-user mode for traditional ciphers
|
||||||
if !strings.HasPrefix(nc.Cipher, "2022-blake3-") {
|
if !isSS2022 {
|
||||||
if len(users) > 0 {
|
if len(users) > 0 {
|
||||||
base["settings"] = M{
|
base["settings"] = M{
|
||||||
"method": nc.Cipher,
|
"method": nc.Cipher,
|
||||||
@@ -300,13 +314,23 @@ func buildShadowsocks(base M, nc *panel.NodeConfig, users []panel.User) M {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Multi-user mode for 2022-blake3 ciphers
|
// Multi-user mode for 2022-blake3 ciphers
|
||||||
clients := make([]M, 0, len(users))
|
clients := make([]M, len(users))
|
||||||
for _, u := range users {
|
rawBuf := make([]byte, ss2022.size)
|
||||||
clients = append(clients, M{
|
|
||||||
"password": u.UUID,
|
for i := range users {
|
||||||
|
u := &users[i]
|
||||||
|
// SS2022 User Key must be Base64 of fixed-length raw bytes
|
||||||
|
for j := range rawBuf {
|
||||||
|
rawBuf[j] = 0
|
||||||
|
}
|
||||||
|
copy(rawBuf, u.UUID)
|
||||||
|
|
||||||
|
clients[i] = M{
|
||||||
|
"password": base64.StdEncoding.EncodeToString(rawBuf),
|
||||||
"email": userEmail(u.ID),
|
"email": userEmail(u.ID),
|
||||||
})
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
base["settings"] = M{
|
base["settings"] = M{
|
||||||
"method": nc.Cipher,
|
"method": nc.Cipher,
|
||||||
"password": nc.ServerKey,
|
"password": nc.ServerKey,
|
||||||
|
|||||||
Reference in New Issue
Block a user