From 858e57e9582a37b8a1b7aa7b5ca0bf13a68e5c4b Mon Sep 17 00:00:00 2001 From: afeiszli Date: Tue, 23 Aug 2022 10:12:13 -0400 Subject: [PATCH] add explicit routing + domain for netmaker --- netclient/functions/daemon.go | 4 ++++ netclient/functions/join.go | 6 +++++ netclient/local/routes.go | 39 +++++++++++++++++++++++++++++++-- netclient/local/routes_linux.go | 5 +++++ 4 files changed, 52 insertions(+), 2 deletions(-) diff --git a/netclient/functions/daemon.go b/netclient/functions/daemon.go index 1d277402..a454d9e9 100644 --- a/netclient/functions/daemon.go +++ b/netclient/functions/daemon.go @@ -106,6 +106,10 @@ func startGoRoutines(wg *sync.WaitGroup) context.CancelFunc { // == subscribe to all nodes for each on machine == serverSet[server] = true logger.Log(1, "started daemon for server ", server) + err := local.SetNetmakerDomainRoute(cfg.Server.API) + if err != nil { + logger.Log(0, "error setting route for netmaker: "+err.Error()) + } wg.Add(1) go messageQueue(ctx, wg, &cfg) } diff --git a/netclient/functions/join.go b/netclient/functions/join.go index ec3c2ce8..bc978ce0 100644 --- a/netclient/functions/join.go +++ b/netclient/functions/join.go @@ -200,6 +200,12 @@ func JoinNetwork(cfg *config.ClientConfig, privateKey string) error { if err = config.SaveBackup(node.Network); err != nil { logger.Log(0, "network:", node.Network, "failed to make backup, node will not auto restore if config is corrupted") } + + err = local.SetNetmakerDomainRoute(cfg.Server.API) + if err != nil { + logger.Log(0, "error setting route for netmaker: "+err.Error()) + } + logger.Log(0, "starting wireguard") err = wireguard.InitWireguard(&node, privateKey, nodeGET.Peers[:], false) if err != nil { diff --git a/netclient/local/routes.go b/netclient/local/routes.go index 022d9011..f0b5aa52 100644 --- a/netclient/local/routes.go +++ b/netclient/local/routes.go @@ -1,7 +1,9 @@ package local import ( + "fmt" "net" + "net/url" "github.com/gravitl/netmaker/logger" "github.com/gravitl/netmaker/netclient/ncutils" @@ -42,7 +44,7 @@ func SetPeerRoutes(iface string, oldPeers map[string]bool, newPeers []wgtypes.Pe if err != nil { logger.Log(0, "error parsing ip:", err.Error()) } - setRoute(gwIface, &ipNet, gwIP) + SetExplicitRoute(gwIface, &ipNet, gwIP) } } // traverse through all remaining existing peers @@ -82,9 +84,10 @@ func SetCurrentPeerRoutes(iface, currentAddr string, peers []wgtypes.PeerConfig) if err != nil { logger.Log(0, "error parsing ip:", err.Error()) } - setRoute(gwIface, &ipNet, gwIP) + SetExplicitRoute(gwIface, &ipNet, gwIP) } } + } // FlushPeerRoutes - removes all current peer routes @@ -122,3 +125,35 @@ func SetCIDRRoute(iface, currentAddr string, cidr *net.IPNet) { func RemoveCIDRRoute(iface, currentAddr string, cidr *net.IPNet) { removeCidr(iface, cidr, currentAddr) } + +// SetNetmakerDomainRoute - sets explicit route over Gateway for a given DNS name +func SetNetmakerDomainRoute(domainRaw string) error { + var address net.IPNet + + domain, err := url.Parse(domainRaw) + if err != nil { + return err + } + + gwIP, gwIface, err := GetDefaultRoute() + if err != nil { + return fmt.Errorf("error getting default route: %w", err) + } + + ips, err := net.LookupIP(domain.Hostname()) + if err != nil { + return err + } + for _, ip := range ips { + if ipv4 := ip.To4(); ipv4 != nil { + address, err = ncutils.GetIPNetFromString(ipv4.String()) + if err == nil { + break + } + } + } + if err != nil || address.IP == nil { + return fmt.Errorf("address not found") + } + return SetExplicitRoute(gwIface, &address, gwIP) +} diff --git a/netclient/local/routes_linux.go b/netclient/local/routes_linux.go index c7decf75..7374b8ce 100644 --- a/netclient/local/routes_linux.go +++ b/netclient/local/routes_linux.go @@ -44,6 +44,11 @@ func setRoute(iface string, addr *net.IPNet, address string) error { return err } +func SetExplicitRoute(iface string, destination *net.IPNet, gateway string) error { + _, err := ncutils.RunCmd(fmt.Sprintf("ip route add %s via %s dev %s", destination.String(), gateway, iface), false) + return err +} + func deleteRoute(iface string, addr *net.IPNet, address string) error { var err error out, _ := ncutils.RunCmd(fmt.Sprintf("ip route get %s", addr.IP.String()), false)