Skip to content

Commit e96cfc1

Browse files
committed
basichost: don't advertise unreachable addrs.
1 parent 49d58c5 commit e96cfc1

File tree

2 files changed

+54
-14
lines changed

2 files changed

+54
-14
lines changed

p2p/host/basic/addrs_manager.go

Lines changed: 52 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -315,8 +315,8 @@ func (a *addrsManager) updateAddrs(relayAddrs []ma.Multiaddr) hostAddrs {
315315
currReachableAddrs, currUnreachableAddrs, currUnknownAddrs = a.getConfirmedAddrs(localAddrs)
316316
}
317317
relayAddrs = slices.Clone(relayAddrs)
318-
currAddrs := a.getAddrs(slices.Clone(localAddrs), relayAddrs)
319-
318+
currAddrs := a.getDialableAddrs(localAddrs, currReachableAddrs, currUnreachableAddrs, relayAddrs)
319+
currAddrs = a.applyAddrsFactory(currAddrs)
320320
a.addrsMx.Lock()
321321
a.currentAddrs = hostAddrs{
322322
addrs: append(a.currentAddrs.addrs[:0], currAddrs...),
@@ -378,25 +378,36 @@ func (a *addrsManager) handleAddrsUpdated(emitter event.Emitter, localAddrsEmitt
378378
// the node's relay addresses and private network addresses.
379379
func (a *addrsManager) Addrs() []ma.Multiaddr {
380380
a.addrsMx.RLock()
381-
directAddrs := slices.Clone(a.currentAddrs.localAddrs)
382-
relayAddrs := slices.Clone(a.currentAddrs.relayAddrs)
381+
addrs := a.getDialableAddrs(a.currentAddrs.localAddrs, a.currentAddrs.reachableAddrs, a.currentAddrs.unreachableAddrs, a.currentAddrs.relayAddrs)
383382
a.addrsMx.RUnlock()
384-
return a.getAddrs(directAddrs, relayAddrs)
383+
// don't hold the lock while applying addrs factory
384+
return a.applyAddrsFactory(addrs)
385385
}
386386

387-
// getAddrs returns the node's dialable addresses. Mutates localAddrs
388-
func (a *addrsManager) getAddrs(localAddrs []ma.Multiaddr, relayAddrs []ma.Multiaddr) []ma.Multiaddr {
389-
addrs := localAddrs
390-
rch := a.hostReachability.Load()
391-
if rch != nil && *rch == network.ReachabilityPrivate {
392-
// Delete public addresses if the node's reachability is private, and we have relay addresses
393-
if len(relayAddrs) > 0 {
387+
// getDialableAddrs returns the node's dialable addrs. Doesn't mutate any argument.
388+
func (a *addrsManager) getDialableAddrs(localAddrs, reachableAddrs, unreachableAddrs, relayAddrs []ma.Multiaddr) []ma.Multiaddr {
389+
addrs := slices.Clone(localAddrs)
390+
// remove known unreachable addrs
391+
removeInSource(addrs, unreachableAddrs)
392+
// If we have no confirmed reachable addresses, add the relay addresses
393+
if a.addrsReachabilityTracker != nil {
394+
if len(reachableAddrs) == 0 {
395+
addrs = append(addrs, relayAddrs...)
396+
}
397+
} else {
398+
// If we're only using autonatv1, remove public addrs and add relay addrs
399+
if len(relayAddrs) > 0 && *a.hostReachability.Load() == network.ReachabilityPrivate {
394400
addrs = slices.DeleteFunc(addrs, manet.IsPublicAddr)
395401
addrs = append(addrs, relayAddrs...)
396402
}
397403
}
398-
// Make a copy. Consumers can modify the slice elements
399-
addrs = slices.Clone(a.addrsFactory(addrs))
404+
return addrs
405+
}
406+
407+
func (a *addrsManager) applyAddrsFactory(addrs []ma.Multiaddr) []ma.Multiaddr {
408+
af := a.addrsFactory(addrs)
409+
// Copy to our slice in case addrsFactory returns its own same slice always.
410+
addrs = append(addrs[:0], af...)
400411
// Add certhashes for the addresses provided by the user via address factory.
401412
addrs = a.addCertHashes(ma.Unique(addrs))
402413
slices.SortFunc(addrs, func(a, b ma.Multiaddr) int { return a.Compare(b) })
@@ -872,6 +883,33 @@ func removeNotInSource(addrs, source []ma.Multiaddr) []ma.Multiaddr {
872883
return addrs[:i]
873884
}
874885

886+
// removeInSource removes items from addrs that are present in source.
887+
// Modifies the addrs slice in place
888+
// addrs and source must be sorted using multiaddr.Compare.
889+
func removeInSource(addrs, source []ma.Multiaddr) []ma.Multiaddr {
890+
j := 0
891+
// mark entries in source as nil
892+
for i, a := range addrs {
893+
// move right in source as long as a > source[j]
894+
for j < len(source) && a.Compare(source[j]) > 0 {
895+
j++
896+
}
897+
// a is in source, mark nil
898+
if j < len(source) && a.Compare(source[j]) == 0 {
899+
addrs[i] = nil
900+
}
901+
}
902+
// j is the current element, i is the lowest index nil element
903+
i := 0
904+
for j := range len(addrs) {
905+
if addrs[j] != nil {
906+
addrs[i], addrs[j] = addrs[j], addrs[i]
907+
i++
908+
}
909+
}
910+
return addrs[:i]
911+
}
912+
875913
type multiCloser []io.Closer
876914

877915
func (mc *multiCloser) Close() error {

p2p/host/basic/addrs_reachability_tracker.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -281,8 +281,10 @@ func (r *addrsReachabilityTracker) refreshReachability() reachabilityTask {
281281
}
282282
r.probeManager.MarkProbeInProgress(reqs)
283283
rctx, cancel := context.WithTimeout(ctx, probeTimeout)
284+
fmt.Println("probing for", reqs[0].Addr)
284285
res, err := client.GetReachability(rctx, reqs)
285286
cancel()
287+
fmt.Println("probe complete", "requested:", reqs[0].Addr, "dialed", res.Addr, "status", res.Reachability)
286288
r.probeManager.CompleteProbe(reqs, res, err)
287289
if isErrorPersistent(err) {
288290
backoff.Store(true)

0 commit comments

Comments
 (0)