From a11235d05a3e4d7ebff16a9f1315c6e35dfeca30 Mon Sep 17 00:00:00 2001 From: rustaceanrob Date: Sat, 16 Aug 2025 14:24:14 +0100 Subject: [PATCH 1/2] Add TCP handshake timeout parameter Missed this when setting the read/write timeouts. This is probably the most critical timeout. --- src/net.rs | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/src/net.rs b/src/net.rs index 9d5b5c2..25d7679 100644 --- a/src/net.rs +++ b/src/net.rs @@ -26,6 +26,7 @@ use crate::{ pub const READ_TIMEOUT: Duration = Duration::from_secs(60); pub const PING_INTERVAL: Duration = Duration::from_secs(30); +pub const TCP_TIMEOUT: Duration = Duration::from_secs(2); /// Open or begin a connection to an inbound or outbound peer. pub trait ConnectionExt: Send + Sync { @@ -58,7 +59,7 @@ impl ConnectionExt for ConnectionConfig { to: impl Into, timeout_params: TimeoutParams, ) -> Result<(ConnectionWriter, ConnectionReader, ConnectionMetrics), Error> { - let tcp_stream = TcpStream::connect(to.into())?; + let tcp_stream = TcpStream::connect_timeout(&to.into(), timeout_params.tcp)?; tcp_stream.set_read_timeout(timeout_params.read)?; tcp_stream.set_write_timeout(timeout_params.write)?; Self::handshake(self, tcp_stream, timeout_params) @@ -154,6 +155,7 @@ impl ConnectionExt for ConnectionConfig { pub struct TimeoutParams { read: Option, write: Option, + tcp: Duration, ping_interval: Duration, } @@ -170,6 +172,10 @@ impl TimeoutParams { self.write = Some(timeout) } + pub fn tcp_handshake_timeout(&mut self, timeout: Duration) { + self.tcp = timeout; + } + pub fn ping_interval(&mut self, every: Duration) { self.ping_interval = every } @@ -180,6 +186,7 @@ impl Default for TimeoutParams { Self { read: Some(READ_TIMEOUT), write: None, + tcp: TCP_TIMEOUT, ping_interval: PING_INTERVAL, } } From 796ec3541a0bf6e716beddfa31aea756ce8971c7 Mon Sep 17 00:00:00 2001 From: rustaceanrob Date: Sat, 16 Aug 2025 14:31:53 +0100 Subject: [PATCH 2/2] Add missing documentation --- src/lib.rs | 13 ++++++++++++- src/net.rs | 9 +++++++++ 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/src/lib.rs b/src/lib.rs index f27d948..4f5d775 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,3 +1,5 @@ +//! Bitcoin Peer-to-Peer connections. +#![warn(missing_docs)] use std::{ collections::HashMap, sync::{ @@ -143,8 +145,15 @@ impl ConnectionMetrics { /// The rate at which a peer sends a particular message #[derive(Debug, Clone, Copy, PartialEq, PartialOrd)] pub enum MessageRate { + /// No message of this type has been received. NoneReceived, - Ongoing { count: f64, start: Instant }, + /// The total count of messages along with the first message of this type. + Ongoing { + /// Total count of messages + count: f64, + /// The time of the first message + start: Instant, + }, } impl MessageRate { @@ -257,7 +266,9 @@ enum OutboundPing { LastReceived { then: Instant }, } +/// DNS seed provider pub trait SeedsExt { + /// List DNS seeds fn seeds(&self) -> Vec<&str>; } diff --git a/src/net.rs b/src/net.rs index 25d7679..05d65a8 100644 --- a/src/net.rs +++ b/src/net.rs @@ -24,8 +24,11 @@ use crate::{ ConnectionMetrics, OutboundPing, Preferences, TimedMessage, TimedMessages, }; +/// Maximum amount of time the peer has to seed a message after idling. pub const READ_TIMEOUT: Duration = Duration::from_secs(60); +/// The interval to send a new ping message. pub const PING_INTERVAL: Duration = Duration::from_secs(30); +/// The initial TCP handshake timeout. pub const TCP_TIMEOUT: Duration = Duration::from_secs(2); /// Open or begin a connection to an inbound or outbound peer. @@ -151,6 +154,7 @@ impl ConnectionExt for ConnectionConfig { } } +/// Configurations for ending a connection due to inactivity. #[derive(Debug, Clone, Copy, PartialEq, Eq)] pub struct TimeoutParams { read: Option, @@ -160,22 +164,27 @@ pub struct TimeoutParams { } impl TimeoutParams { + /// Construct new timeout parameters pub fn new() -> Self { Self::default() } + /// Set the time a peer has until they have must sent a message. pub fn read_timeout(&mut self, timeout: Duration) { self.read = Some(timeout) } + /// Maximum amount of time it should take to write a message. pub fn write_timeout(&mut self, timeout: Duration) { self.write = Some(timeout) } + /// The initial TCP handshake timeout. pub fn tcp_handshake_timeout(&mut self, timeout: Duration) { self.tcp = timeout; } + /// How often is this peer pinged for activity pub fn ping_interval(&mut self, every: Duration) { self.ping_interval = every }