github.com/sagernet/sing@v0.2.6/common/bufio/vectorised_windows.go (about) 1 package bufio 2 3 import ( 4 "github.com/sagernet/sing/common/buf" 5 M "github.com/sagernet/sing/common/metadata" 6 7 "golang.org/x/sys/windows" 8 ) 9 10 func (w *SyscallVectorisedWriter) WriteVectorised(buffers []*buf.Buffer) error { 11 defer buf.ReleaseMulti(buffers) 12 iovecList := make([]*windows.WSABuf, len(buffers)) 13 for i, buffer := range buffers { 14 iovecList[i] = &windows.WSABuf{ 15 Len: uint32(buffer.Len()), 16 Buf: &buffer.Bytes()[0], 17 } 18 } 19 var n uint32 20 var innerErr error 21 err := w.rawConn.Write(func(fd uintptr) (done bool) { 22 innerErr = windows.WSASend(windows.Handle(fd), iovecList[0], uint32(len(iovecList)), &n, 0, nil, nil) 23 return innerErr != windows.WSAEWOULDBLOCK 24 }) 25 if innerErr != nil { 26 err = innerErr 27 } 28 return err 29 } 30 31 func (w *SyscallVectorisedPacketWriter) WriteVectorisedPacket(buffers []*buf.Buffer, destination M.Socksaddr) error { 32 defer buf.ReleaseMulti(buffers) 33 iovecList := make([]*windows.WSABuf, len(buffers)) 34 for i, buffer := range buffers { 35 iovecList[i] = &windows.WSABuf{ 36 Len: uint32(buffer.Len()), 37 Buf: &buffer.Bytes()[0], 38 } 39 } 40 var sockaddr windows.Sockaddr 41 if destination.IsIPv4() { 42 sockaddr = &windows.SockaddrInet4{ 43 Port: int(destination.Port), 44 Addr: destination.Addr.As4(), 45 } 46 } else { 47 sockaddr = &windows.SockaddrInet6{ 48 Port: int(destination.Port), 49 Addr: destination.Addr.As16(), 50 } 51 } 52 var n uint32 53 var innerErr error 54 err := w.rawConn.Write(func(fd uintptr) (done bool) { 55 innerErr = windows.WSASendto(windows.Handle(fd), iovecList[0], uint32(len(iovecList)), &n, 0, sockaddr, nil, nil) 56 return innerErr != windows.WSAEWOULDBLOCK 57 }) 58 if innerErr != nil { 59 err = innerErr 60 } 61 return err 62 }