1use std::{
17 collections::HashSet,
18 fmt,
19 io,
20 net::{IpAddr, SocketAddr},
21 ops::Deref,
22 sync::{
23 Arc,
24 atomic::{AtomicUsize, Ordering::*},
25 },
26 time::{Duration, Instant},
27};
28
29use anyhow::anyhow;
30#[cfg(feature = "locktick")]
31use locktick::parking_lot::Mutex;
32use once_cell::sync::OnceCell;
33#[cfg(not(feature = "locktick"))]
34use parking_lot::Mutex;
35use tokio::{
36 io::split,
37 net::{TcpListener, TcpSocket, TcpStream},
38 sync::{OwnedSemaphorePermit, Semaphore, oneshot},
39 task::{JoinHandle, JoinSet},
40 time::timeout,
41};
42use tracing::*;
43
44use crate::{
45 BannedPeers,
46 Config,
47 KnownPeers,
48 Stats,
49 connections::{Connection, ConnectionSide, Connections, DisconnectOrigin, create_connection_span},
50 protocols::{Protocol, Protocols},
51};
52
53static SEQUENTIAL_NODE_ID: AtomicUsize = AtomicUsize::new(0);
55
56#[derive(Clone)]
58pub struct Tcp(Arc<InnerTcp>);
59
60impl Deref for Tcp {
61 type Target = Arc<InnerTcp>;
62
63 fn deref(&self) -> &Self::Target {
64 &self.0
65 }
66}
67
68pub trait ApplicationError: Send + Sync + std::fmt::Debug + std::fmt::Display + 'static {}
70
71#[allow(missing_docs)]
73#[derive(thiserror::Error, Debug)]
74pub enum ConnectError {
75 #[error("already reached the maximum number of {limit} connections")]
76 MaximumConnectionsReached { limit: u16 },
77 #[error("already connecting to node at {address:?}")]
78 AlreadyConnecting { address: SocketAddr },
79 #[error("already connected to node at {address:?}")]
80 AlreadyConnected { address: SocketAddr },
81 #[error("attempt to self-connect (at address {address:?}")]
82 SelfConnect { address: SocketAddr },
83 #[error("rejected a connection attempt from a banned IP '{ip}'")]
84 BannedIp { ip: IpAddr },
85 #[error(transparent)]
87 IoError(std::io::Error),
88 #[error("{0}")]
91 ApplicationError(Box<dyn ApplicationError>),
92 #[error(transparent)]
96 Other(#[from] Box<dyn std::error::Error + Send + Sync>),
97}
98
99impl ConnectError {
100 pub fn application<E: ApplicationError>(err: E) -> Self {
102 Self::ApplicationError(Box::new(err))
103 }
104
105 pub fn other<E: Into<Box<dyn std::error::Error + Send + Sync>>>(err: E) -> Self {
107 Self::Other(err.into())
108 }
109}
110
111impl From<ConnectError> for std::io::Error {
112 fn from(err: ConnectError) -> Self {
113 match err {
114 ConnectError::IoError(err) => err,
115 ConnectError::Other(err) => std::io::Error::other(err),
116 err => std::io::Error::other(err.to_string()),
117 }
118 }
119}
120
121impl From<std::io::Error> for ConnectError {
122 fn from(err: std::io::Error) -> Self {
123 if err.kind() == std::io::ErrorKind::Other {
125 let inner = err.into_inner().unwrap_or_else(|| anyhow!("Unknown error").into());
127 ConnectError::other(inner)
128 } else {
129 ConnectError::IoError(err)
130 }
131 }
132}
133
134#[doc(hidden)]
135pub struct InnerTcp {
136 span: Span,
138 config: Config,
140 listening_addr: OnceCell<SocketAddr>,
142 pub(crate) protocols: Protocols,
144 connecting: Mutex<HashSet<SocketAddr>>,
146 pub(crate) connections: Connections,
148 known_peers: KnownPeers,
150 banned_peers: BannedPeers,
152 stats: Stats,
154 pub(crate) tasks: Mutex<Vec<JoinHandle<()>>>,
156}
157
158impl Tcp {
159 pub fn new(mut config: Config) -> Self {
161 if config.name.is_none() {
163 config.name = Some(SEQUENTIAL_NODE_ID.fetch_add(1, Relaxed).to_string());
164 }
165
166 let span = crate::helpers::create_span(config.name.as_deref().unwrap());
168
169 let tcp = Tcp(Arc::new(InnerTcp {
171 span,
172 config,
173 listening_addr: Default::default(),
174 protocols: Default::default(),
175 connecting: Default::default(),
176 connections: Default::default(),
177 known_peers: Default::default(),
178 banned_peers: Default::default(),
179 stats: Stats::new(Instant::now()),
180 tasks: Default::default(),
181 }));
182
183 debug!(parent: tcp.span(), "The node is ready");
184
185 tcp
186 }
187
188 pub fn uptime(&self) -> Duration {
190 self.stats.timestamp().elapsed()
191 }
192
193 #[inline]
195 pub fn name(&self) -> &str {
196 self.config.name.as_deref().unwrap()
198 }
199
200 #[inline]
202 pub fn config(&self) -> &Config {
203 &self.config
204 }
205
206 pub fn listening_addr(&self) -> io::Result<SocketAddr> {
209 self.listening_addr.get().copied().ok_or_else(|| io::ErrorKind::AddrNotAvailable.into())
210 }
211
212 pub fn is_connected(&self, addr: SocketAddr) -> bool {
214 self.connections.is_connected(addr)
215 }
216
217 pub fn is_connecting(&self, addr: SocketAddr) -> bool {
219 self.connecting.lock().contains(&addr)
220 }
221
222 pub fn num_connected(&self) -> usize {
224 self.connections.num_connected()
225 }
226
227 pub fn num_connecting(&self) -> usize {
229 self.connecting.lock().len()
230 }
231
232 pub fn connected_addrs(&self) -> Vec<SocketAddr> {
234 self.connections.addrs()
235 }
236
237 pub fn connecting_addrs(&self) -> Vec<SocketAddr> {
239 self.connecting.lock().iter().copied().collect()
240 }
241
242 #[inline]
244 pub fn known_peers(&self) -> &KnownPeers {
245 &self.known_peers
246 }
247
248 #[inline]
250 pub fn banned_peers(&self) -> &BannedPeers {
251 &self.banned_peers
252 }
253
254 #[inline]
256 pub fn stats(&self) -> &Stats {
257 &self.stats
258 }
259
260 #[inline]
262 pub fn span(&self) -> &Span {
263 &self.span
264 }
265
266 pub async fn shut_down(&self) {
268 debug!(parent: self.span(), "Shutting down the TCP stack");
269
270 let mut tasks = std::mem::take(&mut *self.tasks.lock()).into_iter();
272
273 if let Some(listening_task) = tasks.next() {
275 listening_task.abort(); }
277
278 let mut disconnect_tasks = JoinSet::new();
280 for addr in self.connected_addrs() {
281 let node = self.clone();
282 disconnect_tasks.spawn(async move {
283 node.disconnect_w_origin(addr, DisconnectOrigin::Shutdown).await;
284 });
285 }
286 while disconnect_tasks.join_next().await.is_some() {}
287
288 for handle in tasks {
290 handle.abort();
291 }
292 }
293}
294
295impl Tcp {
296 pub async fn connect(&self, addr: SocketAddr) -> Result<(), ConnectError> {
298 if let Ok(listening_addr) = self.listening_addr() {
299 if addr == listening_addr || self.is_self_connect(addr) {
301 error!(parent: self.span(), "Attempted to self-connect ({addr})");
302 return Err(ConnectError::SelfConnect { address: addr });
303 }
304 }
305
306 if !self.can_add_connection() {
307 error!(parent: self.span(), "Too many connections; refusing to connect to {addr}");
308 return Err(ConnectError::MaximumConnectionsReached { limit: self.config.max_connections });
309 }
310
311 if self.is_connected(addr) {
312 trace!(parent: self.span(), "Already connected to {addr}");
313 return Err(ConnectError::AlreadyConnected { address: addr });
314 }
315
316 if !self.connecting.lock().insert(addr) {
317 debug!(parent: self.span(), "Already connecting to {addr}");
318 return Err(ConnectError::AlreadyConnecting { address: addr });
319 }
320
321 let timeout_duration = Duration::from_millis(self.config().connection_timeout_ms.into());
322
323 let res = if let Some(listen_ip) = self.config().listener_ip {
326 timeout(timeout_duration, self.connect_with_specific_interface(listen_ip, addr)).await
327 } else {
328 timeout(timeout_duration, TcpStream::connect(addr)).await
329 };
330
331 let stream = match res {
332 Ok(Ok(stream)) => Ok(stream),
333 Ok(err) => {
334 self.connecting.lock().remove(&addr);
335 err
336 }
337 Err(err) => {
338 self.connecting.lock().remove(&addr);
339 error!("connection timeout error: {}", err);
340 Err(io::ErrorKind::TimedOut.into())
341 }
342 }?;
343
344 let ret = self.adapt_stream(stream, addr, ConnectionSide::Initiator).await;
345
346 if let Err(ref e) = ret {
347 self.connecting.lock().remove(&addr);
348 self.known_peers().register_failure(addr.ip());
349 error!(parent: self.span(), "Unable to initiate a connection with {addr}: {e}");
350 }
351
352 ret.map_err(|err| err.into())
353 }
354
355 async fn connect_with_specific_interface(&self, listen_ip: IpAddr, addr: SocketAddr) -> io::Result<TcpStream> {
356 let sock = if listen_ip.is_ipv4() { TcpSocket::new_v4()? } else { TcpSocket::new_v6()? };
357 sock.bind(SocketAddr::new(listen_ip, 0))?;
359 sock.connect(addr).await
360 }
361
362 pub async fn disconnect(&self, addr: SocketAddr) -> bool {
366 self.disconnect_w_origin(addr, DisconnectOrigin::User).await
367 }
368
369 pub(crate) async fn disconnect_w_origin(&self, addr: SocketAddr, origin: DisconnectOrigin) -> bool {
370 if let Some(conn) = self.connections.0.read().get(&addr) {
372 if conn.disconnecting.swap(true, AcqRel) {
373 return false;
375 }
376 } else {
377 return false;
379 };
380
381 if let Some(handler) = self.protocols.disconnect.get() {
382 let (sender, receiver) = oneshot::channel();
383 handler.trigger(((addr, origin), sender)).await;
384 if let Ok((handle, waiter)) = receiver.await {
385 if let Some(conn) = self.connections.0.write().get_mut(&addr) {
388 conn.tasks.push(handle);
389 }
390 let _ = waiter.await;
392 }
393 }
394
395 let conn = self.connections.remove(addr);
396 let disconnected = conn.is_some();
397
398 if let Some(conn) = conn {
399 debug!(parent: self.span(), "Disconnecting from {addr}");
400
401 drop(conn);
403
404 debug!(parent: self.span(), "Disconnected from {addr}");
405 } else {
406 warn!(parent: self.span(), "Failed to disconnect, was not connected to {addr}");
407 }
408
409 disconnected
410 }
411}
412
413impl Tcp {
414 pub async fn enable_listener(&self) -> io::Result<SocketAddr> {
416 let listener_ip =
418 self.config().listener_ip.expect("Tcp::enable_listener was called, but Config::listener_ip is not set");
419
420 let listener = self.create_listener(listener_ip).await?;
422
423 let port = listener.local_addr()?.port();
425
426 let listening_addr = (listener_ip, port).into();
428 self.listening_addr.set(listening_addr).expect("The node's listener was started more than once");
429
430 let (tx, rx) = oneshot::channel();
432
433 let inbound_permits = Arc::new(Semaphore::new(self.config.max_connections as usize));
438
439 let tcp = self.clone();
440 let listening_task = tokio::spawn(async move {
441 trace!(parent: tcp.span(), "Spawned the listening task");
442 tx.send(()).unwrap(); loop {
445 let permit = match inbound_permits.clone().acquire_owned().await {
447 Ok(p) => p,
448 Err(_) => {
449 error!(parent: tcp.span(), "Inbound permit semaphore closed unexpectedly");
451 return;
452 }
453 };
454
455 match listener.accept().await {
457 Ok((stream, addr)) => tcp.handle_connection(stream, addr, permit),
458 Err(e) => {
459 drop(permit);
461
462 match e.kind() {
463 io::ErrorKind::ConnectionAborted | io::ErrorKind::ConnectionReset => {
465 debug!(parent: tcp.span(), "Transient accept error: {e}");
466 }
467 _ => {
470 error!(parent: tcp.span(), "Couldn't accept a connection: {e}");
471 tokio::time::sleep(Duration::from_millis(500)).await;
472 }
473 }
474 }
475 }
476 }
477 });
478 self.tasks.lock().push(listening_task);
479 let _ = rx.await;
480 debug!(parent: self.span(), "Listening on {listening_addr}");
481
482 Ok(listening_addr)
483 }
484
485 async fn create_listener(&self, listener_ip: IpAddr) -> io::Result<TcpListener> {
487 debug!("Creating a TCP listener on {listener_ip}...");
488 let listener = if let Some(port) = self.config().desired_listening_port {
489 let desired_listening_addr = SocketAddr::new(listener_ip, port);
491 match TcpListener::bind(desired_listening_addr).await {
493 Ok(listener) => listener,
494 Err(e) => {
495 if self.config().allow_random_port {
496 warn!(
497 parent: self.span(),
498 "Trying any listening port, as the desired port is unavailable: {e}"
499 );
500 let random_available_addr = SocketAddr::new(listener_ip, 0);
501 TcpListener::bind(random_available_addr).await?
502 } else {
503 error!(parent: self.span(), "The desired listening port is unavailable: {e}");
504 return Err(e);
505 }
506 }
507 }
508 } else if self.config().allow_random_port {
509 let random_available_addr = SocketAddr::new(listener_ip, 0);
510 TcpListener::bind(random_available_addr).await?
511 } else {
512 panic!("As 'listener_ip' is set, either 'desired_listening_port' or 'allow_random_port' must be set");
513 };
514
515 Ok(listener)
516 }
517
518 fn handle_connection(&self, stream: TcpStream, addr: SocketAddr, permit: OwnedSemaphorePermit) {
520 debug!(parent: self.span(), "Received a connection from {addr}");
521
522 if !self.can_add_connection() || self.is_self_connect(addr) {
523 debug!(parent: self.span(), "Rejecting the connection from {addr}");
524 return;
525 }
526
527 self.connecting.lock().insert(addr);
528
529 let tcp = self.clone();
530 tokio::spawn(async move {
531 let _permit = permit;
533
534 if let Err(e) = tcp.adapt_stream(stream, addr, ConnectionSide::Responder).await {
535 tcp.connecting.lock().remove(&addr);
536 tcp.known_peers().register_failure(addr.ip());
537 error!(parent: tcp.span(), "Failed to connect with {addr}: {e}");
538 }
539 });
540 }
541
542 fn is_self_connect(&self, addr: SocketAddr) -> bool {
544 let listening_addr = self.listening_addr().unwrap();
546
547 match listening_addr.ip().is_loopback() {
548 true => listening_addr.port() == addr.port(),
551 false => listening_addr.ip() == addr.ip(),
553 }
554 }
555
556 fn can_add_connection(&self) -> bool {
558 let num_connected = self.num_connected();
560 let limit = self.config.max_connections as usize;
562
563 if num_connected >= limit {
564 warn!(parent: self.span(), "Maximum number of active connections ({limit}) reached");
565 false
566 } else if num_connected + self.num_connecting() >= limit {
567 warn!(parent: self.span(), "Maximum number of active & pending connections ({limit}) reached");
568 false
569 } else {
570 true
571 }
572 }
573
574 async fn adapt_stream(&self, stream: TcpStream, peer_addr: SocketAddr, own_side: ConnectionSide) -> io::Result<()> {
576 self.known_peers.add(peer_addr.ip());
577
578 if own_side == ConnectionSide::Initiator {
580 if let Ok(addr) = stream.local_addr() {
581 debug!(
582 parent: self.span(), "establishing connection with {}; the peer is connected on port {}",
583 peer_addr, addr.port()
584 );
585 } else {
586 warn!(parent: self.span(), "couldn't determine the peer's port");
587 }
588 }
589
590 let conn_span = create_connection_span(peer_addr, self.span());
591 let connection = Connection::new(peer_addr, stream, !own_side, conn_span);
592
593 let mut connection = self.enable_protocols(connection).await?;
595
596 let conn_ready_tx = connection.readiness_notifier.take();
598
599 self.connections.add(connection);
600 self.connecting.lock().remove(&peer_addr);
601
602 if let Some(tx) = conn_ready_tx {
604 let _ = tx.send(());
605 }
606
607 if let Some(handler) = self.protocols.on_connect.get() {
609 let (sender, receiver) = oneshot::channel();
610 handler.trigger((peer_addr, sender)).await;
611 if let Ok(handle) = receiver.await {
613 if let Some(conn) = self.connections.0.write().get_mut(&peer_addr) {
615 conn.tasks.push(handle);
616 } else {
617 handle.abort();
619 }
620 }
621 }
622
623 Ok(())
624 }
625
626 async fn enable_protocols(&self, conn: Connection) -> io::Result<Connection> {
628 macro_rules! enable_protocol {
630 ($handler_type: ident, $node:expr, $conn: expr) => {
631 if let Some(handler) = $node.protocols.$handler_type.get() {
632 let (conn_returner, conn_retriever) = oneshot::channel();
633
634 handler.trigger(($conn, conn_returner)).await;
635
636 match conn_retriever.await {
637 Ok(Ok(conn)) => conn,
638 Err(_) => return Err(io::ErrorKind::BrokenPipe.into()),
639 Ok(e) => return e,
640 }
641 } else {
642 $conn
643 }
644 };
645 }
646
647 let mut conn = enable_protocol!(handshake, self, conn);
648
649 if let Some(stream) = conn.stream.take() {
651 let (reader, writer) = split(stream);
652 conn.reader = Some(Box::new(reader));
653 conn.writer = Some(Box::new(writer));
654 }
655
656 let conn = enable_protocol!(reading, self, conn);
657 let conn = enable_protocol!(writing, self, conn);
658
659 Ok(conn)
660 }
661}
662
663impl fmt::Debug for Tcp {
664 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
665 write!(f, "The TCP stack config: {:?}", self.config)
666 }
667}
668
669#[cfg(test)]
670mod tests {
671 use super::*;
672
673 use std::{
674 net::{IpAddr, Ipv4Addr},
675 str::FromStr,
676 };
677
678 #[tokio::test]
679 async fn test_new() {
680 let tcp = Tcp::new(Config {
681 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
682 max_connections: 200,
683 ..Default::default()
684 });
685
686 assert_eq!(tcp.config.max_connections, 200);
687 assert_eq!(tcp.config.listener_ip, Some(IpAddr::V4(Ipv4Addr::LOCALHOST)));
688 assert_eq!(tcp.enable_listener().await.unwrap().ip(), IpAddr::V4(Ipv4Addr::LOCALHOST));
689
690 assert_eq!(tcp.num_connected(), 0);
691 assert_eq!(tcp.num_connecting(), 0);
692 }
693
694 #[tokio::test]
695 async fn test_connect() {
696 let tcp = Tcp::new(Config::default());
697 let node_ip = tcp.enable_listener().await.unwrap();
698
699 let result = tcp.connect(node_ip).await;
701 assert!(matches!(result, Err(ConnectError::SelfConnect { .. })));
702
703 assert_eq!(tcp.num_connected(), 0);
704 assert_eq!(tcp.num_connecting(), 0);
705 assert!(!tcp.is_connected(node_ip));
706 assert!(!tcp.is_connecting(node_ip));
707
708 let peer = Tcp::new(Config {
710 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
711 desired_listening_port: Some(0),
712 max_connections: 1,
713 ..Default::default()
714 });
715 let peer_ip = peer.enable_listener().await.unwrap();
716
717 tcp.connect(peer_ip).await.unwrap();
719 assert_eq!(tcp.num_connected(), 1);
720 assert_eq!(tcp.num_connecting(), 0);
721 assert!(tcp.is_connected(peer_ip));
722 assert!(!tcp.is_connecting(peer_ip));
723 }
724
725 #[tokio::test]
726 async fn test_disconnect() {
727 let tcp = Tcp::new(Config::default());
728 let _node_ip = tcp.enable_listener().await.unwrap();
729
730 let peer = Tcp::new(Config {
732 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
733 desired_listening_port: Some(0),
734 max_connections: 1,
735 ..Default::default()
736 });
737 let peer_ip = peer.enable_listener().await.unwrap();
738
739 tcp.connect(peer_ip).await.unwrap();
741 assert_eq!(tcp.num_connected(), 1);
742 assert_eq!(tcp.num_connecting(), 0);
743 assert!(tcp.is_connected(peer_ip));
744 assert!(!tcp.is_connecting(peer_ip));
745
746 let has_disconnected = tcp.disconnect(peer_ip).await;
748 assert!(has_disconnected);
749 assert_eq!(tcp.num_connected(), 0);
750 assert_eq!(tcp.num_connecting(), 0);
751 assert!(!tcp.is_connected(peer_ip));
752 assert!(!tcp.is_connecting(peer_ip));
753
754 let has_disconnected = tcp.disconnect(peer_ip).await;
756 assert!(!has_disconnected);
757 assert_eq!(tcp.num_connected(), 0);
758 assert_eq!(tcp.num_connecting(), 0);
759 assert!(!tcp.is_connected(peer_ip));
760 assert!(!tcp.is_connecting(peer_ip));
761 }
762
763 #[tokio::test]
764 async fn test_can_add_connection() {
765 let tcp = Tcp::new(Config { max_connections: 1, ..Default::default() });
766
767 let peer = Tcp::new(Config {
769 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
770 desired_listening_port: Some(0),
771 max_connections: 1,
772 ..Default::default()
773 });
774 let peer_ip = peer.enable_listener().await.unwrap();
775
776 assert!(tcp.can_add_connection());
777
778 let stream = TcpStream::connect(peer_ip).await.unwrap();
780 tcp.connections.add(Connection::new(peer_ip, stream, ConnectionSide::Initiator, Span::none()));
781 assert!(!tcp.can_add_connection());
782
783 let another_ip = SocketAddr::from_str("1.2.3.4:4242").unwrap();
786 let result = tcp.connect(another_ip).await;
787 assert!(matches!(result, Err(ConnectError::MaximumConnectionsReached { .. })));
788
789 tcp.connections.remove(peer_ip);
791 assert!(tcp.can_add_connection());
792
793 tcp.connecting.lock().insert(peer_ip);
795 assert!(!tcp.can_add_connection());
796
797 let another_ip = SocketAddr::from_str("1.2.3.4:4242").unwrap();
799 let result = tcp.connect(another_ip).await;
800 assert!(matches!(result, Err(ConnectError::MaximumConnectionsReached { .. })));
801
802 tcp.connecting.lock().remove(&peer_ip);
804 assert!(tcp.can_add_connection());
805
806 let stream = TcpStream::connect(peer_ip).await.unwrap();
808 tcp.connections.add(Connection::new(peer_ip, stream, ConnectionSide::Responder, Span::none()));
809 tcp.connecting.lock().insert(peer_ip);
810 assert!(!tcp.can_add_connection());
811
812 tcp.connections.remove(peer_ip);
814 tcp.connecting.lock().remove(&peer_ip);
815 assert!(tcp.can_add_connection());
816 }
817
818 #[tokio::test]
819 async fn test_handle_connection() {
820 let tcp = Tcp::new(Config {
821 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
822 max_connections: 1,
823 ..Default::default()
824 });
825
826 let peer1 = Tcp::new(Config {
828 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
829 desired_listening_port: Some(0),
830 max_connections: 1,
831 ..Default::default()
832 });
833 let peer1_ip = peer1.enable_listener().await.unwrap();
834
835 let stream = TcpStream::connect(peer1_ip).await.unwrap();
837 tcp.connections.add(Connection::new(peer1_ip, stream, ConnectionSide::Responder, Span::none()));
838 assert!(!tcp.can_add_connection());
839 assert_eq!(tcp.num_connected(), 1);
840 assert_eq!(tcp.num_connecting(), 0);
841 assert!(tcp.is_connected(peer1_ip));
842 assert!(!tcp.is_connecting(peer1_ip));
843
844 let peer2 = Tcp::new(Config {
846 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
847 desired_listening_port: Some(0),
848 max_connections: 1,
849 ..Default::default()
850 });
851 let peer2_ip = peer2.enable_listener().await.unwrap();
852
853 let stream = TcpStream::connect(peer2_ip).await.unwrap();
855 let inbound_permits = Arc::new(Semaphore::new(1));
856 let permit = inbound_permits.clone().acquire_owned().await.unwrap();
857 tcp.handle_connection(stream, peer2_ip, permit);
858 assert!(!tcp.can_add_connection());
859 assert_eq!(tcp.num_connected(), 1);
860 assert_eq!(tcp.num_connecting(), 0);
861 assert!(tcp.is_connected(peer1_ip));
862 assert!(!tcp.is_connected(peer2_ip));
863 assert!(!tcp.is_connecting(peer1_ip));
864 assert!(!tcp.is_connecting(peer2_ip));
865 }
866
867 #[tokio::test]
868 async fn test_adapt_stream() {
869 let tcp = Tcp::new(Config { max_connections: 1, ..Default::default() });
870
871 let peer = Tcp::new(Config {
873 listener_ip: Some(IpAddr::V4(Ipv4Addr::LOCALHOST)),
874 desired_listening_port: Some(0),
875 max_connections: 1,
876 ..Default::default()
877 });
878 let peer_ip = peer.enable_listener().await.unwrap();
879
880 tcp.connecting.lock().insert(peer_ip);
882 assert_eq!(tcp.num_connected(), 0);
883 assert_eq!(tcp.num_connecting(), 1);
884 assert!(!tcp.is_connected(peer_ip));
885 assert!(tcp.is_connecting(peer_ip));
886
887 let stream = TcpStream::connect(peer_ip).await.unwrap();
889 tcp.adapt_stream(stream, peer_ip, ConnectionSide::Responder).await.unwrap();
890 assert_eq!(tcp.num_connected(), 1);
891 assert_eq!(tcp.num_connecting(), 0);
892 assert!(tcp.is_connected(peer_ip));
893 assert!(!tcp.is_connecting(peer_ip));
894 }
895}