func ipToSocksAddr(family int, ip net.IP, port int, zone string) (unix.Sockaddr, error) { switch family { case unix.AF_INET: if len(ip) == 0 { ip = net.IPv4zero } if ip = ip.To4(); ip == nil { return nil, net.InvalidAddrError("non-IPv4 address") } sa := new(unix.SockaddrInet4) for i := 0; i < net.IPv4len; i++ { sa.Addr[i] = ip[i] } sa.Port = port return sa, nil case unix.AF_INET6: if len(ip) == 0 { ip = net.IPv6zero } // IPv4 callers use 0.0.0.0 to mean "announce on any available address". // In IPv6 mode, Linux treats that as meaning "announce on 0.0.0.0", // which it refuses to do. Rewrite to the IPv6 unspecified address. if ip.Equal(net.IPv4zero) { ip = net.IPv6zero } if ip = ip.To16(); ip == nil { return nil, net.InvalidAddrError("non-IPv6 address") } sa := new(unix.SockaddrInet6) for i := 0; i < net.IPv6len; i++ { sa.Addr[i] = ip[i] } sa.Port = port sa.ZoneId = uint32(zoneToInt(zone)) return sa, nil } return nil, net.InvalidAddrError("unexpected socket family") }