@ -310,7 +310,7 @@ func (b *LocalBackend) setClientStatus(st controlclient.Status) {
prefsChanged = true
}
if st . NetMap != nil {
if b . keepOneExitNodeLocked ( st . NetMap ) {
if b . findExitNodeID ( st . NetMap ) {
prefsChanged = true
}
b . setNetMapLocked ( st . NetMap )
@ -371,51 +371,35 @@ func (b *LocalBackend) setClientStatus(st controlclient.Status) {
b . authReconfig ( )
}
// keepOneExitNodeLocked edits nm to retain only the default
// routes provided by the exit node specified in b.prefs. It returns
// whether prefs was mutated as part of the process, due to an exit
// node IP being converted into a node ID.
func ( b * LocalBackend ) keepOneExitNodeLocked ( nm * netmap . NetworkMap ) ( prefsChanged bool ) {
// findExitNodeID updates b.prefs to reference an exit node by ID,
// rather than by IP. It returns whether prefs was mutated.
func ( b * LocalBackend ) findExitNodeID ( nm * netmap . NetworkMap ) ( prefsChanged bool ) {
// If we have a desired IP on file, try to find the corresponding
// node.
if ! b . prefs . ExitNodeIP . IsZero ( ) {
// IP takes precedence over ID, so if both are set, clear ID.
if b . prefs . ExitNodeID != "" {
b . prefs . ExitNodeID = ""
prefsChanged = true
}
if b . prefs . ExitNodeIP . IsZero ( ) {
return false
}
peerLoop :
for _ , peer := range nm . Peers {
for _ , addr := range peer . Addresses {
if ! addr . IsSingleIP ( ) || addr . IP != b . prefs . ExitNodeIP {
continue
}
// Found the node being referenced, upgrade prefs to
// reference it directly for next time.
b . prefs . ExitNodeID = peer . StableID
b . prefs . ExitNodeIP = netaddr . IP { }
prefsChanged = true
break peerLoop
}
}
// IP takes precedence over ID, so if both are set, clear ID.
if b . prefs . ExitNodeID != "" {
b . prefs . ExitNodeID = ""
prefsChanged = true
}
// At this point, we have a node ID if the requested node is in
// the netmap. If not, the ID will be empty, and we'll strip out
// all default routes.
for _ , peer := range nm . Peers {
out := peer . AllowedIPs [ : 0 ]
for _ , allowedIP := range peer . AllowedIPs {
if allowedIP . Bits == 0 && peer . StableID != b . prefs . ExitNodeID {
for _ , addr := range peer . Addresses {
if ! addr . IsSingleIP ( ) || addr . IP != b . prefs . ExitNodeIP {
continue
}
out = append ( out , allowedIP )
// Found the node being referenced, upgrade prefs to
// reference it directly for next time.
b . prefs . ExitNodeID = peer . StableID
b . prefs . ExitNodeIP = netaddr . IP { }
return true
}
peer . AllowedIPs = out
}
return prefsChanged
return false
}
// setWgengineStatus is the callback by the wireguard engine whenever it posts a new status.
@ -1274,7 +1258,7 @@ func (b *LocalBackend) authReconfig() {
}
}
cfg , err := nmcfg . WGCfg ( nm , b . logf , flags )
cfg , err := nmcfg . WGCfg ( nm , b . logf , flags , uc . ExitNodeID )
if err != nil {
b . logf ( "wgcfg: %v" , err )
return