Chore: bump to go1.18rc1, use netip.Addr to replace net.IP with system TUN stack
This commit is contained in:
@ -389,3 +389,9 @@ func genAddr(host string, port int, allowLan bool) string {
|
||||
|
||||
return fmt.Sprintf("127.0.0.1:%d", port)
|
||||
}
|
||||
|
||||
func Cleanup() {
|
||||
if tunStackListener != nil {
|
||||
_ = tunStackListener.Close()
|
||||
}
|
||||
}
|
||||
|
@ -64,11 +64,11 @@ func (t *TUN) Read(packet []byte) (int, error) {
|
||||
return t.nt.Read(packet, t.offset)
|
||||
}
|
||||
|
||||
buff := make([]byte, t.offset+int(t.mtu))
|
||||
buff := make([]byte, t.offset+cap(packet))
|
||||
|
||||
n, err := t.nt.Read(buff, t.offset)
|
||||
if err != nil {
|
||||
return n, err
|
||||
return 0, err
|
||||
}
|
||||
|
||||
copy(packet, buff[t.offset:t.offset+n])
|
||||
|
@ -1,7 +1,7 @@
|
||||
package commons
|
||||
|
||||
import (
|
||||
"net"
|
||||
"net/netip"
|
||||
"time"
|
||||
|
||||
"github.com/Dreamacro/clash/component/resolver"
|
||||
@ -11,17 +11,12 @@ import (
|
||||
|
||||
const DefaultDnsReadTimeout = time.Second * 10
|
||||
|
||||
func ShouldHijackDns(dnsAdds []net.IP, targetAddr net.IP, targetPort int) bool {
|
||||
if targetPort != 53 {
|
||||
return false
|
||||
}
|
||||
|
||||
for _, ip := range dnsAdds {
|
||||
if ip.IsUnspecified() || ip.Equal(targetAddr) {
|
||||
func ShouldHijackDns(dnsAdds []netip.AddrPort, targetAddr netip.AddrPort) bool {
|
||||
for _, addrPort := range dnsAdds {
|
||||
if addrPort == targetAddr || (addrPort.Addr().IsUnspecified() && targetAddr.Port() == 53) {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
|
||||
|
@ -7,7 +7,8 @@ import (
|
||||
|
||||
var ROUTES = []string{"1.0.0.0/8", "2.0.0.0/7", "4.0.0.0/6", "8.0.0.0/5", "16.0.0.0/4", "32.0.0.0/3", "64.0.0.0/2", "128.0.0.0/1"}
|
||||
|
||||
func IPv4MaskString(m net.IPMask) string {
|
||||
func IPv4MaskString(bits int) string {
|
||||
m := net.CIDRMask(bits, 32)
|
||||
if len(m) != 4 {
|
||||
panic("ipv4Mask: len must be 4 bytes")
|
||||
}
|
||||
|
@ -2,7 +2,7 @@ package commons
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net"
|
||||
"net/netip"
|
||||
|
||||
"github.com/Dreamacro/clash/common/cmd"
|
||||
"github.com/Dreamacro/clash/listener/tun/device"
|
||||
@ -12,14 +12,14 @@ func GetAutoDetectInterface() (string, error) {
|
||||
return cmd.ExecCmd("bash -c netstat -rnf inet | grep 'default' | awk -F ' ' 'NR==1{print $6}' | xargs echo -n")
|
||||
}
|
||||
|
||||
func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, autoRoute bool) error {
|
||||
func ConfigInterfaceAddress(dev device.Device, addr netip.Prefix, forceMTU int, autoRoute bool) error {
|
||||
interfaceName := dev.Name()
|
||||
if addr.IP.To4() == nil {
|
||||
if !addr.Addr().Is4() {
|
||||
return fmt.Errorf("supported ipv4 only")
|
||||
}
|
||||
|
||||
ip := addr.IP.String()
|
||||
netmask := IPv4MaskString(addr.Mask)
|
||||
ip := addr.Addr()
|
||||
netmask := IPv4MaskString(addr.Bits())
|
||||
cmdStr := fmt.Sprintf("ifconfig %s inet %s netmask %s %s", interfaceName, ip, netmask, ip)
|
||||
|
||||
_, err := cmd.ExecCmd(cmdStr)
|
||||
@ -27,10 +27,10 @@ func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, au
|
||||
return err
|
||||
}
|
||||
|
||||
_, err = cmd.ExecCmd(fmt.Sprintf("ipconfig set %s automatic-v6", interfaceName))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
// _, err = cmd.ExecCmd(fmt.Sprintf("ipconfig set %s automatic-v6", interfaceName))
|
||||
// if err != nil {
|
||||
// return err
|
||||
// }
|
||||
|
||||
if autoRoute {
|
||||
err = configInterfaceRouting(interfaceName, addr)
|
||||
@ -38,7 +38,7 @@ func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, au
|
||||
return err
|
||||
}
|
||||
|
||||
func configInterfaceRouting(interfaceName string, addr *net.IPNet) error {
|
||||
func configInterfaceRouting(interfaceName string, addr netip.Prefix) error {
|
||||
routes := append(ROUTES, addr.String())
|
||||
|
||||
for _, route := range routes {
|
||||
@ -47,7 +47,8 @@ func configInterfaceRouting(interfaceName string, addr *net.IPNet) error {
|
||||
}
|
||||
}
|
||||
|
||||
return execRouterCmd("add", "-inet6", "2000::/3", interfaceName)
|
||||
// return execRouterCmd("add", "-inet6", "2000::/3", interfaceName)
|
||||
return nil
|
||||
}
|
||||
|
||||
func execRouterCmd(action, inet, route string, interfaceName string) error {
|
||||
|
@ -2,7 +2,7 @@ package commons
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net"
|
||||
"net/netip"
|
||||
|
||||
"github.com/Dreamacro/clash/common/cmd"
|
||||
"github.com/Dreamacro/clash/listener/tun/device"
|
||||
@ -12,7 +12,7 @@ func GetAutoDetectInterface() (string, error) {
|
||||
return cmd.ExecCmd("bash -c ip route show | grep 'default via' | awk -F ' ' 'NR==1{print $5}' | xargs echo -n")
|
||||
}
|
||||
|
||||
func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, autoRoute bool) error {
|
||||
func ConfigInterfaceAddress(dev device.Device, addr netip.Prefix, forceMTU int, autoRoute bool) error {
|
||||
interfaceName := dev.Name()
|
||||
_, err := cmd.ExecCmd(fmt.Sprintf("ip addr add %s dev %s", addr.String(), interfaceName))
|
||||
if err != nil {
|
||||
@ -30,9 +30,9 @@ func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, au
|
||||
return err
|
||||
}
|
||||
|
||||
func configInterfaceRouting(interfaceName string, addr *net.IPNet) error {
|
||||
func configInterfaceRouting(interfaceName string, addr netip.Prefix) error {
|
||||
for _, route := range ROUTES {
|
||||
if err := execRouterCmd("add", route, interfaceName, addr.IP.String()); err != nil {
|
||||
if err := execRouterCmd("add", route, interfaceName, addr.Addr().String()); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ package commons
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net"
|
||||
"net/netip"
|
||||
"runtime"
|
||||
|
||||
"github.com/Dreamacro/clash/listener/tun/device"
|
||||
@ -14,6 +14,6 @@ func GetAutoDetectInterface() (string, error) {
|
||||
return "", fmt.Errorf("can not auto detect interface-name on this OS: %s, you must be detecting interface-name by manual", runtime.GOOS)
|
||||
}
|
||||
|
||||
func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, autoRoute bool) error {
|
||||
func ConfigInterfaceAddress(device.Device, netip.Prefix, int, bool) error {
|
||||
return fmt.Errorf("unsupported on this OS: %s", runtime.GOOS)
|
||||
}
|
||||
|
@ -1,11 +1,9 @@
|
||||
package commons
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"errors"
|
||||
"fmt"
|
||||
"net"
|
||||
"sort"
|
||||
"net/netip"
|
||||
"time"
|
||||
|
||||
"github.com/Dreamacro/clash/listener/tun/device"
|
||||
@ -25,7 +23,7 @@ func GetAutoDetectInterface() (string, error) {
|
||||
return getAutoDetectInterfaceByFamily(winipcfg.AddressFamily(windows.AF_INET6))
|
||||
}
|
||||
|
||||
func ConfigInterfaceAddress(dev device.Device, addr *net.IPNet, forceMTU int, autoRoute bool) error {
|
||||
func ConfigInterfaceAddress(dev device.Device, addr netip.Prefix, forceMTU int, autoRoute bool) error {
|
||||
retryOnFailure := StartedAtBoot()
|
||||
tryTimes := 0
|
||||
startOver:
|
||||
@ -38,41 +36,39 @@ startOver:
|
||||
tryTimes++
|
||||
|
||||
luid := winipcfg.LUID(dev.(*tun.TUN).LUID())
|
||||
|
||||
if guid, err1 := luid.GUID(); err1 == nil {
|
||||
log.Infoln("[wintun]: tun adapter GUID: %s", guid.String())
|
||||
}
|
||||
|
||||
tunAddress := ParseIPCidr(addr.String())
|
||||
addresses := []net.IPNet{tunAddress.IPNet()}
|
||||
addresses := []netip.Prefix{addr}
|
||||
|
||||
family := winipcfg.AddressFamily(windows.AF_INET)
|
||||
familyV6 := winipcfg.AddressFamily(windows.AF_INET6)
|
||||
|
||||
currentFamily := winipcfg.AddressFamily(windows.AF_INET6)
|
||||
if addr.IP.To4() != nil {
|
||||
if addr.Addr().Is4() {
|
||||
currentFamily = winipcfg.AddressFamily(windows.AF_INET)
|
||||
}
|
||||
|
||||
err = luid.FlushIPAddresses(familyV6)
|
||||
err = luid.FlushRoutes(windows.AF_INET6)
|
||||
if err == windows.ERROR_NOT_FOUND && retryOnFailure {
|
||||
goto startOver
|
||||
} else if err != nil {
|
||||
return err
|
||||
}
|
||||
err = luid.FlushDNS(family)
|
||||
err = luid.FlushIPAddresses(windows.AF_INET6)
|
||||
if err == windows.ERROR_NOT_FOUND && retryOnFailure {
|
||||
goto startOver
|
||||
} else if err != nil {
|
||||
return err
|
||||
}
|
||||
err = luid.FlushDNS(familyV6)
|
||||
err = luid.FlushDNS(windows.AF_INET6)
|
||||
if err == windows.ERROR_NOT_FOUND && retryOnFailure {
|
||||
goto startOver
|
||||
} else if err != nil {
|
||||
return err
|
||||
}
|
||||
err = luid.FlushRoutes(familyV6)
|
||||
err = luid.FlushDNS(windows.AF_INET)
|
||||
if err == windows.ERROR_NOT_FOUND && retryOnFailure {
|
||||
goto startOver
|
||||
} else if err != nil {
|
||||
@ -83,64 +79,39 @@ startOver:
|
||||
foundDefault6 := false
|
||||
|
||||
if autoRoute {
|
||||
allowedIPs := []*IPCidr{}
|
||||
routeArr := append(ROUTES, "224.0.0.0/4", "255.255.255.255/32")
|
||||
var allowedIPs []netip.Prefix
|
||||
routeArr := ROUTES
|
||||
|
||||
for _, route := range routeArr {
|
||||
allowedIPs = append(allowedIPs, ParseIPCidr(route))
|
||||
allowedIPs = append(allowedIPs, netip.MustParsePrefix(route))
|
||||
}
|
||||
|
||||
estimatedRouteCount := len(allowedIPs)
|
||||
routes := make([]winipcfg.RouteData, 0, estimatedRouteCount)
|
||||
var haveV4Address, haveV6Address bool = true, false
|
||||
routes := make(map[winipcfg.RouteData]bool, estimatedRouteCount)
|
||||
|
||||
for _, allowedip := range allowedIPs {
|
||||
allowedip.MaskSelf()
|
||||
if (allowedip.Bits() == 32 && !haveV4Address) || (allowedip.Bits() == 128 && !haveV6Address) {
|
||||
continue
|
||||
}
|
||||
route := winipcfg.RouteData{
|
||||
Destination: allowedip.IPNet(),
|
||||
Destination: allowedip.Masked(),
|
||||
Metric: 0,
|
||||
}
|
||||
if allowedip.Bits() == 32 {
|
||||
if allowedip.Cidr == 0 {
|
||||
if allowedip.Addr().Is4() {
|
||||
if allowedip.Bits() == 0 {
|
||||
foundDefault4 = true
|
||||
}
|
||||
route.NextHop = net.IPv4zero
|
||||
} else if allowedip.Bits() == 128 {
|
||||
if allowedip.Cidr == 0 {
|
||||
route.NextHop = netip.IPv4Unspecified()
|
||||
} else if allowedip.Addr().Is6() {
|
||||
if allowedip.Bits() == 0 {
|
||||
foundDefault6 = true
|
||||
}
|
||||
route.NextHop = net.IPv6zero
|
||||
route.NextHop = netip.IPv6Unspecified()
|
||||
}
|
||||
routes = append(routes, route)
|
||||
routes[route] = true
|
||||
}
|
||||
|
||||
deduplicatedRoutes := make([]*winipcfg.RouteData, 0, len(routes))
|
||||
sort.Slice(routes, func(i, j int) bool {
|
||||
if routes[i].Metric != routes[j].Metric {
|
||||
return routes[i].Metric < routes[j].Metric
|
||||
}
|
||||
if c := bytes.Compare(routes[i].NextHop, routes[j].NextHop); c != 0 {
|
||||
return c < 0
|
||||
}
|
||||
if c := bytes.Compare(routes[i].Destination.IP, routes[j].Destination.IP); c != 0 {
|
||||
return c < 0
|
||||
}
|
||||
if c := bytes.Compare(routes[i].Destination.Mask, routes[j].Destination.Mask); c != 0 {
|
||||
return c < 0
|
||||
}
|
||||
return false
|
||||
})
|
||||
for i := 0; i < len(routes); i++ {
|
||||
if i > 0 && routes[i].Metric == routes[i-1].Metric &&
|
||||
bytes.Equal(routes[i].NextHop, routes[i-1].NextHop) &&
|
||||
bytes.Equal(routes[i].Destination.IP, routes[i-1].Destination.IP) &&
|
||||
bytes.Equal(routes[i].Destination.Mask, routes[i-1].Destination.Mask) {
|
||||
continue
|
||||
}
|
||||
deduplicatedRoutes = append(deduplicatedRoutes, &routes[i])
|
||||
for route := range routes {
|
||||
r := route
|
||||
deduplicatedRoutes = append(deduplicatedRoutes, &r)
|
||||
}
|
||||
|
||||
err = luid.SetRoutesForFamily(family, deduplicatedRoutes)
|
||||
@ -167,6 +138,7 @@ startOver:
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
ipif.ForwardingEnabled = true
|
||||
ipif.RouterDiscoveryBehavior = winipcfg.RouterDiscoveryDisabled
|
||||
ipif.DadTransmits = 0
|
||||
ipif.ManagedAddressConfigurationSupported = false
|
||||
@ -208,28 +180,24 @@ startOver:
|
||||
return fmt.Errorf("unable to set v6 metric and MTU: %w", err)
|
||||
}
|
||||
|
||||
err = luid.SetDNS(family, []net.IP{net.ParseIP("198.18.0.2")}, nil)
|
||||
dnsAdds := []netip.Addr{netip.MustParseAddr("198.18.0.2")}
|
||||
err = luid.SetDNS(family, dnsAdds, nil)
|
||||
if err == windows.ERROR_NOT_FOUND && retryOnFailure {
|
||||
goto startOver
|
||||
} else if err != nil {
|
||||
return fmt.Errorf("unable to set DNS %s %s: %w", "198.18.0.2", "nil", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func cleanupAddressesOnDisconnectedInterfaces(family winipcfg.AddressFamily, addresses []net.IPNet) {
|
||||
func cleanupAddressesOnDisconnectedInterfaces(family winipcfg.AddressFamily, addresses []netip.Prefix) {
|
||||
if len(addresses) == 0 {
|
||||
return
|
||||
}
|
||||
addrToStr := func(ip *net.IP) string {
|
||||
if ip4 := ip.To4(); ip4 != nil {
|
||||
return string(ip4)
|
||||
}
|
||||
return string(*ip)
|
||||
}
|
||||
addrHash := make(map[string]bool, len(addresses))
|
||||
addrHash := make(map[netip.Addr]bool, len(addresses))
|
||||
for i := range addresses {
|
||||
addrHash[addrToStr(&addresses[i].IP)] = true
|
||||
addrHash[addresses[i].Addr()] = true
|
||||
}
|
||||
interfaces, err := winipcfg.GetAdaptersAddresses(family, winipcfg.GAAFlagDefault)
|
||||
if err != nil {
|
||||
@ -240,11 +208,10 @@ func cleanupAddressesOnDisconnectedInterfaces(family winipcfg.AddressFamily, add
|
||||
continue
|
||||
}
|
||||
for address := iface.FirstUnicastAddress; address != nil; address = address.Next {
|
||||
ip := address.Address.IP()
|
||||
if addrHash[addrToStr(&ip)] {
|
||||
ipnet := net.IPNet{IP: ip, Mask: net.CIDRMask(int(address.OnLinkPrefixLength), 8*len(ip))}
|
||||
log.Infoln("Cleaning up stale address %s from interface ‘%s’", ipnet.String(), iface.FriendlyName())
|
||||
iface.LUID.DeleteIPAddress(ipnet)
|
||||
if ip, _ := netip.AddrFromSlice(address.Address.IP()); addrHash[ip] {
|
||||
prefix := netip.PrefixFrom(ip, int(address.OnLinkPrefixLength))
|
||||
log.Infoln("Cleaning up stale address %s from interface ‘%s’", prefix.String(), iface.FriendlyName())
|
||||
iface.LUID.DeleteIPAddress(prefix)
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -255,27 +222,25 @@ func getAutoDetectInterfaceByFamily(family winipcfg.AddressFamily) (string, erro
|
||||
if err != nil {
|
||||
return "", fmt.Errorf("get ethernet interface failure. %w", err)
|
||||
}
|
||||
|
||||
var destination netip.Prefix
|
||||
if family == windows.AF_INET {
|
||||
destination = netip.PrefixFrom(netip.IPv4Unspecified(), 0)
|
||||
} else {
|
||||
destination = netip.PrefixFrom(netip.IPv6Unspecified(), 0)
|
||||
}
|
||||
|
||||
for _, iface := range interfaces {
|
||||
if iface.OperStatus != winipcfg.IfOperStatusUp {
|
||||
continue
|
||||
}
|
||||
|
||||
ifname := iface.FriendlyName()
|
||||
if ifname == "Clash" {
|
||||
continue
|
||||
}
|
||||
|
||||
for gatewayAddress := iface.FirstGatewayAddress; gatewayAddress != nil; gatewayAddress = gatewayAddress.Next {
|
||||
nextHop := gatewayAddress.Address.IP()
|
||||
nextHop, _ := netip.AddrFromSlice(gatewayAddress.Address.IP())
|
||||
|
||||
var ipnet net.IPNet
|
||||
if family == windows.AF_INET {
|
||||
ipnet = net.IPNet{IP: net.IPv4zero, Mask: net.CIDRMask(0, 32)}
|
||||
} else {
|
||||
ipnet = net.IPNet{IP: net.IPv6zero, Mask: net.CIDRMask(0, 128)}
|
||||
}
|
||||
|
||||
if _, err = iface.LUID.Route(ipnet, nextHop); err == nil {
|
||||
if _, err = iface.LUID.Route(destination, nextHop); err == nil {
|
||||
return ifname, nil
|
||||
}
|
||||
}
|
||||
|
@ -3,6 +3,7 @@ package gvisor
|
||||
import (
|
||||
"encoding/binary"
|
||||
"net"
|
||||
"net/netip"
|
||||
"time"
|
||||
|
||||
"github.com/Dreamacro/clash/adapter/inbound"
|
||||
@ -17,7 +18,7 @@ import (
|
||||
var _ adapter.Handler = (*GVHandler)(nil)
|
||||
|
||||
type GVHandler struct {
|
||||
DNSAdds []net.IP
|
||||
DNSAdds []netip.AddrPort
|
||||
|
||||
TCPIn chan<- C.ConnContext
|
||||
UDPIn chan<- *inbound.PacketAdapter
|
||||
@ -32,9 +33,12 @@ func (gh *GVHandler) HandleTCPConn(tunConn adapter.TCPConn) {
|
||||
Zone: "",
|
||||
}
|
||||
|
||||
if D.ShouldHijackDns(gh.DNSAdds, rAddr.IP, rAddr.Port) {
|
||||
addrIp, _ := netip.AddrFromSlice(rAddr.IP)
|
||||
addrPort := netip.AddrPortFrom(addrIp, id.LocalPort)
|
||||
|
||||
if D.ShouldHijackDns(gh.DNSAdds, addrPort) {
|
||||
go func() {
|
||||
log.Debugln("[TUN] hijack dns tcp: %s", rAddr.String())
|
||||
log.Debugln("[TUN] hijack dns tcp: %s", addrPort.String())
|
||||
|
||||
defer tunConn.Close()
|
||||
|
||||
@ -46,21 +50,21 @@ func (gh *GVHandler) HandleTCPConn(tunConn adapter.TCPConn) {
|
||||
|
||||
length := uint16(0)
|
||||
if err := binary.Read(tunConn, binary.BigEndian, &length); err != nil {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
if int(length) > len(buf) {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
n, err := tunConn.Read(buf[:length])
|
||||
if err != nil {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
msg, err := D.RelayDnsPacket(buf[:n])
|
||||
if err != nil {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
_, _ = tunConn.Write(msg)
|
||||
@ -82,6 +86,8 @@ func (gh *GVHandler) HandleUDPConn(tunConn adapter.UDPConn) {
|
||||
Zone: "",
|
||||
}
|
||||
|
||||
addrIp, _ := netip.AddrFromSlice(rAddr.IP)
|
||||
addrPort := netip.AddrPortFrom(addrIp, id.LocalPort)
|
||||
target := socks5.ParseAddrToSocksAddr(rAddr)
|
||||
|
||||
go func() {
|
||||
@ -91,12 +97,12 @@ func (gh *GVHandler) HandleUDPConn(tunConn adapter.UDPConn) {
|
||||
n, addr, err := tunConn.ReadFrom(buf)
|
||||
if err != nil {
|
||||
pool.Put(buf)
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
payload := buf[:n]
|
||||
|
||||
if D.ShouldHijackDns(gh.DNSAdds, rAddr.IP, rAddr.Port) {
|
||||
if D.ShouldHijackDns(gh.DNSAdds, addrPort) {
|
||||
go func() {
|
||||
defer pool.Put(buf)
|
||||
|
||||
|
@ -4,6 +4,7 @@ import (
|
||||
"encoding/binary"
|
||||
"io"
|
||||
"net"
|
||||
"net/netip"
|
||||
"strconv"
|
||||
"time"
|
||||
|
||||
@ -35,9 +36,10 @@ func (s sysStack) Close() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
var _, ipv4LoopBack, _ = net.ParseCIDR("127.0.0.0/8")
|
||||
var ipv4LoopBack = netip.MustParsePrefix("127.0.0.0/8")
|
||||
|
||||
func New(device device.Device, dnsHijack []net.IP, portal net.IP, tcpIn chan<- C.ConnContext, udpIn chan<- *inbound.PacketAdapter) (ipstack.Stack, error) {
|
||||
func New(device device.Device, dnsHijack []netip.AddrPort, tunAddress netip.Prefix, tcpIn chan<- C.ConnContext, udpIn chan<- *inbound.PacketAdapter) (ipstack.Stack, error) {
|
||||
portal := tunAddress.Addr()
|
||||
gateway := portal
|
||||
|
||||
stack, err := tun2socket.StartTun2Socket(device, gateway, portal)
|
||||
@ -64,15 +66,18 @@ func New(device device.Device, dnsHijack []net.IP, portal net.IP, tcpIn chan<- C
|
||||
lAddr := conn.LocalAddr().(*net.TCPAddr)
|
||||
rAddr := conn.RemoteAddr().(*net.TCPAddr)
|
||||
|
||||
if ipv4LoopBack.Contains(rAddr.IP) {
|
||||
addrIp, _ := netip.AddrFromSlice(rAddr.IP)
|
||||
addrPort := netip.AddrPortFrom(addrIp, uint16(rAddr.Port))
|
||||
|
||||
if ipv4LoopBack.Contains(addrIp) {
|
||||
conn.Close()
|
||||
|
||||
continue
|
||||
}
|
||||
|
||||
if D.ShouldHijackDns(dnsAddr, rAddr.IP, rAddr.Port) {
|
||||
if D.ShouldHijackDns(dnsAddr, addrPort) {
|
||||
go func() {
|
||||
log.Debugln("[TUN] hijack dns tcp: %s", rAddr.String())
|
||||
log.Debugln("[TUN] hijack dns tcp: %s", addrPort.String())
|
||||
|
||||
defer conn.Close()
|
||||
|
||||
@ -84,21 +89,21 @@ func New(device device.Device, dnsHijack []net.IP, portal net.IP, tcpIn chan<- C
|
||||
|
||||
length := uint16(0)
|
||||
if err := binary.Read(conn, binary.BigEndian, &length); err != nil {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
if int(length) > len(buf) {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
n, err := conn.Read(buf[:length])
|
||||
if err != nil {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
msg, err := D.RelayDnsPacket(buf[:n])
|
||||
if err != nil {
|
||||
return
|
||||
break
|
||||
}
|
||||
|
||||
_, _ = conn.Write(msg)
|
||||
@ -139,13 +144,16 @@ func New(device device.Device, dnsHijack []net.IP, portal net.IP, tcpIn chan<- C
|
||||
lAddr := lRAddr.(*net.UDPAddr)
|
||||
rAddr := rRAddr.(*net.UDPAddr)
|
||||
|
||||
if ipv4LoopBack.Contains(rAddr.IP) {
|
||||
addrIp, _ := netip.AddrFromSlice(rAddr.IP)
|
||||
addrPort := netip.AddrPortFrom(addrIp, uint16(rAddr.Port))
|
||||
|
||||
if ipv4LoopBack.Contains(addrIp) {
|
||||
pool.Put(buf)
|
||||
|
||||
continue
|
||||
}
|
||||
|
||||
if D.ShouldHijackDns(dnsAddr, rAddr.IP, rAddr.Port) {
|
||||
if D.ShouldHijackDns(dnsAddr, addrPort) {
|
||||
go func() {
|
||||
defer pool.Put(buf)
|
||||
|
||||
@ -156,7 +164,7 @@ func New(device device.Device, dnsHijack []net.IP, portal net.IP, tcpIn chan<- C
|
||||
|
||||
_, _ = stack.UDP().WriteTo(msg, rAddr, lAddr)
|
||||
|
||||
log.Debugln("[TUN] hijack dns udp: %s", rAddr.String())
|
||||
log.Debugln("[TUN] hijack dns udp: %s", addrPort.String())
|
||||
}()
|
||||
|
||||
continue
|
||||
|
@ -2,7 +2,7 @@ package tun
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net"
|
||||
"net/netip"
|
||||
"net/url"
|
||||
"runtime"
|
||||
"strings"
|
||||
@ -28,7 +28,7 @@ func New(tunConf *config.Tun, tcpIn chan<- C.ConnContext, udpIn chan<- *inbound.
|
||||
devName = generateDeviceName()
|
||||
}
|
||||
|
||||
tunAddrIPNet := &net.IPNet{IP: net.IP{198, 18, 0, 1}, Mask: net.CIDRMask(16, 32)}
|
||||
tunAddress := netip.MustParsePrefix("198.18.0.1/16")
|
||||
autoRoute := tunConf.AutoRoute
|
||||
stackType := tunConf.Stack
|
||||
mtu := 9000
|
||||
@ -71,7 +71,7 @@ func New(tunConf *config.Tun, tcpIn chan<- C.ConnContext, udpIn chan<- *inbound.
|
||||
return nil, fmt.Errorf("can't attach endpoint to tun: %w", err)
|
||||
}
|
||||
|
||||
tunStack, err = system.New(tunDevice, tunConf.DNSHijack, tunAddrIPNet.IP, tcpIn, udpIn)
|
||||
tunStack, err = system.New(tunDevice, tunConf.DNSHijack, tunAddress, tcpIn, udpIn)
|
||||
if err != nil {
|
||||
_ = tunDevice.Close()
|
||||
return nil, fmt.Errorf("can't New system stack: %w", err)
|
||||
@ -81,7 +81,7 @@ func New(tunConf *config.Tun, tcpIn chan<- C.ConnContext, udpIn chan<- *inbound.
|
||||
}
|
||||
|
||||
// setting address and routing
|
||||
err = commons.ConfigInterfaceAddress(tunDevice, tunAddrIPNet, mtu, autoRoute)
|
||||
err = commons.ConfigInterfaceAddress(tunDevice, tunAddress, mtu, autoRoute)
|
||||
if err != nil {
|
||||
_ = tunDevice.Close()
|
||||
return nil, fmt.Errorf("setting interface address and routing failed: %w", err)
|
||||
@ -89,7 +89,7 @@ func New(tunConf *config.Tun, tcpIn chan<- C.ConnContext, udpIn chan<- *inbound.
|
||||
|
||||
setAtLatest(stackType)
|
||||
|
||||
log.Infoln("TUN stack listening at: %s(%s), mtu: %d, auto route: %v, ip stack: %s", tunDevice.Name(), tunAddrIPNet.IP.String(), mtu, autoRoute, stackType)
|
||||
log.Infoln("TUN stack listening at: %s(%s), mtu: %d, auto route: %v, ip stack: %s", tunDevice.Name(), tunAddress.Addr().String(), mtu, autoRoute, stackType)
|
||||
return tunStack, nil
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user