diff --git a/common.go b/common.go index bd14b98..8b19ccf 100644 --- a/common.go +++ b/common.go @@ -562,6 +562,8 @@ type Config struct { MaxTimeDiff time.Duration ShortIds map[[8]byte]bool + Mldsa65Key []byte + LimitFallbackUpload LimitFallback LimitFallbackDownload LimitFallback diff --git a/go.mod b/go.mod index 9588881..8decec6 100644 --- a/go.mod +++ b/go.mod @@ -3,9 +3,16 @@ module github.com/xtls/reality go 1.24 require ( + github.com/cloudflare/circl v1.6.1 github.com/juju/ratelimit v1.0.2 github.com/pires/go-proxyproto v0.8.1 - github.com/refraction-networking/utls v1.7.3 - golang.org/x/crypto v0.39.0 - golang.org/x/sys v0.33.0 + github.com/refraction-networking/utls v1.8.0 + golang.org/x/crypto v0.40.0 + golang.org/x/sys v0.34.0 +) + +require ( + github.com/andybalholm/brotli v1.0.6 // indirect + github.com/klauspost/compress v1.17.4 // indirect + gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c // indirect ) diff --git a/go.sum b/go.sum index ea33dbf..6d478f7 100644 --- a/go.sum +++ b/go.sum @@ -1,10 +1,23 @@ +github.com/andybalholm/brotli v1.0.6 h1:Yf9fFpf49Zrxb9NlQaluyE92/+X7UVHlhMNJN2sxfOI= +github.com/andybalholm/brotli v1.0.6/go.mod h1:fO7iG3H7G2nSZ7m0zPUDn85XEX2GTukHGRSepvi9Eig= +github.com/cloudflare/circl v1.6.1 h1:zqIqSPIndyBh1bjLVVDHMPpVKqp8Su/V+6MeDzzQBQ0= +github.com/cloudflare/circl v1.6.1/go.mod h1:uddAzsPgqdMAYatqJ0lsjX1oECcQLIlRpzZh3pJrofs= github.com/juju/ratelimit v1.0.2 h1:sRxmtRiajbvrcLQT7S+JbqU0ntsb9W2yhSdNN8tWfaI= github.com/juju/ratelimit v1.0.2/go.mod h1:qapgC/Gy+xNh9UxzV13HGGl/6UXNN+ct+vwSgWNm/qk= +github.com/klauspost/compress v1.17.4 h1:Ej5ixsIri7BrIjBkRZLTo6ghwrEtHFk7ijlczPW4fZ4= +github.com/klauspost/compress v1.17.4/go.mod h1:/dCuZOvVtNoHsyb+cuJD3itjs3NbnF6KH9zAO4BDxPM= +github.com/kr/pretty v0.2.1 h1:Fmg33tUaq4/8ym9TJN1x7sLJnHVwhP33CNkpYV/7rwI= +github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI= +github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE= +github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/pires/go-proxyproto v0.8.1 h1:9KEixbdJfhrbtjpz/ZwCdWDD2Xem0NZ38qMYaASJgp0= github.com/pires/go-proxyproto v0.8.1/go.mod h1:ZKAAyp3cgy5Y5Mo4n9AlScrkCZwUy0g3Jf+slqQVcuU= -github.com/refraction-networking/utls v1.7.3 h1:L0WRhHY7Oq1T0zkdzVZMR6zWZv+sXbHB9zcuvsAEqCo= -github.com/refraction-networking/utls v1.7.3/go.mod h1:TUhh27RHMGtQvjQq+RyO11P6ZNQNBb3N0v7wsEjKAIQ= -golang.org/x/crypto v0.39.0 h1:SHs+kF4LP+f+p14esP5jAoDpHU8Gu/v9lFRK6IT5imM= -golang.org/x/crypto v0.39.0/go.mod h1:L+Xg3Wf6HoL4Bn4238Z6ft6KfEpN0tJGo53AAPC632U= -golang.org/x/sys v0.33.0 h1:q3i8TbbEz+JRD9ywIRlyRAQbM0qF7hu24q3teo2hbuw= -golang.org/x/sys v0.33.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= +github.com/refraction-networking/utls v1.8.0 h1:L38krhiTAyj9EeiQQa2sg+hYb4qwLCqdMcpZrRfbONE= +github.com/refraction-networking/utls v1.8.0/go.mod h1:jkSOEkLqn+S/jtpEHPOsVv/4V4EVnelwbMQl4vCWXAM= +golang.org/x/crypto v0.40.0 h1:r4x+VvoG5Fm+eJcxMaY8CQM7Lb0l1lsmjGBQ6s8BfKM= +golang.org/x/crypto v0.40.0/go.mod h1:Qr1vMER5WyS2dfPHAlsOj01wgLbsyWtFn/aY+5+ZdxY= +golang.org/x/sys v0.34.0 h1:H5Y5sJ2L2JRdyv7ROF1he/lPdvFsd0mJHFw2ThKHxLA= +golang.org/x/sys v0.34.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= +gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q= diff --git a/handshake_server_tls13.go b/handshake_server_tls13.go index 0fad34a..cae3317 100644 --- a/handshake_server_tls13.go +++ b/handshake_server_tls13.go @@ -16,6 +16,7 @@ import ( "crypto/rsa" "crypto/sha512" "crypto/x509" + "crypto/x509/pkix" "encoding/binary" "errors" "fmt" @@ -26,6 +27,7 @@ import ( "sort" "time" + "github.com/cloudflare/circl/sign/mldsa/mldsa65" "github.com/xtls/reality/fips140tls" "github.com/xtls/reality/hpke" "github.com/xtls/reality/tls13" @@ -70,19 +72,26 @@ type serverHandshakeStateTLS13 struct { } var ( - ed25519Priv ed25519.PrivateKey - signedCert []byte + ed25519Priv ed25519.PrivateKey + signedCert []byte + signedCertMldsa65 []byte ) func init() { certificate := x509.Certificate{SerialNumber: &big.Int{}} + certificateMldsa65 := x509.Certificate{SerialNumber: &big.Int{}, ExtraExtensions: []pkix.Extension{{Id: []int{0, 0}, Value: empty[:3309]}}} _, ed25519Priv, _ = ed25519.GenerateKey(rand.Reader) signedCert, _ = x509.CreateCertificate(rand.Reader, &certificate, &certificate, ed25519.PublicKey(ed25519Priv[32:]), ed25519Priv) + signedCertMldsa65, _ = x509.CreateCertificate(rand.Reader, &certificateMldsa65, &certificateMldsa65, ed25519.PublicKey(ed25519Priv[32:]), ed25519Priv) } func (hs *serverHandshakeStateTLS13) handshake() error { c := hs.c - + if c.config.Show { + remoteAddr := c.RemoteAddr().String() + fmt.Printf("REALITY remoteAddr: %v\tis using X25519MLKEM768 for TLS' communication: %v\n", remoteAddr, hs.hello.serverShare.group == X25519MLKEM768) + fmt.Printf("REALITY remoteAddr: %v\tis using ML-DSA-65 for cert's extra signature: %v\n", remoteAddr, len(c.config.Mldsa65Key) > 0) + } // For an overview of the TLS 1.3 handshake, see RFC 8446, Section 2. /* if err := hs.processClientHello(); err != nil { @@ -130,14 +139,26 @@ func (hs *serverHandshakeStateTLS13) handshake() error { } */ { - signedCert := append([]byte{}, signedCert...) + var cert []byte + if len(c.config.Mldsa65Key) > 0 { + cert = bytes.Clone(signedCertMldsa65) + } else { + cert = bytes.Clone(signedCert) + } h := hmac.New(sha512.New, c.AuthKey) h.Write(ed25519Priv[32:]) - h.Sum(signedCert[:len(signedCert)-64]) + h.Sum(cert[:len(cert)-64]) + + if len(c.config.Mldsa65Key) > 0 { + h.Write(hs.clientHello.original) + h.Write(hs.hello.original) + key, _ := mldsa65.Scheme().UnmarshalBinaryPrivateKey(c.config.Mldsa65Key) + mldsa65.SignTo(key.(*mldsa65.PrivateKey), h.Sum(nil), nil, false, cert[126:]) // fixed location + } hs.cert = &Certificate{ - Certificate: [][]byte{signedCert}, + Certificate: [][]byte{cert}, PrivateKey: ed25519Priv, } hs.sigAlg = Ed25519