From 4f049a3193349d57af9b663e3eacb63301a69d78 Mon Sep 17 00:00:00 2001 From: Daniel N <2color@users.noreply.github.com> Date: Wed, 21 Aug 2024 11:48:31 +0200 Subject: [PATCH 1/5] fix: allow punching undialable host public ip fixes #2913 --- p2p/protocol/holepunch/svc.go | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/p2p/protocol/holepunch/svc.go b/p2p/protocol/holepunch/svc.go index 9de0a11e0c..3b3c1a2f55 100644 --- a/p2p/protocol/holepunch/svc.go +++ b/p2p/protocol/holepunch/svc.go @@ -106,7 +106,8 @@ func (s *Service) watchForPublicAddr() { t := time.NewTimer(duration) defer t.Stop() for { - if containsPublicAddr(s.ids.OwnObservedAddrs()) { + // Use both host and observed to enable hole punching for undialable public ips that might not be observed + if containsPublicAddr(s.ids.OwnObservedAddrs()) || containsPublicAddr(s.host.Addrs()) { log.Debug("Host now has a public address. Starting holepunch protocol.") s.host.SetStreamHandler(Protocol, s.handleNewStream) break @@ -172,6 +173,7 @@ func (s *Service) incomingHolePunch(str network.Stream) (rtt time.Duration, remo return 0, nil, nil, fmt.Errorf("received hole punch stream: %s", str.Conn().RemoteMultiaddr()) } ownAddrs = removeRelayAddrs(s.ids.OwnObservedAddrs()) + ownAddrs = append(ownAddrs, s.host.Addrs()...) if s.filter != nil { ownAddrs = s.filter.FilterLocal(str.Conn().RemotePeer(), ownAddrs) } From cc9cefe868a1ffb0d10b5f3f736c25f39f0d9474 Mon Sep 17 00:00:00 2001 From: Daniel N <2color@users.noreply.github.com> Date: Fri, 23 Aug 2024 11:50:26 +0200 Subject: [PATCH 2/5] chore: use interface listen addrs to enable dctur --- p2p/protocol/holepunch/svc.go | 15 +++++++++++++-- 1 file changed, 13 insertions(+), 2 deletions(-) diff --git a/p2p/protocol/holepunch/svc.go b/p2p/protocol/holepunch/svc.go index 3b3c1a2f55..d92365f963 100644 --- a/p2p/protocol/holepunch/svc.go +++ b/p2p/protocol/holepunch/svc.go @@ -106,8 +106,13 @@ func (s *Service) watchForPublicAddr() { t := time.NewTimer(duration) defer t.Stop() for { + interfaceListenAddrs, err := s.host.Network().InterfaceListenAddresses() + + if err != nil { + log.Debugf("failed to get to get InterfaceListenAddresses: %s", err) + } // Use both host and observed to enable hole punching for undialable public ips that might not be observed - if containsPublicAddr(s.ids.OwnObservedAddrs()) || containsPublicAddr(s.host.Addrs()) { + if containsPublicAddr(s.ids.OwnObservedAddrs()) || containsPublicAddr(interfaceListenAddrs) { log.Debug("Host now has a public address. Starting holepunch protocol.") s.host.SetStreamHandler(Protocol, s.handleNewStream) break @@ -173,7 +178,13 @@ func (s *Service) incomingHolePunch(str network.Stream) (rtt time.Duration, remo return 0, nil, nil, fmt.Errorf("received hole punch stream: %s", str.Conn().RemoteMultiaddr()) } ownAddrs = removeRelayAddrs(s.ids.OwnObservedAddrs()) - ownAddrs = append(ownAddrs, s.host.Addrs()...) + interfaceListenAddrs, err := s.host.Network().InterfaceListenAddresses() + + if err != nil { + log.Debugf("failed to get to get InterfaceListenAddresses: %s", err) + } + ownAddrs = ma.Unique(append(ownAddrs, interfaceListenAddrs...)) + if s.filter != nil { ownAddrs = s.filter.FilterLocal(str.Conn().RemotePeer(), ownAddrs) } From 2c34ca0e5a5ed81a2764dc1d58279764a42cfe25 Mon Sep 17 00:00:00 2001 From: Daniel N <2color@users.noreply.github.com> Date: Wed, 28 Aug 2024 14:46:11 +0200 Subject: [PATCH 3/5] fix: filter public addresses --- p2p/protocol/holepunch/svc.go | 37 ++++++++++++++++++++++++----------- 1 file changed, 26 insertions(+), 11 deletions(-) diff --git a/p2p/protocol/holepunch/svc.go b/p2p/protocol/holepunch/svc.go index d92365f963..9ca9e0d148 100644 --- a/p2p/protocol/holepunch/svc.go +++ b/p2p/protocol/holepunch/svc.go @@ -19,6 +19,7 @@ import ( "github.com/libp2p/go-msgio/pbio" ma "github.com/multiformats/go-multiaddr" + manet "github.com/multiformats/go-multiaddr/net" ) // Protocol is the libp2p protocol for Hole Punching. @@ -106,13 +107,9 @@ func (s *Service) watchForPublicAddr() { t := time.NewTimer(duration) defer t.Stop() for { - interfaceListenAddrs, err := s.host.Network().InterfaceListenAddresses() - if err != nil { - log.Debugf("failed to get to get InterfaceListenAddresses: %s", err) - } // Use both host and observed to enable hole punching for undialable public ips that might not be observed - if containsPublicAddr(s.ids.OwnObservedAddrs()) || containsPublicAddr(interfaceListenAddrs) { + if len(s.getPublicAddrs()) > 0 { log.Debug("Host now has a public address. Starting holepunch protocol.") s.host.SetStreamHandler(Protocol, s.handleNewStream) break @@ -177,13 +174,8 @@ func (s *Service) incomingHolePunch(str network.Stream) (rtt time.Duration, remo if !isRelayAddress(str.Conn().RemoteMultiaddr()) { return 0, nil, nil, fmt.Errorf("received hole punch stream: %s", str.Conn().RemoteMultiaddr()) } - ownAddrs = removeRelayAddrs(s.ids.OwnObservedAddrs()) - interfaceListenAddrs, err := s.host.Network().InterfaceListenAddresses() - if err != nil { - log.Debugf("failed to get to get InterfaceListenAddresses: %s", err) - } - ownAddrs = ma.Unique(append(ownAddrs, interfaceListenAddrs...)) + ownAddrs = s.getPublicAddrs() if s.filter != nil { ownAddrs = s.filter.FilterLocal(str.Conn().RemotePeer(), ownAddrs) @@ -287,6 +279,29 @@ func (s *Service) handleNewStream(str network.Stream) { s.tracer.HolePunchFinished("receiver", 1, addrs, ownAddrs, getDirectConnection(s.host, rp)) } +// getPublicAddrs returns public observed and interface addresses +func (s *Service) getPublicAddrs() []ma.Multiaddr { + addrs := removeRelayAddrs(s.ids.OwnObservedAddrs()) + + interfaceListenAddrs, err := s.host.Network().InterfaceListenAddresses() + if err != nil { + log.Debugf("failed to get to get InterfaceListenAddresses: %s", err) + } else { + addrs = append(addrs, interfaceListenAddrs...) + } + + addrs = ma.Unique(addrs) + + publicAddrs := make([]ma.Multiaddr, 0, len(addrs)) + + for _, addr := range addrs { + if manet.IsPublicAddr(addr) { + publicAddrs = append(publicAddrs, addr) + } + } + return publicAddrs +} + // DirectConnect is only exposed for testing purposes. // TODO: find a solution for this. func (s *Service) DirectConnect(p peer.ID) error { From 204210319003a49ddd7eb0690609cb8077b84bb6 Mon Sep 17 00:00:00 2001 From: Daniel N <2color@users.noreply.github.com> Date: Wed, 28 Aug 2024 14:46:54 +0200 Subject: [PATCH 4/5] chore: remove unused function --- p2p/protocol/holepunch/util.go | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/p2p/protocol/holepunch/util.go b/p2p/protocol/holepunch/util.go index 13013568fe..947b1ffd82 100644 --- a/p2p/protocol/holepunch/util.go +++ b/p2p/protocol/holepunch/util.go @@ -8,19 +8,8 @@ import ( "github.com/libp2p/go-libp2p/core/peer" ma "github.com/multiformats/go-multiaddr" - manet "github.com/multiformats/go-multiaddr/net" ) -func containsPublicAddr(addrs []ma.Multiaddr) bool { - for _, addr := range addrs { - if isRelayAddress(addr) || !manet.IsPublicAddr(addr) { - continue - } - return true - } - return false -} - func removeRelayAddrs(addrs []ma.Multiaddr) []ma.Multiaddr { result := make([]ma.Multiaddr, 0, len(addrs)) for _, addr := range addrs { From 317c8af958c0f2fad8d05f4ffd4bd1742388e4da Mon Sep 17 00:00:00 2001 From: Daniel N <2color@users.noreply.github.com> Date: Wed, 28 Aug 2024 14:48:51 +0200 Subject: [PATCH 5/5] chore: formatting --- p2p/protocol/holepunch/svc.go | 4 ---- 1 file changed, 4 deletions(-) diff --git a/p2p/protocol/holepunch/svc.go b/p2p/protocol/holepunch/svc.go index 9ca9e0d148..eb8ad9fd38 100644 --- a/p2p/protocol/holepunch/svc.go +++ b/p2p/protocol/holepunch/svc.go @@ -107,8 +107,6 @@ func (s *Service) watchForPublicAddr() { t := time.NewTimer(duration) defer t.Stop() for { - - // Use both host and observed to enable hole punching for undialable public ips that might not be observed if len(s.getPublicAddrs()) > 0 { log.Debug("Host now has a public address. Starting holepunch protocol.") s.host.SetStreamHandler(Protocol, s.handleNewStream) @@ -174,9 +172,7 @@ func (s *Service) incomingHolePunch(str network.Stream) (rtt time.Duration, remo if !isRelayAddress(str.Conn().RemoteMultiaddr()) { return 0, nil, nil, fmt.Errorf("received hole punch stream: %s", str.Conn().RemoteMultiaddr()) } - ownAddrs = s.getPublicAddrs() - if s.filter != nil { ownAddrs = s.filter.FilterLocal(str.Conn().RemotePeer(), ownAddrs) }