github.com/sagernet/sing@v0.4.0-beta.19.0.20240518125136-f67a0988a636/common/control/frag_windows.go (about)

     1  package control
     2  
     3  import (
     4  	"os"
     5  	"syscall"
     6  
     7  	N "github.com/sagernet/sing/common/network"
     8  
     9  	"golang.org/x/sys/windows"
    10  )
    11  
    12  const (
    13  	IP_MTU_DISCOVER   = 71
    14  	IPV6_MTU_DISCOVER = 71
    15  )
    16  
    17  // enum PMTUD_STATE from ws2ipdef.h
    18  const (
    19  	IP_PMTUDISC_NOT_SET = iota
    20  	IP_PMTUDISC_DO
    21  	IP_PMTUDISC_DONT
    22  	IP_PMTUDISC_PROBE
    23  	IP_PMTUDISC_MAX
    24  )
    25  
    26  func DisableUDPFragment() Func {
    27  	return func(network, address string, conn syscall.RawConn) error {
    28  		switch N.NetworkName(network) {
    29  		case N.NetworkUDP:
    30  		default:
    31  			return nil
    32  		}
    33  		return Raw(conn, func(fd uintptr) error {
    34  			if err := windows.SetsockoptInt(windows.Handle(fd), windows.IPPROTO_IP, IP_MTU_DISCOVER, IP_PMTUDISC_DO); err != nil {
    35  				return os.NewSyscallError("SETSOCKOPT IP_MTU_DISCOVER IP_PMTUDISC_DO", err)
    36  			}
    37  			if network == "udp6" {
    38  				if err := windows.SetsockoptInt(windows.Handle(fd), windows.IPPROTO_IPV6, IPV6_MTU_DISCOVER, IP_PMTUDISC_DO); err != nil {
    39  					return os.NewSyscallError("SETSOCKOPT IPV6_MTU_DISCOVER IP_PMTUDISC_DO", err)
    40  				}
    41  			}
    42  			return nil
    43  		})
    44  	}
    45  }