From babace573ef330f4fbffd70e07cbdf9daae14daf Mon Sep 17 00:00:00 2001 From: Julien Viard de Galbert Date: Fri, 16 Apr 2021 19:00:57 +0200 Subject: [PATCH] Handle discovered Endpoints in topology to enable NAT 2 NAT --- pkg/mesh/mesh.go | 10 +- pkg/mesh/topology.go | 58 ++++-- pkg/mesh/topology_test.go | 425 ++++++++++++++++++++------------------ 3 files changed, 273 insertions(+), 220 deletions(-) diff --git a/pkg/mesh/mesh.go b/pkg/mesh/mesh.go index 978aa80..42f9fa1 100644 --- a/pkg/mesh/mesh.go +++ b/pkg/mesh/mesh.go @@ -389,6 +389,7 @@ func (m *Mesh) handleLocal(n *Node) { PersistentKeepalive: n.PersistentKeepalive, Subnet: n.Subnet, WireGuardIP: m.wireGuardIP, + DiscoveredEndpoints: n.DiscoveredEndpoints, } if !nodesAreEqual(n, local) { level.Debug(m.logger).Log("msg", "local node differs from backend") @@ -469,7 +470,7 @@ func (m *Mesh) applyTopology() { return } oldConf := wireguard.Parse(oldConfRaw) - natEndpoints := updateNATEndpoints(nodes, peers, oldConf, m.logger) + natEndpoints := discoverNATEndpoints(nodes, peers, oldConf, m.logger) nodes[m.hostname].DiscoveredEndpoints = natEndpoints m.nodes[m.hostname].DiscoveredEndpoints = natEndpoints t, err := NewTopology(nodes, peers, m.granularity, m.hostname, nodes[m.hostname].Endpoint.Port, m.priv, m.subnet, nodes[m.hostname].PersistentKeepalive) @@ -792,9 +793,8 @@ func linkByIndex(index int) (netlink.Link, error) { return link, nil } -// updateNATEndpoints ensures that nodes and peers behind NAT update -// their endpoints from the WireGuard configuration so they can roam. -func updateNATEndpoints(nodes map[string]*Node, peers map[string]*Peer, conf *wireguard.Conf, logger log.Logger) map[string]*wireguard.Endpoint { +// discoverNATEndpoints uses the node's WireGuard configuration to returns a list of the most recently discovered endpoints for all nodes and peers behind NAT so that they can roam. +func discoverNATEndpoints(nodes map[string]*Node, peers map[string]*Peer, conf *wireguard.Conf, logger log.Logger) map[string]*wireguard.Endpoint { natEndpoints := make(map[string]*wireguard.Endpoint) keys := make(map[string]*wireguard.Peer) for i := range conf.Peers { @@ -808,7 +808,6 @@ func updateNATEndpoints(nodes map[string]*Node, peers map[string]*Peer, conf *wi if !n.Endpoint.Equal(peer.Endpoint) { natEndpoints[string(n.Key)] = peer.Endpoint } - n.Endpoint = peer.Endpoint } } for _, p := range peers { @@ -816,7 +815,6 @@ func updateNATEndpoints(nodes map[string]*Node, peers map[string]*Peer, conf *wi if !p.Endpoint.Equal(peer.Endpoint) { natEndpoints[string(p.PublicKey)] = peer.Endpoint } - p.Endpoint = peer.Endpoint } } level.Debug(logger).Log("msg", "Discovered WireGuard NAT Endpoints", "DiscoveredEndpoints", natEndpoints) diff --git a/pkg/mesh/topology.go b/pkg/mesh/topology.go index 4e7708d..858c900 100644 --- a/pkg/mesh/topology.go +++ b/pkg/mesh/topology.go @@ -55,12 +55,15 @@ type Topology struct { // the IP is the 0th address in the subnet, i.e. the CIDR // is equal to the Kilo subnet. wireGuardCIDR *net.IPNet + // discoveredEndpoints is the updated map of valid discovered Endpoints + discoveredEndpoints map[string]*wireguard.Endpoint } type segment struct { - allowedIPs []*net.IPNet - endpoint *wireguard.Endpoint - key []byte + allowedIPs []*net.IPNet + endpoint *wireguard.Endpoint + key []byte + persistentKeepalive int // Location is the logical location of this segment. location string @@ -106,7 +109,7 @@ func NewTopology(nodes map[string]*Node, peers map[string]*Peer, granularity Gra localLocation = nodeLocationPrefix + hostname } - t := Topology{key: key, port: port, hostname: hostname, location: localLocation, persistentKeepalive: persistentKeepalive, privateIP: nodes[hostname].InternalIP, subnet: nodes[hostname].Subnet, wireGuardCIDR: subnet} + t := Topology{key: key, port: port, hostname: hostname, location: localLocation, persistentKeepalive: persistentKeepalive, privateIP: nodes[hostname].InternalIP, subnet: nodes[hostname].Subnet, wireGuardCIDR: subnet, discoveredEndpoints: make(map[string]*wireguard.Endpoint)} for location := range topoMap { // Sort the location so the result is stable. sort.Slice(topoMap[location], func(i, j int) bool { @@ -134,14 +137,15 @@ func NewTopology(nodes map[string]*Node, peers map[string]*Peer, granularity Gra hostnames = append(hostnames, node.Name) } t.segments = append(t.segments, &segment{ - allowedIPs: allowedIPs, - endpoint: topoMap[location][leader].Endpoint, - key: topoMap[location][leader].Key, - location: location, - cidrs: cidrs, - hostnames: hostnames, - leader: leader, - privateIPs: privateIPs, + allowedIPs: allowedIPs, + endpoint: topoMap[location][leader].Endpoint, + key: topoMap[location][leader].Key, + persistentKeepalive: topoMap[location][leader].PersistentKeepalive, + location: location, + cidrs: cidrs, + hostnames: hostnames, + leader: leader, + privateIPs: privateIPs, }) } // Sort the Topology segments so the result is stable. @@ -159,6 +163,10 @@ func NewTopology(nodes map[string]*Node, peers map[string]*Peer, granularity Gra // We need to defensively deduplicate peer allowed IPs. If two peers claim the same IP, // the WireGuard configuration could flap, causing the interface to churn. t.peers = deduplicatePeerIPs(t.peers) + // Copy the host node DiscoveredEndpoints in the topology as a starting point. + for key := range nodes[hostname].DiscoveredEndpoints { + t.discoveredEndpoints[key] = nodes[hostname].DiscoveredEndpoints[key] + } // Allocate IPs to the segment leaders in a stable, coordination-free manner. a := newAllocator(*subnet) for _, segment := range t.segments { @@ -171,11 +179,33 @@ func NewTopology(nodes map[string]*Node, peers map[string]*Peer, granularity Gra if t.leader && segment.location == t.location { t.wireGuardCIDR = &net.IPNet{IP: ipNet.IP, Mask: subnet.Mask} } + + // Now that the topology is ordered, update the discoveredEndpoints map + // add new ones by going through the ordered topology: segments, nodes + for _, node := range topoMap[segment.location] { + for key := range node.DiscoveredEndpoints { + if _, ok := t.discoveredEndpoints[key]; !ok { + t.discoveredEndpoints[key] = node.DiscoveredEndpoints[key] + } + } + } } return &t, nil } +func (t *Topology) updateEndpoint(endpoint *wireguard.Endpoint, key []byte, persistentKeepalive int) *wireguard.Endpoint { + // Do not update non-nat peers + if persistentKeepalive == 0 { + return endpoint + } + e, ok := t.discoveredEndpoints[string(key)] + if ok { + return e + } + return endpoint +} + // Conf generates a WireGuard configuration file for a given Topology. func (t *Topology) Conf() *wireguard.Conf { c := &wireguard.Conf{ @@ -190,7 +220,7 @@ func (t *Topology) Conf() *wireguard.Conf { } peer := &wireguard.Peer{ AllowedIPs: s.allowedIPs, - Endpoint: s.endpoint, + Endpoint: t.updateEndpoint(s.endpoint, s.key, s.persistentKeepalive), PersistentKeepalive: t.persistentKeepalive, PublicKey: s.key, } @@ -199,7 +229,7 @@ func (t *Topology) Conf() *wireguard.Conf { for _, p := range t.peers { peer := &wireguard.Peer{ AllowedIPs: p.AllowedIPs, - Endpoint: p.Endpoint, + Endpoint: t.updateEndpoint(p.Endpoint, p.PublicKey, p.PersistentKeepalive), PersistentKeepalive: t.persistentKeepalive, PresharedKey: p.PresharedKey, PublicKey: p.PublicKey, diff --git a/pkg/mesh/topology_test.go b/pkg/mesh/topology_test.go index 3089c03..d74a5af 100644 --- a/pkg/mesh/topology_test.go +++ b/pkg/mesh/topology_test.go @@ -126,34 +126,37 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: &net.IPNet{IP: w1, Mask: net.CIDRMask(16, 32)}, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: logicalLocationPrefix + nodes["a"].Location, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: logicalLocationPrefix + nodes["a"].Location, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: logicalLocationPrefix + nodes["b"].Location, - cidrs: []*net.IPNet{nodes["b"].Subnet, nodes["c"].Subnet}, - hostnames: []string{"b", "c"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP, nodes["c"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: logicalLocationPrefix + nodes["b"].Location, + cidrs: []*net.IPNet{nodes["b"].Subnet, nodes["c"].Subnet}, + hostnames: []string{"b", "c"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP, nodes["c"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w3, }, }, peers: []*Peer{peers["a"], peers["b"]}, @@ -172,34 +175,37 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: &net.IPNet{IP: w2, Mask: net.CIDRMask(16, 32)}, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: logicalLocationPrefix + nodes["a"].Location, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: logicalLocationPrefix + nodes["a"].Location, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: logicalLocationPrefix + nodes["b"].Location, - cidrs: []*net.IPNet{nodes["b"].Subnet, nodes["c"].Subnet}, - hostnames: []string{"b", "c"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP, nodes["c"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: logicalLocationPrefix + nodes["b"].Location, + cidrs: []*net.IPNet{nodes["b"].Subnet, nodes["c"].Subnet}, + hostnames: []string{"b", "c"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP, nodes["c"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w3, }, }, peers: []*Peer{peers["a"], peers["b"]}, @@ -218,34 +224,37 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: DefaultKiloSubnet, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: logicalLocationPrefix + nodes["a"].Location, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: logicalLocationPrefix + nodes["a"].Location, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: logicalLocationPrefix + nodes["b"].Location, - cidrs: []*net.IPNet{nodes["b"].Subnet, nodes["c"].Subnet}, - hostnames: []string{"b", "c"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP, nodes["c"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: logicalLocationPrefix + nodes["b"].Location, + cidrs: []*net.IPNet{nodes["b"].Subnet, nodes["c"].Subnet}, + hostnames: []string{"b", "c"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP, nodes["c"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w3, }, }, peers: []*Peer{peers["a"], peers["b"]}, @@ -264,44 +273,48 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: &net.IPNet{IP: w1, Mask: net.CIDRMask(16, 32)}, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: nodeLocationPrefix + nodes["a"].Name, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["a"].Name, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: nodeLocationPrefix + nodes["b"].Name, - cidrs: []*net.IPNet{nodes["b"].Subnet}, - hostnames: []string{"b"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["b"].Name, + cidrs: []*net.IPNet{nodes["b"].Subnet}, + hostnames: []string{"b"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["c"].Endpoint, - key: nodes["c"].Key, - location: nodeLocationPrefix + nodes["c"].Name, - cidrs: []*net.IPNet{nodes["c"].Subnet}, - hostnames: []string{"c"}, - privateIPs: []net.IP{nodes["c"].InternalIP.IP}, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["c"].Endpoint, + key: nodes["c"].Key, + persistentKeepalive: nodes["c"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["c"].Name, + cidrs: []*net.IPNet{nodes["c"].Subnet}, + hostnames: []string{"c"}, + privateIPs: []net.IP{nodes["c"].InternalIP.IP}, + wireGuardIP: w3, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w4, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w4, }, }, peers: []*Peer{peers["a"], peers["b"]}, @@ -320,44 +333,48 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: &net.IPNet{IP: w2, Mask: net.CIDRMask(16, 32)}, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: nodeLocationPrefix + nodes["a"].Name, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["a"].Name, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: nodeLocationPrefix + nodes["b"].Name, - cidrs: []*net.IPNet{nodes["b"].Subnet}, - hostnames: []string{"b"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["b"].Name, + cidrs: []*net.IPNet{nodes["b"].Subnet}, + hostnames: []string{"b"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["c"].Endpoint, - key: nodes["c"].Key, - location: nodeLocationPrefix + nodes["c"].Name, - cidrs: []*net.IPNet{nodes["c"].Subnet}, - hostnames: []string{"c"}, - privateIPs: []net.IP{nodes["c"].InternalIP.IP}, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["c"].Endpoint, + key: nodes["c"].Key, + persistentKeepalive: nodes["c"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["c"].Name, + cidrs: []*net.IPNet{nodes["c"].Subnet}, + hostnames: []string{"c"}, + privateIPs: []net.IP{nodes["c"].InternalIP.IP}, + wireGuardIP: w3, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w4, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w4, }, }, peers: []*Peer{peers["a"], peers["b"]}, @@ -376,44 +393,48 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: &net.IPNet{IP: w3, Mask: net.CIDRMask(16, 32)}, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: nodeLocationPrefix + nodes["a"].Name, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["a"].Name, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: nodeLocationPrefix + nodes["b"].Name, - cidrs: []*net.IPNet{nodes["b"].Subnet}, - hostnames: []string{"b"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["b"].Name, + cidrs: []*net.IPNet{nodes["b"].Subnet}, + hostnames: []string{"b"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["c"].Endpoint, - key: nodes["c"].Key, - location: nodeLocationPrefix + nodes["c"].Name, - cidrs: []*net.IPNet{nodes["c"].Subnet}, - hostnames: []string{"c"}, - privateIPs: []net.IP{nodes["c"].InternalIP.IP}, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["c"].Endpoint, + key: nodes["c"].Key, + persistentKeepalive: nodes["c"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["c"].Name, + cidrs: []*net.IPNet{nodes["c"].Subnet}, + hostnames: []string{"c"}, + privateIPs: []net.IP{nodes["c"].InternalIP.IP}, + wireGuardIP: w3, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w4, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w4, }, }, peers: []*Peer{peers["a"], peers["b"]}, @@ -432,44 +453,48 @@ func TestNewTopology(t *testing.T) { wireGuardCIDR: &net.IPNet{IP: w4, Mask: net.CIDRMask(16, 32)}, segments: []*segment{ { - allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["a"].Endpoint, - key: nodes["a"].Key, - location: nodeLocationPrefix + nodes["a"].Name, - cidrs: []*net.IPNet{nodes["a"].Subnet}, - hostnames: []string{"a"}, - privateIPs: []net.IP{nodes["a"].InternalIP.IP}, - wireGuardIP: w1, + allowedIPs: []*net.IPNet{nodes["a"].Subnet, nodes["a"].InternalIP, {IP: w1, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["a"].Endpoint, + key: nodes["a"].Key, + persistentKeepalive: nodes["a"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["a"].Name, + cidrs: []*net.IPNet{nodes["a"].Subnet}, + hostnames: []string{"a"}, + privateIPs: []net.IP{nodes["a"].InternalIP.IP}, + wireGuardIP: w1, }, { - allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["b"].Endpoint, - key: nodes["b"].Key, - location: nodeLocationPrefix + nodes["b"].Name, - cidrs: []*net.IPNet{nodes["b"].Subnet}, - hostnames: []string{"b"}, - privateIPs: []net.IP{nodes["b"].InternalIP.IP}, - wireGuardIP: w2, + allowedIPs: []*net.IPNet{nodes["b"].Subnet, nodes["b"].InternalIP, {IP: w2, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["b"].Endpoint, + key: nodes["b"].Key, + persistentKeepalive: nodes["b"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["b"].Name, + cidrs: []*net.IPNet{nodes["b"].Subnet}, + hostnames: []string{"b"}, + privateIPs: []net.IP{nodes["b"].InternalIP.IP}, + wireGuardIP: w2, }, { - allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["c"].Endpoint, - key: nodes["c"].Key, - location: nodeLocationPrefix + nodes["c"].Name, - cidrs: []*net.IPNet{nodes["c"].Subnet}, - hostnames: []string{"c"}, - privateIPs: []net.IP{nodes["c"].InternalIP.IP}, - wireGuardIP: w3, + allowedIPs: []*net.IPNet{nodes["c"].Subnet, nodes["c"].InternalIP, {IP: w3, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["c"].Endpoint, + key: nodes["c"].Key, + persistentKeepalive: nodes["c"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["c"].Name, + cidrs: []*net.IPNet{nodes["c"].Subnet}, + hostnames: []string{"c"}, + privateIPs: []net.IP{nodes["c"].InternalIP.IP}, + wireGuardIP: w3, }, { - allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, - endpoint: nodes["d"].Endpoint, - key: nodes["d"].Key, - location: nodeLocationPrefix + nodes["d"].Name, - cidrs: []*net.IPNet{nodes["d"].Subnet}, - hostnames: []string{"d"}, - privateIPs: nil, - wireGuardIP: w4, + allowedIPs: []*net.IPNet{nodes["d"].Subnet, {IP: w4, Mask: net.CIDRMask(32, 32)}}, + endpoint: nodes["d"].Endpoint, + key: nodes["d"].Key, + persistentKeepalive: nodes["d"].PersistentKeepalive, + location: nodeLocationPrefix + nodes["d"].Name, + cidrs: []*net.IPNet{nodes["d"].Subnet}, + hostnames: []string{"d"}, + privateIPs: nil, + wireGuardIP: w4, }, }, peers: []*Peer{peers["a"], peers["b"]},