Amir Khan 1 год назад
Родитель
Сommit
8e697f758d

+ 1 - 1
go.mod

@@ -40,7 +40,7 @@ require (
 	github.com/Psiphon-Labs/consistent v0.0.0-20240322131436-20aaa4e05737
 	github.com/Psiphon-Labs/goptlib v0.0.0-20200406165125-c0e32a7a3464
 	github.com/Psiphon-Labs/psiphon-tls v0.0.0-20250219165059-533f95b512e9
-	github.com/Psiphon-Labs/quic-go v0.0.0-20250226213529-818b69c11139
+	github.com/Psiphon-Labs/quic-go v0.0.0-20250303214000-94770c5d46a0
 	github.com/Psiphon-Labs/utls v0.0.0-20250228222508-0e6c20273fcc
 	github.com/armon/go-proxyproto v0.0.0-20180202201750-5b7edb60ff5f
 	github.com/bifurcation/mint v0.0.0-20180306135233-198357931e61

+ 2 - 2
go.sum

@@ -24,8 +24,8 @@ github.com/Psiphon-Labs/goptlib v0.0.0-20200406165125-c0e32a7a3464 h1:VmnMMMheFX
 github.com/Psiphon-Labs/goptlib v0.0.0-20200406165125-c0e32a7a3464/go.mod h1:Pe5BqN2DdIdChorAXl6bDaQd/wghpCleJfid2NoSli0=
 github.com/Psiphon-Labs/psiphon-tls v0.0.0-20250219165059-533f95b512e9 h1:PjzuvkU8C0My+ixI+FWiJYV9PbALsw8uA1F8HrqPG/w=
 github.com/Psiphon-Labs/psiphon-tls v0.0.0-20250219165059-533f95b512e9/go.mod h1:7ZUnPnWT5z8J8hxfsVjKHYK77Zme/Y0If1b/zeziiJs=
-github.com/Psiphon-Labs/quic-go v0.0.0-20250226213529-818b69c11139 h1:FG1ovy7+hwLuHRl59LOC937Q1pk6+tMkVRF4FeFWd5g=
-github.com/Psiphon-Labs/quic-go v0.0.0-20250226213529-818b69c11139/go.mod h1:rONdWgPMbFjyyBai7gB1IBF4pT9r4l0GyiDst5XR1SY=
+github.com/Psiphon-Labs/quic-go v0.0.0-20250303214000-94770c5d46a0 h1:E1L02sxaIDWp7c7KOmU2iQHodg7On6sB//i2BMWs//w=
+github.com/Psiphon-Labs/quic-go v0.0.0-20250303214000-94770c5d46a0/go.mod h1:rONdWgPMbFjyyBai7gB1IBF4pT9r4l0GyiDst5XR1SY=
 github.com/Psiphon-Labs/utls v0.0.0-20250228222508-0e6c20273fcc h1:ojzcP5Hia0pAidJvnNAd2DaA/siX9vPDTPC9kvhDRFY=
 github.com/Psiphon-Labs/utls v0.0.0-20250228222508-0e6c20273fcc/go.mod h1:1vv0gVAzq9e2XYkW8HAKrmtuuZrBdDixQFx5H22KAjI=
 github.com/alexbrainman/sspi v0.0.0-20231016080023-1a75b4708caa h1:LHTHcTQiSGT7VVbI0o4wBRNQIgn917usHWOd6VAffYI=

+ 1 - 1
psiphon/common/inproxy/inproxy_disabled.go

@@ -120,7 +120,7 @@ func (conn *webRTCConn) GetMetrics() common.LogFields {
 	return nil
 }
 
-func GetQUICMaxPacketSizeAdjustment(isIPv6 bool) int {
+func GetQUICMaxPacketSizeAdjustment() int {
 	return 0
 }
 

+ 2 - 2
psiphon/common/inproxy/inproxy_test.go

@@ -602,7 +602,7 @@ func runTestInproxy(doMustUpgrade bool) error {
 					nil,
 					nil,
 					disablePathMTUDiscovery,
-					GetQUICMaxPacketSizeAdjustment(false),
+					GetQUICMaxPacketSizeAdjustment(),
 					false,
 					false,
 					common.WrapClientSessionCache(tls.NewLRUClientSessionCache(0), ""),
@@ -1084,7 +1084,7 @@ func newQuicEchoServer() (*quicEchoServer, error) {
 		nil,
 		nil,
 		"127.0.0.1:0",
-		GetQUICMaxPacketSizeAdjustment(false),
+		GetQUICMaxPacketSizeAdjustment(),
 		obfuscationKey,
 		false)
 	if err != nil {

+ 5 - 11
psiphon/common/inproxy/webrtc.go

@@ -2003,7 +2003,7 @@ func (conn *webRTCConn) writeDataChannelMessage(p []byte, decoy bool) (int, erro
 // INPROXY-QUIC-OSSH must apply GetQUICMaxPacketSizeAdjustment on both the
 // client and server side. In addition, the client must disable
 // DisablePathMTUDiscovery.
-func GetQUICMaxPacketSizeAdjustment(isIPv6 bool) int {
+func GetQUICMaxPacketSizeAdjustment() int {
 
 	// Limitations:
 	//
@@ -2017,12 +2017,8 @@ func GetQUICMaxPacketSizeAdjustment(isIPv6 bool) int {
 	//   channel mode. Furthermore, the lower maximum QUIC packet size is
 	//   directly observable on the 2nd hop.
 
-	// common/quic.MAX_PRE_DISCOVERY_PACKET_SIZE_IPV4 = 1252
-	// common/quic.MAX_PRE_DISCOVERY_PACKET_SIZE_IPV6 = 1232
-	quicMTU := 1252
-	if isIPv6 {
-		quicMTU = 1232
-	}
+	// common/quic.MAX_PRE_DISCOVERY_PACKET_SIZE = 1280
+	quicMTU := 1280
 	targetMTUAdjustment := quicMTU - mediaTrackMaxUDPPayloadLength
 	if targetMTUAdjustment < 0 {
 		targetMTUAdjustment = 0
@@ -2351,8 +2347,7 @@ func (conn *webRTCConn) addRTPReliabilityLayer(ctx context.Context) error {
 			ClientSessionCache:     sessionCache,
 		}
 
-		isIPv6 := true // remote addr is synthetic uniqueIPv6Address
-		maxPacketSizeAdjustment := GetQUICMaxPacketSizeAdjustment(isIPv6)
+		maxPacketSizeAdjustment := GetQUICMaxPacketSizeAdjustment()
 
 		// Set ClientMaxPacketSizeAdjustment to so that quic-go will produce
 		// packets with a small enough max size to produce the overall target
@@ -2441,8 +2436,7 @@ func (conn *webRTCConn) addRTPReliabilityLayer(ctx context.Context) error {
 			MaxIncomingUniStreams:   -1,
 			VerifyClientHelloRandom: nil,
 			ServerMaxPacketSizeAdjustment: func(addr net.Addr) int {
-				isIPv6 := true // remote addr is synthetic uniqueIPv6Address
-				return GetQUICMaxPacketSizeAdjustment(isIPv6)
+				return GetQUICMaxPacketSizeAdjustment()
 			},
 		}
 

+ 7 - 21
psiphon/common/quic/obfuscator.go

@@ -53,14 +53,10 @@ const (
 
 	MAX_PACKET_SIZE = 1452
 
-	// MAX_PRE_DISCOVERY_PACKET_SIZE_IPV4/IPV6 are the largest packet sizes
-	// quic-go will produce before MTU discovery, 1280 less IP and UDP header
-	// sizes. These values, which match quic-go
-	// internal/protocol.InitialPacketSizeIPv4/IPv6, are used to calculate
-	// maximum padding sizes.
+	// MAX_PRE_DISCOVERY_PACKET_SIZE is the largest packet size quic-go will
+	// produce before MTU discovery.
 
-	MAX_PRE_DISCOVERY_PACKET_SIZE_IPV4 = 1252
-	MAX_PRE_DISCOVERY_PACKET_SIZE_IPV6 = 1232
+	MAX_PRE_DISCOVERY_PACKET_SIZE = 1280
 
 	// OBFUSCATED_MAX_PACKET_SIZE_ADJUSTMENT is the minimum amount of bytes
 	// required for obfuscation overhead, the nonce and the padding length.
@@ -429,7 +425,7 @@ func (conn *ObfuscatedPacketConn) readPacketWithType(
 				if atomic.CompareAndSwapInt32(&conn.decoyPacketCount, count, count-1) {
 
 					packetSize := conn.paddingPRNG.Range(
-						1, getMaxPreDiscoveryPacketSize(addr))
+						1, MAX_PRE_DISCOVERY_PACKET_SIZE)
 
 					// decoyBuffer is all zeros, so the QUIC Fixed Bit is zero.
 					// Ignore any errors when writing decoy packets.
@@ -775,7 +771,7 @@ func (conn *ObfuscatedPacketConn) writePacket(
 				}
 			}
 
-			maxPadding := getMaxPaddingSize(isIETF, addr, n)
+			maxPadding := getMaxPaddingSize(isIETF, n)
 
 			paddingLen := conn.paddingPRNG.Intn(maxPadding + 1)
 			buffer[NONCE_SIZE] = uint8(paddingLen)
@@ -843,19 +839,9 @@ func (conn *ObfuscatedPacketConn) writePacket(
 	return n, oobn, err
 }
 
-func getMaxPreDiscoveryPacketSize(addr net.Addr) int {
-	maxPacketSize := MAX_PRE_DISCOVERY_PACKET_SIZE_IPV4
-	if udpAddr, ok := addr.(*net.UDPAddr); ok &&
-		udpAddr != nil && udpAddr.IP != nil && udpAddr.IP.To4() == nil {
+func getMaxPaddingSize(isIETF bool, packetSize int) int {
 
-		maxPacketSize = MAX_PRE_DISCOVERY_PACKET_SIZE_IPV6
-	}
-	return maxPacketSize
-}
-
-func getMaxPaddingSize(isIETF bool, addr net.Addr, packetSize int) int {
-
-	maxPacketSize := getMaxPreDiscoveryPacketSize(addr)
+	maxPacketSize := MAX_PRE_DISCOVERY_PACKET_SIZE
 
 	maxPadding := 0
 

+ 1 - 14
psiphon/dialParameters.go

@@ -1298,20 +1298,7 @@ func MakeDialParameters(
 			// packet size must be adjusted to fit. In addition, QUIC path
 			// MTU discovery is disabled, to avoid sending oversized packets.
 
-			// isIPv6 indicates whether quic-go will use a max initial packet
-			// size appropriate for IPv6 or IPv4;
-			// GetQUICMaxPacketSizeAdjustment modifies the adjustment
-			// accordingly. quic-go selects based on the RemoteAddr of the
-			// net.PacketConn passed to quic.Dial. In the in-proxy case, that
-			// RemoteAddr, inproxy.ClientConn.RemoteAddr, is synthetic and
-			// can reflect inproxy.ClientConfig.RemoteAddrOverride, which, in
-			// turn, is currently based on serverEntry.IpAddress; see
-			// dialInproxy. Limitation: not compatible with FRONTED-QUIC.
-
-			IPAddress := net.ParseIP(serverEntry.IpAddress)
-			isIPv6 := IPAddress != nil && IPAddress.To4() == nil
-
-			dialParams.QUICMaxPacketSizeAdjustment = inproxy.GetQUICMaxPacketSizeAdjustment(isIPv6)
+			dialParams.QUICMaxPacketSizeAdjustment = inproxy.GetQUICMaxPacketSizeAdjustment()
 			dialParams.QUICDisablePathMTUDiscovery = true
 
 			// Select a QUIC variant that is compatible with WebRTC media

+ 1 - 4
psiphon/server/tunnelServer.go

@@ -193,10 +193,7 @@ func (server *TunnelServer) Run() error {
 				// this will result in suboptimal packet sizes (10s of bytes)
 				// and a corresponding different traffic shape on the 2nd hop.
 
-				IPAddress := net.ParseIP(support.Config.ServerIPAddress)
-				isIPv6 := IPAddress != nil && IPAddress.To4() == nil
-
-				maxPacketSizeAdjustment = inproxy.GetQUICMaxPacketSizeAdjustment(isIPv6)
+				maxPacketSizeAdjustment = inproxy.GetQUICMaxPacketSizeAdjustment()
 			}
 
 			logTunnelProtocol := tunnelProtocol

+ 12 - 0
vendor/github.com/Psiphon-Labs/quic-go/connection.go

@@ -1862,6 +1862,18 @@ func (s *connection) applyTransportParameters() {
 		maxPacketSize = params.MaxUDPPayloadSize
 	}
 
+	// [Psiphon]
+	// Adjust the max packet size to allow for obfuscation overhead.
+	maxPacketSizeAdjustment := 0
+	if s.config.ServerMaxPacketSizeAdjustment != nil {
+		maxPacketSizeAdjustment = s.config.ServerMaxPacketSizeAdjustment(s.conn.RemoteAddr())
+	} else {
+		maxPacketSizeAdjustment = s.config.ClientMaxPacketSizeAdjustment
+	}
+	if maxPacketSize > protocol.ByteCount(maxPacketSizeAdjustment) {
+		maxPacketSize -= protocol.ByteCount(maxPacketSizeAdjustment)
+	}
+
 	// [Psiphon]
 	initialMaxPacketSize := s.maxPacketSize()
 

+ 1 - 1
vendor/modules.txt

@@ -40,7 +40,7 @@ github.com/Psiphon-Labs/psiphon-tls/byteorder
 github.com/Psiphon-Labs/psiphon-tls/internal/boring
 github.com/Psiphon-Labs/psiphon-tls/internal/hpke
 github.com/Psiphon-Labs/psiphon-tls/internal/mlkem768
-# github.com/Psiphon-Labs/quic-go v0.0.0-20250226213529-818b69c11139
+# github.com/Psiphon-Labs/quic-go v0.0.0-20250303214000-94770c5d46a0
 ## explicit; go 1.23
 github.com/Psiphon-Labs/quic-go
 github.com/Psiphon-Labs/quic-go/http3