From 767a2c48f8d2603bdb9e88968cfc074c13556b0f Mon Sep 17 00:00:00 2001 From: MOHAN KUMAR R Date: Mon, 9 Dec 2024 21:58:20 +0530 Subject: [PATCH 1/4] Re-register proxy on local address change event from libp2p host - Subscribe to local address update events from libp2p host - On address change, shut down the existing mDNS server and re-register with updated address --- p2p/discovery/mdns/mdns.go | 37 +++++++++++++++++++++++++++++++++++++ 1 file changed, 37 insertions(+) diff --git a/p2p/discovery/mdns/mdns.go b/p2p/discovery/mdns/mdns.go index 637fcdcb08..b9042cfe8a 100644 --- a/p2p/discovery/mdns/mdns.go +++ b/p2p/discovery/mdns/mdns.go @@ -3,10 +3,12 @@ package mdns import ( "context" "errors" + "github.com/libp2p/go-libp2p/core/event" "io" "math/rand" "strings" "sync" + "time" "github.com/libp2p/go-libp2p/core/host" "github.com/libp2p/go-libp2p/core/peer" @@ -69,6 +71,40 @@ func (s *mdnsService) Start() error { return err } s.startResolver(s.ctx) + + ipEvt, err := s.host.EventBus().Subscribe(&event.EvtLocalAddressesUpdated{}) + if err != nil { + if err = s.Close(); err != nil { + log.Errorf("failed to close mdns service: %s", err) + } + return err + } + go func() { + defer ipEvt.Close() + var addrUpdateDebounce sync.Once + for { + select { + case <-s.ctx.Done(): + return + case evt := <-ipEvt.Out(): + if _, ok := evt.(event.EvtLocalAddressesUpdated); ok { + addrUpdateDebounce.Do(func() { + time.AfterFunc(2*time.Second, func() { + addrUpdateDebounce = sync.Once{} + if s.server != nil { + s.server.Shutdown() + s.server = nil + } + if err = s.startServer(); err != nil { + log.Errorf("failed to restart mdns server: %s", err) + } + }) + }) + } + } + } + }() + return nil } @@ -143,6 +179,7 @@ func (s *mdnsService) startServer() error { txts, nil, ) + if err != nil { return err } From e73024f2bc3b932c2a9fd87935e3c72a83c93635 Mon Sep 17 00:00:00 2001 From: MOHAN KUMAR R Date: Mon, 9 Dec 2024 21:59:36 +0530 Subject: [PATCH 2/4] Re-register proxy on local address change event from libp2p host - Subscribe to local address update events from libp2p host - On address change, shut down the existing mDNS server and re-register with updated address --- p2p/discovery/mdns/mdns.go | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/p2p/discovery/mdns/mdns.go b/p2p/discovery/mdns/mdns.go index b9042cfe8a..5945e5e65d 100644 --- a/p2p/discovery/mdns/mdns.go +++ b/p2p/discovery/mdns/mdns.go @@ -80,7 +80,11 @@ func (s *mdnsService) Start() error { return err } go func() { - defer ipEvt.Close() + defer func() { + if err := ipEvt.Close(); err != nil { + log.Errorf("failed to close ipEvt: %s", err) + } + }() var addrUpdateDebounce sync.Once for { select { From b1fdc89ee8b3723321e3cc84d048c959d8da5134 Mon Sep 17 00:00:00 2001 From: MOHAN KUMAR R Date: Tue, 10 Dec 2024 07:20:18 +0530 Subject: [PATCH 3/4] since ip change events are fired by 5sec schedulers , no need to wait. --- p2p/discovery/mdns/mdns.go | 27 ++++++++++----------------- 1 file changed, 10 insertions(+), 17 deletions(-) diff --git a/p2p/discovery/mdns/mdns.go b/p2p/discovery/mdns/mdns.go index 5945e5e65d..c5d4ed63a7 100644 --- a/p2p/discovery/mdns/mdns.go +++ b/p2p/discovery/mdns/mdns.go @@ -4,14 +4,12 @@ import ( "context" "errors" "github.com/libp2p/go-libp2p/core/event" + "github.com/libp2p/go-libp2p/core/host" + "github.com/libp2p/go-libp2p/core/peer" "io" "math/rand" "strings" "sync" - "time" - - "github.com/libp2p/go-libp2p/core/host" - "github.com/libp2p/go-libp2p/core/peer" "github.com/libp2p/zeroconf/v2" @@ -85,25 +83,20 @@ func (s *mdnsService) Start() error { log.Errorf("failed to close ipEvt: %s", err) } }() - var addrUpdateDebounce sync.Once + for { select { case <-s.ctx.Done(): return case evt := <-ipEvt.Out(): if _, ok := evt.(event.EvtLocalAddressesUpdated); ok { - addrUpdateDebounce.Do(func() { - time.AfterFunc(2*time.Second, func() { - addrUpdateDebounce = sync.Once{} - if s.server != nil { - s.server.Shutdown() - s.server = nil - } - if err = s.startServer(); err != nil { - log.Errorf("failed to restart mdns server: %s", err) - } - }) - }) + if s.server != nil { + s.server.Shutdown() + s.server = nil + } + if err = s.startServer(); err != nil { + log.Errorf("failed to restart mdns server: %s", err) + } } } } From 9ee3a1d04a7a2b22564a99b9c56dea13831491fb Mon Sep 17 00:00:00 2001 From: MOHAN KUMAR R Date: Tue, 10 Dec 2024 11:43:24 +0530 Subject: [PATCH 4/4] fixed race condition in accessing mdnsService.server --- p2p/discovery/mdns/mdns.go | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/p2p/discovery/mdns/mdns.go b/p2p/discovery/mdns/mdns.go index c5d4ed63a7..54e6989a7f 100644 --- a/p2p/discovery/mdns/mdns.go +++ b/p2p/discovery/mdns/mdns.go @@ -48,6 +48,8 @@ type mdnsService struct { server *zeroconf.Server notifee Notifee + + mu sync.Mutex } func NewMdnsService(host host.Host, serviceName string, notifee Notifee) *mdnsService { @@ -90,6 +92,7 @@ func (s *mdnsService) Start() error { return case evt := <-ipEvt.Out(): if _, ok := evt.(event.EvtLocalAddressesUpdated); ok { + s.mu.Lock() if s.server != nil { s.server.Shutdown() s.server = nil @@ -97,6 +100,7 @@ func (s *mdnsService) Start() error { if err = s.startServer(); err != nil { log.Errorf("failed to restart mdns server: %s", err) } + s.mu.Unlock() } } } @@ -106,6 +110,9 @@ func (s *mdnsService) Start() error { } func (s *mdnsService) Close() error { + s.mu.Lock() + defer s.mu.Unlock() + s.ctxCancel() if s.server != nil { s.server.Shutdown()