Skip to content

Commit 8efcd02

Browse files
bors[bot]taiki-e
andauthored
Merge #798
798: channel: Do not panic on very large timeout r=taiki-e a=taiki-e Fixes #795 Co-authored-by: Taiki Endo <[email protected]>
2 parents 113daf4 + baedeb0 commit 8efcd02

File tree

5 files changed

+16
-6
lines changed

5 files changed

+16
-6
lines changed

crossbeam-channel/src/channel.rs

+3-2
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ use crate::err::{
1414
};
1515
use crate::flavors;
1616
use crate::select::{Operation, SelectHandle, Token};
17+
use crate::utils;
1718

1819
/// Creates a channel of unbounded capacity.
1920
///
@@ -471,7 +472,7 @@ impl<T> Sender<T> {
471472
/// );
472473
/// ```
473474
pub fn send_timeout(&self, msg: T, timeout: Duration) -> Result<(), SendTimeoutError<T>> {
474-
self.send_deadline(msg, Instant::now() + timeout)
475+
self.send_deadline(msg, utils::convert_timeout_to_deadline(timeout))
475476
}
476477

477478
/// Waits for a message to be sent into the channel, but only until a given deadline.
@@ -861,7 +862,7 @@ impl<T> Receiver<T> {
861862
/// );
862863
/// ```
863864
pub fn recv_timeout(&self, timeout: Duration) -> Result<T, RecvTimeoutError> {
864-
self.recv_deadline(Instant::now() + timeout)
865+
self.recv_deadline(utils::convert_timeout_to_deadline(timeout))
865866
}
866867

867868
/// Waits for a message to be received from the channel, but only before a given deadline.

crossbeam-channel/src/flavors/at.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ impl Channel {
3535
/// Creates a channel that delivers a message after a certain duration of time.
3636
#[inline]
3737
pub(crate) fn new_timeout(dur: Duration) -> Self {
38-
Self::new_deadline(Instant::now() + dur)
38+
Self::new_deadline(utils::convert_timeout_to_deadline(dur))
3939
}
4040

4141
/// Attempts to receive a message without blocking.

crossbeam-channel/src/flavors/tick.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ use crossbeam_utils::atomic::AtomicCell;
1010
use crate::context::Context;
1111
use crate::err::{RecvTimeoutError, TryRecvError};
1212
use crate::select::{Operation, SelectHandle, Token};
13+
use crate::utils;
1314

1415
/// Result of a receive operation.
1516
pub(crate) type TickToken = Option<Instant>;
@@ -28,7 +29,7 @@ impl Channel {
2829
#[inline]
2930
pub(crate) fn new(dur: Duration) -> Self {
3031
Channel {
31-
delivery_time: AtomicCell::new(Instant::now() + dur),
32+
delivery_time: AtomicCell::new(utils::convert_timeout_to_deadline(dur)),
3233
duration: dur,
3334
}
3435
}

crossbeam-channel/src/select.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -487,7 +487,7 @@ pub fn select_timeout<'a>(
487487
handles: &mut [(&'a dyn SelectHandle, usize, *const u8)],
488488
timeout: Duration,
489489
) -> Result<SelectedOperation<'a>, SelectTimeoutError> {
490-
select_deadline(handles, Instant::now() + timeout)
490+
select_deadline(handles, utils::convert_timeout_to_deadline(timeout))
491491
}
492492

493493
/// Blocks until a given deadline, or until one of the operations becomes ready and selects it.
@@ -1043,7 +1043,7 @@ impl<'a> Select<'a> {
10431043
/// }
10441044
/// ```
10451045
pub fn ready_timeout(&mut self, timeout: Duration) -> Result<usize, ReadyTimeoutError> {
1046-
self.ready_deadline(Instant::now() + timeout)
1046+
self.ready_deadline(utils::convert_timeout_to_deadline(timeout))
10471047
}
10481048

10491049
/// Blocks until a given deadline, or until one of the operations becomes ready.

crossbeam-channel/src/utils.rs

+8
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,14 @@ pub(crate) fn sleep_until(deadline: Option<Instant>) {
6161
}
6262
}
6363

64+
// https://github.com/crossbeam-rs/crossbeam/issues/795
65+
pub(crate) fn convert_timeout_to_deadline(timeout: Duration) -> Instant {
66+
match Instant::now().checked_add(timeout) {
67+
Some(deadline) => deadline,
68+
None => Instant::now() + Duration::from_secs(86400 * 365 * 30),
69+
}
70+
}
71+
6472
/// A simple spinlock.
6573
pub(crate) struct Spinlock<T> {
6674
flag: AtomicBool,

0 commit comments

Comments
 (0)