Skip to content

Commit

Permalink
Add quic fingerprints and preset configs
Browse files Browse the repository at this point in the history
  • Loading branch information
yuhan6665 committed Nov 2, 2024
1 parent 816f2bc commit 5eee4e0
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 3 deletions.
9 changes: 9 additions & 0 deletions transport/internet/http/dialer.go
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,15 @@ func getHTTPClient(ctx context.Context, dest net.Destination, streamSettings *in
},
}
transport = roundTripper

if fingerprint := tls.GetQuicFingerprint(tlsConfigs.Fingerprint); fingerprint != nil {
quicSpec, err := quic.QUICID2Spec(*fingerprint)
if err != nil {
errors.LogError(ctx, "unknown fingerprint: ", tlsConfigs.Fingerprint)
} else {
transport = http3.GetURoundTripper(roundTripper, &quicSpec, nil)
}
}
} else {
transportH2 := &http2.Transport{
DialTLSContext: func(hctx context.Context, string, addr string, tlsConfig *gotls.Config) (net.Conn, error) {
Expand Down
15 changes: 12 additions & 3 deletions transport/internet/splithttp/dialer.go
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ func getHTTPClient(ctx context.Context, dest net.Destination, streamSettings *in
}

muxManager = NewMuxManager(mux, func() interface{} {
return createHTTPClient(dest, streamSettings)
return createHTTPClient(ctx, dest, streamSettings)
})
globalDialerMap[key] = muxManager
}
Expand All @@ -82,7 +82,7 @@ func getHTTPClient(ctx context.Context, dest net.Destination, streamSettings *in
return res.Resource.(DialerClient), res
}

func createHTTPClient(dest net.Destination, streamSettings *internet.MemoryStreamConfig) DialerClient {
func createHTTPClient(ctx context.Context, dest net.Destination, streamSettings *internet.MemoryStreamConfig) DialerClient {
tlsConfig := tls.ConfigFromStreamSettings(streamSettings)
realityConfig := reality.ConfigFromStreamSettings(streamSettings)

Expand Down Expand Up @@ -145,7 +145,7 @@ func createHTTPClient(dest net.Destination, streamSettings *internet.MemoryStrea
MaxIncomingStreams: -1,
KeepAlivePeriod: h3KeepalivePeriod,
}
transport = &http3.RoundTripper{
roundTripper := &http3.RoundTripper{
QuicConfig: quicConfig,
TLSClientConfig: tls.CopyConfig(gotlsConfig),
Dial: func(ctx context.Context, addr string, tlsCfg *utls.Config, cfg *quic.Config) (quic.EarlyConnection, error) {
Expand Down Expand Up @@ -185,6 +185,15 @@ func createHTTPClient(dest net.Destination, streamSettings *internet.MemoryStrea
return quic.DialEarly(ctx, udpConn, udpAddr, tlsCfg, cfg)
},
}
transport = roundTripper
if fingerprint := tls.GetQuicFingerprint(tlsConfig.Fingerprint); fingerprint != nil {
quicSpec, err := quic.QUICID2Spec(*fingerprint)
if err != nil {
errors.LogError(ctx, "unknown fingerprint: ", tlsConfig.Fingerprint)
} else {
transport = http3.GetURoundTripper(roundTripper, &quicSpec, nil)
}
}
} else if isH2 {
transport = &http2.Transport{
DialTLSContext: func(ctxInner context.Context, network string, addr string, cfg *gotls.Config) (net.Conn, error) {
Expand Down
42 changes: 42 additions & 0 deletions transport/internet/tls/tls.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"math/big"
"time"

"github.com/refraction-networking/uquic"
utls "github.com/refraction-networking/utls"
"github.com/xtls/xray-core/common/buf"
"github.com/xtls/xray-core/common/net"
Expand Down Expand Up @@ -154,6 +155,18 @@ func init() {
}
i++
}

bigInt, _ = rand.Int(rand.Reader, big.NewInt(int64(len(QuicAllFingerprints))))
stopAt = int(bigInt.Int64())
i = 0
for _, v := range QuicAllFingerprints {
if i == stopAt {
QuicPresetFingerprints["random"] = v
break
}
i++
}

weights := utls.DefaultWeights
weights.TLSVersMax_Set_VersionTLS13 = 1
weights.FirstKeyShare_Set_CurveP256 = 0
Expand All @@ -179,6 +192,35 @@ func GetFingerprint(name string) (fingerprint *utls.ClientHelloID) {
return
}

func GetQuicFingerprint(name string) (fingerprint *quic.QUICID) {
if name == "" {
return
}
if fingerprint = QuicPresetFingerprints[name]; fingerprint != nil {
return
}
if fingerprint = QuicAllFingerprints[name]; fingerprint != nil {
return
}
return
}

var QuicPresetFingerprints = map[string]*quic.QUICID {
"chrome": &quic.QUICChrome_115,
"firefox": &quic.QUICFirefox_116,
"random": nil,
}

var QuicAllFingerprints = map[string]*quic.QUICID {
"quicchrome_115": &quic.QUICChrome_115,
"quicchrome_115_ipv4": &quic.QUICChrome_115_IPv4,
"quicchrome_115_ipv6": &quic.QUICChrome_115_IPv6,
"quicfirefox_116": &quic.QUICFirefox_116,
"quicfirefox_116a": &quic.QUICFirefox_116A,
"quicfirefox_116b": &quic.QUICFirefox_116B,
"quicfirefox_116c": &quic.QUICFirefox_116C,
}

var PresetFingerprints = map[string]*utls.ClientHelloID{
// Recommended preset options in GUI clients
"chrome": &utls.HelloChrome_Auto,
Expand Down

0 comments on commit 5eee4e0

Please sign in to comment.