summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorDavid Anderson <danderson@tailscale.com>2021-03-11 19:24:45 -0800
committerBrad Fitzpatrick <bradfitz@tailscale.com>2021-03-12 13:34:14 -0800
commitbbb0e84cf1faf69556e725a18abf9d6ffc7b8c34 (patch)
treeb6ad60dbc2722a8f922b864479d945c92d50eb4f
parentf7ef32da5ff838cc852736207261b5ef19be511c (diff)
downloadtailscale-bradfitz/proposed_1.4.6.tar.xz
tailscale-bradfitz/proposed_1.4.6.zip
wgengine/router: don't touch interface routesbradfitz/proposed_1.4.6
Developed by a cast of dozens. Fixes #1448 Signed-off-by: David Anderson <danderson@tailscale.com> (cherry picked from commit fa6110e47bb0f0f5320004a6a8e5ed00fa96eb44)
-rw-r--r--wgengine/router/ifconfig_windows.go30
1 files changed, 28 insertions, 2 deletions
diff --git a/wgengine/router/ifconfig_windows.go b/wgengine/router/ifconfig_windows.go
index 486915e6e..74b9ae335 100644
--- a/wgengine/router/ifconfig_windows.go
+++ b/wgengine/router/ifconfig_windows.go
@@ -20,6 +20,7 @@ import (
"github.com/tailscale/wireguard-go/tun"
"golang.org/x/sys/windows"
"golang.zx2c4.com/wireguard/windows/tunnel/winipcfg"
+ "inet.af/netaddr"
"tailscale.com/net/interfaces"
"tailscale.com/wgengine/winnet"
)
@@ -378,7 +379,7 @@ func configureInterface(cfg *Config, tun *tun.NativeTun) (retErr error) {
}
var errAcc error
- err = syncRoutes(iface, deduplicatedRoutes)
+ err = syncRoutes(iface, deduplicatedRoutes, cfg.LocalAddrs)
if err != nil && errAcc == nil {
log.Printf("setroutes: %v", err)
errAcc = err
@@ -659,9 +660,29 @@ func getInterfaceRoutes(ifc *winipcfg.IPAdapterAddresses, family winipcfg.Addres
return
}
+// isSingleRouteInPrefixes reports whether r is a single-address
+// prefix that appears in pfxs.
+func isSingleRouteInPrefixes(r net.IPNet, pfxs []netaddr.IPPrefix) bool {
+ rr, ok := netaddr.FromStdIPNet(&r)
+ if !ok {
+ return false
+ }
+ if !rr.IsSingleIP() {
+ return false
+ }
+ for _, pfx := range pfxs {
+ if pfx == rr {
+ return true
+ }
+ }
+ return false
+}
+
// syncRoutes incrementally sets multiples routes on an interface.
// This avoids a full ifc.FlushRoutes call.
-func syncRoutes(ifc *winipcfg.IPAdapterAddresses, want []*winipcfg.RouteData) error {
+// dontDelete is a list of interface address routes that the
+// synchronization logic should never delete.
+func syncRoutes(ifc *winipcfg.IPAdapterAddresses, want []*winipcfg.RouteData, dontDelete []netaddr.IPPrefix) error {
routes, err := getInterfaceRoutes(ifc, windows.AF_INET)
if err != nil {
return err
@@ -669,6 +690,11 @@ func syncRoutes(ifc *winipcfg.IPAdapterAddresses, want []*winipcfg.RouteData) er
got := make([]*winipcfg.RouteData, 0, len(routes))
for _, r := range routes {
+ if isSingleRouteInPrefixes(r.DestinationPrefix.IPNet(), dontDelete) {
+ // See issue 1448: we don't want to touch the routes added
+ // by Windows for our interface addresses.
+ continue
+ }
got = append(got, &winipcfg.RouteData{
Destination: r.DestinationPrefix.IPNet(),
NextHop: r.NextHop.IP(),