@@ -31,6 +31,7 @@ use libp2p_core::{upgrade, ConnectedPoint};
31
31
use libp2p_identity:: PeerId ;
32
32
use libp2p_swarm:: handler:: {
33
33
ConnectionEvent , DialUpgradeError , FullyNegotiatedInbound , FullyNegotiatedOutbound ,
34
+ ProtocolsChange ,
34
35
} ;
35
36
use libp2p_swarm:: {
36
37
ConnectionHandler , ConnectionHandlerEvent , ConnectionHandlerUpgrErr , KeepAlive ,
@@ -92,10 +93,12 @@ pub struct KademliaHandler<TUserData> {
92
93
enum ProtocolStatus {
93
94
/// It is as yet unknown whether the remote supports the
94
95
/// configured protocol name.
95
- Unconfirmed ,
96
+ Unknown ,
96
97
/// The configured protocol name has been confirmed by the remote
97
98
/// but has not yet been reported to the `Kademlia` behaviour.
98
99
Confirmed ,
100
+ /// The configured protocol name(s) are not or no longer supported by the remote.
101
+ NotSupported ,
99
102
/// The configured protocol has been confirmed by the remote
100
103
/// and the confirmation reported to the `Kademlia` behaviour.
101
104
Reported ,
@@ -226,13 +229,11 @@ impl<TUserData> InboundSubstreamState<TUserData> {
226
229
#[ derive( Debug ) ]
227
230
pub enum KademliaHandlerEvent < TUserData > {
228
231
/// The configured protocol name has been confirmed by the peer through
229
- /// a successfully negotiated substream.
230
- ///
231
- /// This event is only emitted once by a handler upon the first
232
- /// successfully negotiated inbound or outbound substream and
233
- /// indicates that the connected peer participates in the Kademlia
234
- /// overlay network identified by the configured protocol name.
232
+ /// a successfully negotiated substream or by learning the supported protocols of the remote.
235
233
ProtocolConfirmed { endpoint : ConnectedPoint } ,
234
+ /// The configured protocol name(s) are not or no longer supported by the peer on the provided
235
+ /// connection and it should be removed from the routing table.
236
+ ProtocolNotSupported { endpoint : ConnectedPoint } ,
236
237
237
238
/// Request for the list of nodes whose IDs are the closest to `key`. The number of nodes
238
239
/// returned is not specified, but should be around 20.
@@ -501,7 +502,7 @@ where
501
502
num_requested_outbound_streams : 0 ,
502
503
requested_streams : Default :: default ( ) ,
503
504
keep_alive,
504
- protocol_status : ProtocolStatus :: Unconfirmed ,
505
+ protocol_status : ProtocolStatus :: Unknown ,
505
506
}
506
507
}
507
508
@@ -520,7 +521,7 @@ where
520
521
protocol, msg, user_data,
521
522
) ) ;
522
523
self . num_requested_outbound_streams -= 1 ;
523
- if let ProtocolStatus :: Unconfirmed = self . protocol_status {
524
+ if let ProtocolStatus :: Unknown = self . protocol_status {
524
525
// Upon the first successfully negotiated substream, we know that the
525
526
// remote is configured with the same protocol name and we want
526
527
// the behaviour to add this peer to the routing table, if possible.
@@ -542,7 +543,7 @@ where
542
543
future:: Either :: Right ( p) => void:: unreachable ( p) ,
543
544
} ;
544
545
545
- if let ProtocolStatus :: Unconfirmed = self . protocol_status {
546
+ if let ProtocolStatus :: Unknown = self . protocol_status {
546
547
// Upon the first successfully negotiated substream, we know that the
547
548
// remote is configured with the same protocol name and we want
548
549
// the behaviour to add this peer to the routing table, if possible.
@@ -789,7 +790,25 @@ where
789
790
ConnectionEvent :: AddressChange ( _)
790
791
| ConnectionEvent :: ListenUpgradeError ( _)
791
792
| ConnectionEvent :: LocalProtocolsChange ( _) => { }
792
- ConnectionEvent :: RemoteProtocolsChange ( _) => { }
793
+ ConnectionEvent :: RemoteProtocolsChange ( ProtocolsChange { protocols } ) => {
794
+ // TODO: We should cache this / it will get simpler with #2831.
795
+ let kademlia_protocols = self
796
+ . config
797
+ . protocol_config
798
+ . protocol_names ( )
799
+ . iter ( )
800
+ . filter_map ( |b| String :: from_utf8 ( b. to_vec ( ) ) . ok ( ) )
801
+ . collect :: < Vec < _ > > ( ) ;
802
+
803
+ let remote_supports_our_kademlia_protocols =
804
+ kademlia_protocols. iter ( ) . all ( |p| protocols. contains ( p) ) ;
805
+
806
+ if remote_supports_our_kademlia_protocols {
807
+ self . protocol_status = ProtocolStatus :: Confirmed ;
808
+ } else {
809
+ self . protocol_status = ProtocolStatus :: NotSupported ;
810
+ }
811
+ }
793
812
}
794
813
}
795
814
}
0 commit comments