wgengine/magicsock: revise derp fallback logic

Revision to earlier 6284454ae5

Don't be sticky if we have no peers.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
pull/222/head
Brad Fitzpatrick 4 years ago committed by Brad Fitzpatrick
parent cbd8aceb95
commit 577f321c38

@ -378,18 +378,13 @@ func (c *Conn) pickDERPFallback() int {
c.mu.Lock()
defer c.mu.Unlock()
if c.myDerp != 0 {
// If we already had one in the past, stay on it.
return c.myDerp
}
ids := c.derps.IDs()
if len(ids) == 0 {
// No DERP nodes registered.
return 0
}
// See where our peers are. Pick wherever the most nodes are.
// See where our peers are.
var (
peersOnDerp = map[int]int{}
best int
@ -404,6 +399,15 @@ func (c *Conn) pickDERPFallback() int {
}
}
}
// If we already had selected something in the past and it has
// any peers, stay on it. If there are no peers, though, also
// stay where we are.
if c.myDerp != 0 && (best == 0 || peersOnDerp[c.myDerp] != 0) {
return c.myDerp
}
// Otherwise pick wherever the most peers are.
if best != 0 {
return best
}

@ -135,6 +135,15 @@ func TestPickDERPFallback(t *testing.T) {
if got := c.pickDERPFallback(); got != someNode {
t.Errorf("not sticky: got %v; want %v", got, someNode)
}
// But move if peers are elsewhere.
const otherNode = 789
c.addrsByKey = map[key.Public]*AddrSet{
key.Public{1}: &AddrSet{addrs: []net.UDPAddr{{IP: derpMagicIP, Port: otherNode}}},
}
if got := c.pickDERPFallback(); got != otherNode {
t.Errorf("didn't join peers: got %v; want %v", got, someNode)
}
}
func makeConfigs(t *testing.T, ports []uint16) []wgcfg.Config {

Loading…
Cancel
Save