From fac3de27d3858be700498b6722c8531e1eab08b8 Mon Sep 17 00:00:00 2001 From: e1732a364fed <75717694+e1732a364fed@users.noreply.github.com> Date: Sat, 1 Jan 2000 00:00:00 +0000 Subject: [PATCH] =?UTF-8?q?=E4=BF=AE=E8=AE=A2tun=20auto=20route=E4=BB=A3?= =?UTF-8?q?=E7=A0=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- examples/tun.client.toml | 5 +- proxy/tun/route_darwin.go | 117 +++++++++++++++++++------------------ proxy/tun/route_windows.go | 117 ++++++++++++++++++++----------------- 3 files changed, 130 insertions(+), 109 deletions(-) diff --git a/examples/tun.client.toml b/examples/tun.client.toml index b5bbc95..33a062a 100644 --- a/examples/tun.client.toml +++ b/examples/tun.client.toml @@ -7,7 +7,10 @@ # 对于小白来说,下面的指导太过于高级,难以看懂,因此对于小白来说推荐全自动化的方案。 # 在macos上, 配置路由表还需要在tun设备建立之后才能进行,因为tun设备的名称是无法自定义的 -# 在macos上, 需要管理员权限(sudo)运行vs_gui 才能 成功自动创建tun设备 +# 需要管理员权限(sudo)运行vs_gui 才能自动修改路由表 或者创建tun设备 + +# 在windows上,目前的tun实际上由tap执行, 程序不会主动试图创建tap设备 +# 而是需要 Tap-windows 虚拟网卡安装好,(Tap-Windows Provider V9 Network adapters) ############################################################### diff --git a/proxy/tun/route_darwin.go b/proxy/tun/route_darwin.go index a753084..d30402a 100644 --- a/proxy/tun/route_darwin.go +++ b/proxy/tun/route_darwin.go @@ -16,7 +16,6 @@ func init() { utils.Warn("tun auto route called, but no direct list given. auto route will not run.") } - var ok = false params := "-nr -f inet" out, err := exec.Command("netstat", strings.Split(params, " ")...).Output() if err != nil { @@ -25,68 +24,74 @@ func init() { } return } - //log.Println(string(out)) - lines := strings.Split(string(out), "\n") - for i, l := range lines { + + startLineIndex := -1 + fields := strings.Split(string(out), "\n") + for i, l := range fields { if strings.HasPrefix(l, "Destination") { - if i < len(lines)-1 && strings.HasPrefix(lines[i+1], "default") { - str := utils.StandardizeSpaces(lines[i+1]) - lines = strings.Split(str, " ") - //log.Println(lines, len(lines)) + if i < len(fields)-1 && strings.HasPrefix(fields[i+1], "default") { + startLineIndex = i + 1 - if len(lines) > 1 { - routerIP := lines[1] - if ce := utils.CanLogInfo("auto route: Your router's ip should be"); ce != nil { - ce.Write(zap.String("ip", routerIP)) - } - rememberedRouterIP = routerIP - - params1 := "delete -host default" - out1, err := exec.Command("route", strings.Split(params1, " ")...).Output() - - //这里err只能捕获没有权限运行等错误; 如果路由表修改失败,是不会返回err的 - - errStep: - if ce := utils.CanLogInfo("auto route delete default"); ce != nil { - ce.Write(zap.String("output", string(out1))) - } - - if err != nil { - if ce := utils.CanLogErr("auto route failed"); ce != nil { - ce.Write(zap.Error(err)) - } - return - } - - params1 = "add default -interface " + tunDevName - out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() - if err != nil { - goto errStep - } - if ce := utils.CanLogInfo("auto route add tun"); ce != nil { - ce.Write(zap.String("output", string(out1))) - } - - for _, v := range directList { - params1 = "add -host " + v + " " + rememberedRouterIP - out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() - if err != nil { - goto errStep - } - if ce := utils.CanLogInfo("auto route add direct"); ce != nil { - ce.Write(zap.String("output", string(out1))) - } - } - - ok = true - } } break } } - if !ok { - utils.Warn("auto route failed") + if startLineIndex < 0 { + utils.Warn("auto route failed, parse netstat output failed,1") + return } + str := utils.StandardizeSpaces(fields[startLineIndex]) + fields = strings.Split(str, " ") + + if len(fields) <= 1 { + utils.Warn("auto route failed, parse netstat output failed,2") + return + + } + routerIP := fields[1] + if ce := utils.CanLogInfo("auto route: Your router's ip should be"); ce != nil { + ce.Write(zap.String("ip", routerIP)) + } + rememberedRouterIP = routerIP + + params1 := "delete -host default" + out1, err := exec.Command("route", strings.Split(params1, " ")...).Output() + + //这里err只能捕获没有权限运行等错误; 如果路由表修改失败,是不会返回err的 + + checkErrStep: + if ce := utils.CanLogInfo("auto route delete default"); ce != nil { + ce.Write(zap.String("output", string(out1))) + } + + if err != nil { + if ce := utils.CanLogErr("auto route failed"); ce != nil { + ce.Write(zap.Error(err)) + } + return + } + + params1 = "add default -interface " + tunDevName + out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() + if err != nil { + goto checkErrStep + } + if ce := utils.CanLogInfo("auto route add tun"); ce != nil { + ce.Write(zap.String("output", string(out1))) + } + + for _, v := range directList { + params1 = "add -host " + v + " " + rememberedRouterIP + out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() + if err != nil { + goto checkErrStep + } + if ce := utils.CanLogInfo("auto route add direct"); ce != nil { + ce.Write(zap.String("output", string(out1))) + } + } + + utils.Warn("auto route succeed!") } autoRouteDownFunc = func(tunDevName, tunGateway, tunIP string, directList []string) { diff --git a/proxy/tun/route_windows.go b/proxy/tun/route_windows.go index 6980116..cfaf4b9 100644 --- a/proxy/tun/route_windows.go +++ b/proxy/tun/route_windows.go @@ -12,7 +12,6 @@ var rememberedRouterIP string func init() { autoRouteFunc = func(tunDevName, tunGateway, tunIP string, directList []string) { - var ok = false params := "-nr" out, err := exec.Command("netstat", params).Output() if err != nil { @@ -23,65 +22,79 @@ func init() { } //log.Println(string(out)) lines := strings.Split(string(out), "\n") + startLineIndex := -1 for i, l := range lines { if strings.HasPrefix(l, "IPv4 Route Table") { if i < len(lines)-3 && strings.HasPrefix(lines[i+3], "Network") { - str := utils.StandardizeSpaces(lines[i+4]) - fields := strings.Split(str, " ") - - if len(fields) > 3 { - routerIP := fields[2] - if ce := utils.CanLogInfo("auto route: Your router's ip should be"); ce != nil { - ce.Write(zap.String("ip", routerIP)) - } - rememberedRouterIP = routerIP - - params1 := "delete 0.0.0.0 mask 0.0.0.0" - out1, err := exec.Command("route", strings.Split(params1, " ")...).Output() - - //这里err只能捕获没有权限运行等错误; 如果路由表修改失败,是不会返回err的 - - errStep: - if ce := utils.CanLogInfo("auto route delete default"); ce != nil { - ce.Write(zap.String("output", string(out1))) - } - - if err != nil { - if ce := utils.CanLogErr("auto route failed"); ce != nil { - ce.Write(zap.Error(err)) - } - return - } - - params1 = "add 0.0.0.0 mask 0.0.0.0 " + tunGateway + " metric 6" - out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() - if err != nil { - goto errStep - } - if ce := utils.CanLogInfo("auto route add tun"); ce != nil { - ce.Write(zap.String("output", string(out1))) - } - - for _, v := range directList { - params1 = "add " + v + " " + rememberedRouterIP + " metric 5" - out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() - if err != nil { - goto errStep - } - if ce := utils.CanLogInfo("auto route add direct"); ce != nil { - ce.Write(zap.String("output", string(out1))) - } - } - - ok = true - } + //应该第一行就是默认的路由 + startLineIndex = i + 4 } break } } - if !ok { - utils.Warn("auto route failed") + + if startLineIndex < 0 { + utils.Warn("auto route failed, parse netstat output failed,1") + return } + str := utils.StandardizeSpaces(lines[startLineIndex]) + fields := strings.Split(str, " ") + + if len(fields) <= 3 { + utils.Warn("auto route failed, parse netstat output failed,2") + return + } + + routerIP := fields[2] + //为了简单起见,只认为192开头的是我们的本地路由地址; + if routerIP == "On-link" || !strings.HasPrefix(routerIP, "192") { + utils.Warn("auto route failed, routerIP parse failed, got " + routerIP) + return + } + if ce := utils.CanLogInfo("auto route: Your router's ip should be"); ce != nil { + ce.Write(zap.String("ip", routerIP)) + } + rememberedRouterIP = routerIP + + params1 := "delete 0.0.0.0 mask 0.0.0.0" + out1, err := exec.Command("route", strings.Split(params1, " ")...).Output() + + //这里err只能捕获没有权限运行等错误; 如果路由表修改失败,是不会返回err的 + + checkErrStep: + if ce := utils.CanLogInfo("auto route delete default"); ce != nil { + ce.Write(zap.String("output", string(out1))) + } + + if err != nil { + if ce := utils.CanLogErr("auto route failed"); ce != nil { + ce.Write(zap.Error(err)) + } + return + } + + params1 = "add 0.0.0.0 mask 0.0.0.0 " + tunGateway + " metric 6" + out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() + if err != nil { + goto checkErrStep + } + if ce := utils.CanLogInfo("auto route add tun"); ce != nil { + ce.Write(zap.String("output", string(out1))) + } + + for _, v := range directList { + params1 = "add " + v + " " + rememberedRouterIP + " metric 5" + out1, err = exec.Command("route", strings.Split(params1, " ")...).Output() + if err != nil { + goto checkErrStep + } + if ce := utils.CanLogInfo("auto route add direct"); ce != nil { + ce.Write(zap.String("output", string(out1))) + } + } + + utils.Warn("auto route succeed!") + } autoRouteDownFunc = func(tunDevName, tunGateway, tunIP string, directList []string) {