@@ -66,13 +66,14 @@ func (c *connectednessEventEmitter) RemoveConn(p peer.ID) {
66
66
}
67
67
68
68
c .removeConnsMx .Lock ()
69
- // This queue is not unbounded since we block in the AddConn method
70
- // So we are adding connections to the swarm only at a rate
71
- // the subscriber for our peer connectedness changed events can consume them .
72
- // If a lot of open connections are closed at once, increasing the disconnected
73
- // event notification rate, the rate of adding connections to the swarm would
74
- // proportionately reduce, which would eventually reduce the length of this slice .
69
+ // This queue is roughly bounded by the total number of added connections we
70
+ // have. If consumers of connectedness events are slow, we apply
71
+ // backpressure to AddConn operations .
72
+ //
73
+ // We purposefully don't block/backpressure here to avoid deadlocks, since it's
74
+ // reasonable for a consumer of the event to want to remove a connection .
75
75
c .removeConns = append (c .removeConns , p )
76
+
76
77
c .removeConnsMx .Unlock ()
77
78
78
79
select {
@@ -111,6 +112,12 @@ func (c *connectednessEventEmitter) runEmitter() {
111
112
}
112
113
}
113
114
115
+ // notifyPeer sends the peer connectedness event using the emitter.
116
+ // Use forceNotConnectedEvent = true to send a NotConnected event even if
117
+ // no Connected event was sent for this peer.
118
+ // In case a peer is disconnected before we sent the Connected event, we still
119
+ // send the Disconnected event because a connection to the peer can be observed
120
+ // in such cases.
114
121
func (c * connectednessEventEmitter ) notifyPeer (p peer.ID , forceNotConnectedEvent bool ) {
115
122
oldState := c .lastEvent [p ]
116
123
c .lastEvent [p ] = c .connectedness (p )
@@ -127,17 +134,10 @@ func (c *connectednessEventEmitter) notifyPeer(p peer.ID, forceNotConnectedEvent
127
134
128
135
func (c * connectednessEventEmitter ) sendConnRemovedNotifications () {
129
136
c .removeConnsMx .Lock ()
130
- defer c .removeConnsMx .Unlock ()
131
- for {
132
- if len (c .removeConns ) == 0 {
133
- return
134
- }
135
- p := c .removeConns [0 ]
136
- c .removeConns [0 ] = ""
137
- c .removeConns = c .removeConns [1 :]
138
-
139
- c .removeConnsMx .Unlock ()
137
+ removeConns := c .removeConns
138
+ c .removeConns = nil
139
+ c .removeConnsMx .Unlock ()
140
+ for _ , p := range removeConns {
140
141
c .notifyPeer (p , false )
141
- c .removeConnsMx .Lock ()
142
142
}
143
143
}
0 commit comments