mirror of
https://github.com/XTLS/Xray-core.git
synced 2026-05-08 14:13:22 +00:00
Chore: Migrate to Go 1.26 (#5680)
This commit is contained in:
2
go.mod
2
go.mod
@@ -1,6 +1,6 @@
|
||||
module github.com/xtls/xray-core
|
||||
|
||||
go 1.25.7
|
||||
go 1.26
|
||||
|
||||
require (
|
||||
github.com/apernet/quic-go v0.57.2-0.20260111184307-eec823306178
|
||||
|
||||
@@ -1,11 +1,14 @@
|
||||
package tls
|
||||
|
||||
import (
|
||||
"crypto/ecdh"
|
||||
"crypto/hpke"
|
||||
"crypto/rand"
|
||||
"encoding/base64"
|
||||
"encoding/pem"
|
||||
"io"
|
||||
"os"
|
||||
|
||||
"github.com/xtls/reality/hpke"
|
||||
"github.com/xtls/xray-core/common"
|
||||
"github.com/xtls/xray-core/main/commands/base"
|
||||
"github.com/xtls/xray-core/transport/internet/tls"
|
||||
@@ -40,15 +43,15 @@ func executeECH(cmd *base.Command, args []string) {
|
||||
// if *input_pqSignatureSchemesEnabled {
|
||||
// kem = 0x30 // hpke.KEM_X25519_KYBER768_DRAFT00
|
||||
// } else {
|
||||
kem = hpke.DHKEM_X25519_HKDF_SHA256
|
||||
kem = hpke.DHKEM(ecdh.X25519()).ID()
|
||||
// }
|
||||
|
||||
echConfig, priv, err := tls.GenerateECHKeySet(0, *input_serverName, kem)
|
||||
echConfig, priv, err := generateECHKeySet(0, *input_serverName, kem)
|
||||
common.Must(err)
|
||||
|
||||
var configBuffer, keyBuffer []byte
|
||||
if *input_echServerKeys == "" {
|
||||
configBytes, _ := tls.MarshalBinary(echConfig)
|
||||
configBytes, _ := marshalBinary(echConfig)
|
||||
var b cryptobyte.Builder
|
||||
b.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
child.AddBytes(configBytes)
|
||||
@@ -91,3 +94,86 @@ func executeECH(cmd *base.Command, args []string) {
|
||||
os.Stdout.WriteString("ECH server keys: \n" + base64.StdEncoding.EncodeToString(keyBuffer) + "\n")
|
||||
}
|
||||
}
|
||||
|
||||
type EchConfig struct {
|
||||
Version uint16
|
||||
ConfigID uint8
|
||||
KemID uint16
|
||||
PublicKey []byte
|
||||
SymmetricCipherSuite []EchCipher
|
||||
MaxNameLength uint8
|
||||
PublicName []byte
|
||||
Extensions []Extension
|
||||
}
|
||||
|
||||
type EchCipher struct {
|
||||
KDFID uint16
|
||||
AEADID uint16
|
||||
}
|
||||
|
||||
type Extension struct {
|
||||
Type uint16
|
||||
Data []byte
|
||||
}
|
||||
|
||||
// reference github.com/OmarTariq612/goech
|
||||
func marshalBinary(ech EchConfig) ([]byte, error) {
|
||||
var b cryptobyte.Builder
|
||||
b.AddUint16(ech.Version)
|
||||
b.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
child.AddUint8(ech.ConfigID)
|
||||
child.AddUint16(ech.KemID)
|
||||
child.AddUint16(uint16(len(ech.PublicKey)))
|
||||
child.AddBytes(ech.PublicKey)
|
||||
child.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
for _, cipherSuite := range ech.SymmetricCipherSuite {
|
||||
child.AddUint16(cipherSuite.KDFID)
|
||||
child.AddUint16(cipherSuite.AEADID)
|
||||
}
|
||||
})
|
||||
child.AddUint8(ech.MaxNameLength)
|
||||
child.AddUint8(uint8(len(ech.PublicName)))
|
||||
child.AddBytes(ech.PublicName)
|
||||
child.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
for _, extention := range ech.Extensions {
|
||||
child.AddUint16(extention.Type)
|
||||
child.AddBytes(extention.Data)
|
||||
}
|
||||
})
|
||||
})
|
||||
return b.Bytes()
|
||||
}
|
||||
|
||||
const ExtensionEncryptedClientHello = 0xfe0d
|
||||
|
||||
func generateECHKeySet(configID uint8, domain string, kem uint16) (EchConfig, []byte, error) {
|
||||
config := EchConfig{
|
||||
Version: ExtensionEncryptedClientHello,
|
||||
ConfigID: configID,
|
||||
PublicName: []byte(domain),
|
||||
KemID: kem,
|
||||
SymmetricCipherSuite: []EchCipher{
|
||||
{KDFID: hpke.HKDFSHA256().ID(), AEADID: hpke.AES128GCM().ID()},
|
||||
{KDFID: hpke.HKDFSHA256().ID(), AEADID: hpke.AES256GCM().ID()},
|
||||
{KDFID: hpke.HKDFSHA256().ID(), AEADID: hpke.ChaCha20Poly1305().ID()},
|
||||
{KDFID: hpke.HKDFSHA384().ID(), AEADID: hpke.AES128GCM().ID()},
|
||||
{KDFID: hpke.HKDFSHA384().ID(), AEADID: hpke.AES256GCM().ID()},
|
||||
{KDFID: hpke.HKDFSHA384().ID(), AEADID: hpke.ChaCha20Poly1305().ID()},
|
||||
{KDFID: hpke.HKDFSHA512().ID(), AEADID: hpke.AES128GCM().ID()},
|
||||
{KDFID: hpke.HKDFSHA512().ID(), AEADID: hpke.AES256GCM().ID()},
|
||||
{KDFID: hpke.HKDFSHA512().ID(), AEADID: hpke.ChaCha20Poly1305().ID()},
|
||||
},
|
||||
MaxNameLength: 0,
|
||||
Extensions: nil,
|
||||
}
|
||||
// if kem == hpke.DHKEM_X25519_HKDF_SHA256 {
|
||||
curve := ecdh.X25519()
|
||||
priv := make([]byte, 32)
|
||||
_, err := io.ReadFull(rand.Reader, priv)
|
||||
if err != nil {
|
||||
return config, nil, err
|
||||
}
|
||||
privKey, _ := curve.NewPrivateKey(priv)
|
||||
config.PublicKey = privKey.PublicKey().Bytes()
|
||||
return config, priv, nil
|
||||
}
|
||||
|
||||
@@ -524,11 +524,13 @@ func ConfigFromStreamSettings(settings *internet.MemoryStreamConfig) *Config {
|
||||
|
||||
func ParseCurveName(curveNames []string) []tls.CurveID {
|
||||
curveMap := map[string]tls.CurveID{
|
||||
"curvep256": tls.CurveP256,
|
||||
"curvep384": tls.CurveP384,
|
||||
"curvep521": tls.CurveP521,
|
||||
"x25519": tls.X25519,
|
||||
"x25519mlkem768": tls.X25519MLKEM768,
|
||||
"curvep256": tls.CurveP256,
|
||||
"curvep384": tls.CurveP384,
|
||||
"curvep521": tls.CurveP521,
|
||||
"x25519": tls.X25519,
|
||||
"x25519mlkem768": tls.X25519MLKEM768,
|
||||
"secp256r1mlkem768": tls.SecP256r1MLKEM768,
|
||||
"secp384r1mlkem1024": tls.SecP384r1MLKEM1024,
|
||||
}
|
||||
|
||||
var curveIDs []tls.CurveID
|
||||
|
||||
@@ -3,8 +3,6 @@ package tls
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"crypto/ecdh"
|
||||
"crypto/rand"
|
||||
"crypto/tls"
|
||||
"encoding/base64"
|
||||
"encoding/binary"
|
||||
@@ -23,8 +21,6 @@ import (
|
||||
"golang.org/x/net/http2"
|
||||
|
||||
"github.com/miekg/dns"
|
||||
"github.com/xtls/reality"
|
||||
"github.com/xtls/reality/hpke"
|
||||
"github.com/xtls/xray-core/common/errors"
|
||||
"github.com/xtls/xray-core/common/net"
|
||||
"github.com/xtls/xray-core/common/utils"
|
||||
@@ -330,34 +326,6 @@ func dnsQuery(server string, domain string, sockopt *internet.SocketConfig) ([]b
|
||||
return nil, dns2.DefaultTTL, nil
|
||||
}
|
||||
|
||||
// reference github.com/OmarTariq612/goech
|
||||
func MarshalBinary(ech reality.EchConfig) ([]byte, error) {
|
||||
var b cryptobyte.Builder
|
||||
b.AddUint16(ech.Version)
|
||||
b.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
child.AddUint8(ech.ConfigID)
|
||||
child.AddUint16(ech.KemID)
|
||||
child.AddUint16(uint16(len(ech.PublicKey)))
|
||||
child.AddBytes(ech.PublicKey)
|
||||
child.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
for _, cipherSuite := range ech.SymmetricCipherSuite {
|
||||
child.AddUint16(cipherSuite.KDFID)
|
||||
child.AddUint16(cipherSuite.AEADID)
|
||||
}
|
||||
})
|
||||
child.AddUint8(ech.MaxNameLength)
|
||||
child.AddUint8(uint8(len(ech.PublicName)))
|
||||
child.AddBytes(ech.PublicName)
|
||||
child.AddUint16LengthPrefixed(func(child *cryptobyte.Builder) {
|
||||
for _, extention := range ech.Extensions {
|
||||
child.AddUint16(extention.Type)
|
||||
child.AddBytes(extention.Data)
|
||||
}
|
||||
})
|
||||
})
|
||||
return b.Bytes()
|
||||
}
|
||||
|
||||
var ErrInvalidLen = errors.New("goech: invalid length")
|
||||
|
||||
func ConvertToGoECHKeys(data []byte) ([]tls.EncryptedClientHelloKey, error) {
|
||||
@@ -392,41 +360,3 @@ func ConvertToGoECHKeys(data []byte) ([]tls.EncryptedClientHelloKey, error) {
|
||||
}
|
||||
return keys, nil
|
||||
}
|
||||
|
||||
const ExtensionEncryptedClientHello = 0xfe0d
|
||||
const KDF_HKDF_SHA384 = 0x0002
|
||||
const KDF_HKDF_SHA512 = 0x0003
|
||||
|
||||
func GenerateECHKeySet(configID uint8, domain string, kem uint16) (reality.EchConfig, []byte, error) {
|
||||
config := reality.EchConfig{
|
||||
Version: ExtensionEncryptedClientHello,
|
||||
ConfigID: configID,
|
||||
PublicName: []byte(domain),
|
||||
KemID: kem,
|
||||
SymmetricCipherSuite: []reality.EchCipher{
|
||||
{KDFID: hpke.KDF_HKDF_SHA256, AEADID: hpke.AEAD_AES_128_GCM},
|
||||
{KDFID: hpke.KDF_HKDF_SHA256, AEADID: hpke.AEAD_AES_256_GCM},
|
||||
{KDFID: hpke.KDF_HKDF_SHA256, AEADID: hpke.AEAD_ChaCha20Poly1305},
|
||||
{KDFID: KDF_HKDF_SHA384, AEADID: hpke.AEAD_AES_128_GCM},
|
||||
{KDFID: KDF_HKDF_SHA384, AEADID: hpke.AEAD_AES_256_GCM},
|
||||
{KDFID: KDF_HKDF_SHA384, AEADID: hpke.AEAD_ChaCha20Poly1305},
|
||||
{KDFID: KDF_HKDF_SHA512, AEADID: hpke.AEAD_AES_128_GCM},
|
||||
{KDFID: KDF_HKDF_SHA512, AEADID: hpke.AEAD_AES_256_GCM},
|
||||
{KDFID: KDF_HKDF_SHA512, AEADID: hpke.AEAD_ChaCha20Poly1305},
|
||||
},
|
||||
MaxNameLength: 0,
|
||||
Extensions: nil,
|
||||
}
|
||||
// if kem == hpke.DHKEM_X25519_HKDF_SHA256 {
|
||||
curve := ecdh.X25519()
|
||||
priv := make([]byte, 32) //x25519
|
||||
_, err := io.ReadFull(rand.Reader, priv)
|
||||
if err != nil {
|
||||
return config, nil, err
|
||||
}
|
||||
privKey, _ := curve.NewPrivateKey(priv)
|
||||
config.PublicKey = privKey.PublicKey().Bytes()
|
||||
return config, priv, nil
|
||||
// }
|
||||
// TODO: add mlkem768 (former kyber768 draft00). The golang mlkem private key is 64 bytes seed?
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user