diff --git a/proxy/socks/protocol/udp.go b/proxy/socks/protocol/udp.go index 0a70bc76e..b87a59aed 100644 --- a/proxy/socks/protocol/udp.go +++ b/proxy/socks/protocol/udp.go @@ -22,6 +22,28 @@ func (request *Socks5UDPRequest) Destination() v2net.Destination { return v2net.NewUDPDestination(request.Address) } +func (request *Socks5UDPRequest) Bytes(buffer []byte) []byte { + if buffer == nil { + buffer = make([]byte, 0, 2*1024) + } + buffer = append(buffer, 0, 0, request.Fragment) + switch { + case request.Address.IsIPv4(): + buffer = append(buffer, AddrTypeIPv4) + buffer = append(buffer, request.Address.IP()...) + case request.Address.IsIPv6(): + buffer = append(buffer, AddrTypeIPv6) + buffer = append(buffer, request.Address.IP()...) + case request.Address.IsDomain(): + buffer = append(buffer, AddrTypeDomain) + buffer = append(buffer, byte(len(request.Address.Domain()))) + buffer = append(buffer, []byte(request.Address.Domain())...) + } + buffer = append(buffer, request.Address.PortBytes()...) + buffer = append(buffer, request.Data...) + return buffer +} + func ReadUDPRequest(packet []byte) (request Socks5UDPRequest, err error) { // packet[0] and packet[1] are reserved request.Fragment = packet[2] diff --git a/proxy/socks/udp.go b/proxy/socks/udp.go index e8842b97b..da655fcc0 100644 --- a/proxy/socks/udp.go +++ b/proxy/socks/udp.go @@ -54,15 +54,17 @@ func (server *SocksServer) AcceptPackets(conn *net.UDPConn) error { } udpPacket := v2net.NewPacket(request.Destination(), request.Data, false) - go server.handlePacket(conn, udpPacket, addr) + go server.handlePacket(conn, udpPacket, addr, request) } } -func (server *SocksServer) handlePacket(conn *net.UDPConn, packet v2net.Packet, clientAddr *net.UDPAddr) { +func (server *SocksServer) handlePacket(conn *net.UDPConn, packet v2net.Packet, clientAddr *net.UDPAddr, request protocol.Socks5UDPRequest) { ray := server.vPoint.DispatchToOutbound(packet) close(ray.InboundInput()) if data, ok := <-ray.InboundOutput(); ok { - conn.WriteToUDP(data, clientAddr) + request.Data = data + udpMessage := request.Bytes(nil) + nBytes, err := conn.WriteToUDP(udpMessage, clientAddr) } }