mirror of
https://github.com/tokio-rs/tokio.git
synced 2026-09-08 00:00:13 +02:00
sync: move into tokio crate (#1705)
A step towards collapsing Tokio sub crates into a single `tokio` crate (#1318). The sync implementation is now provided by the main `tokio` crate. Functionality can be opted out of by using the various net related feature flags.
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
use tokio_sync::oneshot;
|
||||
use tokio::sync::oneshot;
|
||||
|
||||
use std::cell::RefCell;
|
||||
use std::collections::VecDeque;
|
||||
|
||||
@@ -0,0 +1,38 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::AtomicWaker;
|
||||
use tokio_test::task::MockTask;
|
||||
|
||||
use std::task::Waker;
|
||||
|
||||
trait AssertSend: Send {}
|
||||
trait AssertSync: Send {}
|
||||
|
||||
impl AssertSend for AtomicWaker {}
|
||||
impl AssertSync for AtomicWaker {}
|
||||
|
||||
impl AssertSend for Waker {}
|
||||
impl AssertSync for Waker {}
|
||||
|
||||
#[test]
|
||||
fn basic_usage() {
|
||||
let waker = AtomicWaker::new();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
task.enter(|cx| waker.register_by_ref(cx.waker()));
|
||||
waker.wake();
|
||||
|
||||
assert!(task.is_woken());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn wake_without_register() {
|
||||
let waker = AtomicWaker::new();
|
||||
waker.wake();
|
||||
|
||||
// Registering should not result in a notification
|
||||
let mut task = MockTask::new();
|
||||
task.enter(|cx| waker.register_by_ref(cx.waker()));
|
||||
|
||||
assert!(!task.is_woken());
|
||||
}
|
||||
@@ -0,0 +1,94 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::Barrier;
|
||||
|
||||
use tokio_test::task::spawn;
|
||||
use tokio_test::{assert_pending, assert_ready};
|
||||
|
||||
struct IsSend<T: Send>(T);
|
||||
#[test]
|
||||
fn barrier_future_is_send() {
|
||||
let b = Barrier::new(0);
|
||||
IsSend(b.wait());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn zero_does_not_block() {
|
||||
let b = Barrier::new(0);
|
||||
|
||||
{
|
||||
let mut w = spawn(b.wait());
|
||||
let wr = assert_ready!(w.poll());
|
||||
assert!(wr.is_leader());
|
||||
}
|
||||
{
|
||||
let mut w = spawn(b.wait());
|
||||
let wr = assert_ready!(w.poll());
|
||||
assert!(wr.is_leader());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn single() {
|
||||
let b = Barrier::new(1);
|
||||
|
||||
{
|
||||
let mut w = spawn(b.wait());
|
||||
let wr = assert_ready!(w.poll());
|
||||
assert!(wr.is_leader());
|
||||
}
|
||||
{
|
||||
let mut w = spawn(b.wait());
|
||||
let wr = assert_ready!(w.poll());
|
||||
assert!(wr.is_leader());
|
||||
}
|
||||
{
|
||||
let mut w = spawn(b.wait());
|
||||
let wr = assert_ready!(w.poll());
|
||||
assert!(wr.is_leader());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn tango() {
|
||||
let b = Barrier::new(2);
|
||||
|
||||
let mut w1 = spawn(b.wait());
|
||||
assert_pending!(w1.poll());
|
||||
|
||||
let mut w2 = spawn(b.wait());
|
||||
let wr2 = assert_ready!(w2.poll());
|
||||
let wr1 = assert_ready!(w1.poll());
|
||||
|
||||
assert!(wr1.is_leader() || wr2.is_leader());
|
||||
assert!(!(wr1.is_leader() && wr2.is_leader()));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn lots() {
|
||||
let b = Barrier::new(100);
|
||||
|
||||
for _ in 0..10 {
|
||||
let mut wait = Vec::new();
|
||||
for _ in 0..99 {
|
||||
let mut w = spawn(b.wait());
|
||||
assert_pending!(w.poll());
|
||||
wait.push(w);
|
||||
}
|
||||
for w in &mut wait {
|
||||
assert_pending!(w.poll());
|
||||
}
|
||||
|
||||
// pass the barrier
|
||||
let mut w = spawn(b.wait());
|
||||
let mut found_leader = assert_ready!(w.poll()).is_leader();
|
||||
for mut w in wait {
|
||||
let wr = assert_ready!(w.poll());
|
||||
if wr.is_leader() {
|
||||
assert!(!found_leader);
|
||||
found_leader = true;
|
||||
}
|
||||
}
|
||||
assert!(found_leader);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
fn is_error<T: ::std::error::Error + Send + Sync>() {}
|
||||
|
||||
#[test]
|
||||
fn mpsc_error_bound() {
|
||||
use tokio::sync::mpsc::error;
|
||||
|
||||
is_error::<error::SendError>();
|
||||
is_error::<error::TrySendError<()>>();
|
||||
is_error::<error::UnboundedRecvError>();
|
||||
is_error::<error::UnboundedSendError>();
|
||||
is_error::<error::UnboundedTrySendError<()>>();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn oneshot_error_bound() {
|
||||
use tokio::sync::oneshot::error;
|
||||
|
||||
is_error::<error::RecvError>();
|
||||
is_error::<error::TryRecvError>();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn watch_error_bound() {
|
||||
use tokio::sync::watch::error;
|
||||
|
||||
is_error::<error::SendError<()>>();
|
||||
}
|
||||
@@ -0,0 +1,451 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::mpsc;
|
||||
use tokio_test::task::MockTask;
|
||||
use tokio_test::{
|
||||
assert_err, assert_ok, assert_pending, assert_ready, assert_ready_err, assert_ready_ok,
|
||||
};
|
||||
|
||||
use std::sync::Arc;
|
||||
|
||||
trait AssertSend: Send {}
|
||||
impl AssertSend for mpsc::Sender<i32> {}
|
||||
impl AssertSend for mpsc::Receiver<i32> {}
|
||||
|
||||
#[test]
|
||||
fn send_recv_with_buffer() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
|
||||
let (mut tx, mut rx) = mpsc::channel::<i32>(16);
|
||||
|
||||
// Using poll_ready / try_send
|
||||
assert_ready_ok!(t1.enter(|cx| tx.poll_ready(cx)));
|
||||
tx.try_send(1).unwrap();
|
||||
|
||||
// Without poll_ready
|
||||
tx.try_send(2).unwrap();
|
||||
|
||||
drop(tx);
|
||||
|
||||
let val = assert_ready!(t2.enter(|cx| rx.poll_recv(cx)));
|
||||
assert_eq!(val, Some(1));
|
||||
|
||||
let val = assert_ready!(t2.enter(|cx| rx.poll_recv(cx)));
|
||||
assert_eq!(val, Some(2));
|
||||
|
||||
let val = assert_ready!(t2.enter(|cx| rx.poll_recv(cx)));
|
||||
assert!(val.is_none());
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn async_send_recv_with_buffer() {
|
||||
let (mut tx, mut rx) = mpsc::channel(16);
|
||||
|
||||
tokio::spawn(async move {
|
||||
assert_ok!(tx.send(1).await);
|
||||
assert_ok!(tx.send(2).await);
|
||||
});
|
||||
|
||||
assert_eq!(Some(1), rx.recv().await);
|
||||
assert_eq!(Some(2), rx.recv().await);
|
||||
assert_eq!(None, rx.recv().await);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn send_sink_recv_with_buffer() {
|
||||
use futures_core::Stream;
|
||||
use futures_sink::Sink;
|
||||
use futures_util::pin_mut;
|
||||
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (tx, rx) = mpsc::channel::<i32>(16);
|
||||
|
||||
t1.enter(|cx| {
|
||||
pin_mut!(tx);
|
||||
|
||||
assert_ready_ok!(tx.as_mut().poll_ready(cx));
|
||||
assert_ok!(tx.as_mut().start_send(1));
|
||||
|
||||
assert_ready_ok!(tx.as_mut().poll_ready(cx));
|
||||
assert_ok!(tx.as_mut().start_send(2));
|
||||
|
||||
assert_ready_ok!(tx.as_mut().poll_flush(cx));
|
||||
assert_ready_ok!(tx.as_mut().poll_close(cx));
|
||||
});
|
||||
|
||||
t1.enter(|cx| {
|
||||
pin_mut!(rx);
|
||||
|
||||
let val = assert_ready!(rx.as_mut().poll_next(cx));
|
||||
assert_eq!(val, Some(1));
|
||||
|
||||
let val = assert_ready!(rx.as_mut().poll_next(cx));
|
||||
assert_eq!(val, Some(2));
|
||||
|
||||
let val = assert_ready!(rx.as_mut().poll_next(cx));
|
||||
assert!(val.is_none());
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn start_send_past_cap() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
let mut t3 = MockTask::new();
|
||||
|
||||
let (mut tx1, mut rx) = mpsc::channel(1);
|
||||
let mut tx2 = tx1.clone();
|
||||
|
||||
assert_ok!(tx1.try_send(()));
|
||||
|
||||
t1.enter(|cx| {
|
||||
assert_pending!(tx1.poll_ready(cx));
|
||||
});
|
||||
|
||||
t2.enter(|cx| {
|
||||
assert_pending!(tx2.poll_ready(cx));
|
||||
});
|
||||
|
||||
drop(tx1);
|
||||
|
||||
let val = t3.enter(|cx| assert_ready!(rx.poll_recv(cx)));
|
||||
assert!(val.is_some());
|
||||
|
||||
assert!(t2.is_woken());
|
||||
assert!(!t1.is_woken());
|
||||
|
||||
drop(tx2);
|
||||
|
||||
let val = t3.enter(|cx| assert_ready!(rx.poll_recv(cx)));
|
||||
assert!(val.is_none());
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[should_panic]
|
||||
fn buffer_gteq_one() {
|
||||
mpsc::channel::<i32>(0);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn send_recv_unbounded() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (mut tx, mut rx) = mpsc::unbounded_channel::<i32>();
|
||||
|
||||
// Using `try_send`
|
||||
assert_ok!(tx.try_send(1));
|
||||
assert_ok!(tx.try_send(2));
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert_eq!(val, Some(1));
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert_eq!(val, Some(2));
|
||||
|
||||
drop(tx);
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert!(val.is_none());
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn async_send_recv_unbounded() {
|
||||
let (mut tx, mut rx) = mpsc::unbounded_channel();
|
||||
|
||||
tokio::spawn(async move {
|
||||
assert_ok!(tx.try_send(1));
|
||||
assert_ok!(tx.try_send(2));
|
||||
});
|
||||
|
||||
assert_eq!(Some(1), rx.recv().await);
|
||||
assert_eq!(Some(2), rx.recv().await);
|
||||
assert_eq!(None, rx.recv().await);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sink_send_recv_unbounded() {
|
||||
use futures_core::Stream;
|
||||
use futures_sink::Sink;
|
||||
use futures_util::pin_mut;
|
||||
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (tx, rx) = mpsc::unbounded_channel::<i32>();
|
||||
|
||||
t1.enter(|cx| {
|
||||
pin_mut!(tx);
|
||||
|
||||
assert_ready_ok!(tx.as_mut().poll_ready(cx));
|
||||
assert_ok!(tx.as_mut().start_send(1));
|
||||
|
||||
assert_ready_ok!(tx.as_mut().poll_ready(cx));
|
||||
assert_ok!(tx.as_mut().start_send(2));
|
||||
|
||||
assert_ready_ok!(tx.as_mut().poll_flush(cx));
|
||||
assert_ready_ok!(tx.as_mut().poll_close(cx));
|
||||
});
|
||||
|
||||
t1.enter(|cx| {
|
||||
pin_mut!(rx);
|
||||
|
||||
let val = assert_ready!(rx.as_mut().poll_next(cx));
|
||||
assert_eq!(val, Some(1));
|
||||
|
||||
let val = assert_ready!(rx.as_mut().poll_next(cx));
|
||||
assert_eq!(val, Some(2));
|
||||
|
||||
let val = assert_ready!(rx.as_mut().poll_next(cx));
|
||||
assert!(val.is_none());
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn no_t_bounds_buffer() {
|
||||
struct NoImpls;
|
||||
|
||||
let mut t1 = MockTask::new();
|
||||
let (tx, mut rx) = mpsc::channel(100);
|
||||
|
||||
// sender should be Debug even though T isn't Debug
|
||||
println!("{:?}", tx);
|
||||
// same with Receiver
|
||||
println!("{:?}", rx);
|
||||
// and sender should be Clone even though T isn't Clone
|
||||
assert!(tx.clone().try_send(NoImpls).is_ok());
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert!(val.is_some());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn no_t_bounds_unbounded() {
|
||||
struct NoImpls;
|
||||
|
||||
let mut t1 = MockTask::new();
|
||||
let (tx, mut rx) = mpsc::unbounded_channel();
|
||||
|
||||
// sender should be Debug even though T isn't Debug
|
||||
println!("{:?}", tx);
|
||||
// same with Receiver
|
||||
println!("{:?}", rx);
|
||||
// and sender should be Clone even though T isn't Clone
|
||||
assert!(tx.clone().try_send(NoImpls).is_ok());
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert!(val.is_some());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn send_recv_buffer_limited() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
|
||||
let (mut tx, mut rx) = mpsc::channel::<i32>(1);
|
||||
|
||||
// Run on a task context
|
||||
t1.enter(|cx| {
|
||||
assert_ready_ok!(tx.poll_ready(cx));
|
||||
|
||||
// Send first message
|
||||
assert_ok!(tx.try_send(1));
|
||||
|
||||
// Not ready
|
||||
assert_pending!(tx.poll_ready(cx));
|
||||
|
||||
// Send second message
|
||||
assert_err!(tx.try_send(1337));
|
||||
});
|
||||
|
||||
t2.enter(|cx| {
|
||||
// Take the value
|
||||
let val = assert_ready!(rx.poll_recv(cx));
|
||||
assert_eq!(Some(1), val);
|
||||
});
|
||||
|
||||
assert!(t1.is_woken());
|
||||
|
||||
t1.enter(|cx| {
|
||||
assert_ready_ok!(tx.poll_ready(cx));
|
||||
|
||||
assert_ok!(tx.try_send(2));
|
||||
|
||||
// Not ready
|
||||
assert_pending!(tx.poll_ready(cx));
|
||||
});
|
||||
|
||||
t2.enter(|cx| {
|
||||
// Take the value
|
||||
let val = assert_ready!(rx.poll_recv(cx));
|
||||
assert_eq!(Some(2), val);
|
||||
});
|
||||
|
||||
t1.enter(|cx| {
|
||||
assert_ready_ok!(tx.poll_ready(cx));
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn recv_close_gets_none_idle() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (mut tx, mut rx) = mpsc::channel::<i32>(10);
|
||||
|
||||
rx.close();
|
||||
|
||||
t1.enter(|cx| {
|
||||
let val = assert_ready!(rx.poll_recv(cx));
|
||||
assert!(val.is_none());
|
||||
assert_ready_err!(tx.poll_ready(cx));
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn recv_close_gets_none_reserved() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
let mut t3 = MockTask::new();
|
||||
|
||||
let (mut tx1, mut rx) = mpsc::channel::<i32>(1);
|
||||
let mut tx2 = tx1.clone();
|
||||
|
||||
assert_ready_ok!(t1.enter(|cx| tx1.poll_ready(cx)));
|
||||
|
||||
t2.enter(|cx| {
|
||||
assert_pending!(tx2.poll_ready(cx));
|
||||
});
|
||||
|
||||
rx.close();
|
||||
|
||||
assert!(t2.is_woken());
|
||||
|
||||
t2.enter(|cx| {
|
||||
assert_ready_err!(tx2.poll_ready(cx));
|
||||
});
|
||||
|
||||
t3.enter(|cx| assert_pending!(rx.poll_recv(cx)));
|
||||
|
||||
assert!(!t1.is_woken());
|
||||
assert!(!t2.is_woken());
|
||||
|
||||
assert_ok!(tx1.try_send(123));
|
||||
|
||||
assert!(t3.is_woken());
|
||||
|
||||
t3.enter(|cx| {
|
||||
let v = assert_ready!(rx.poll_recv(cx));
|
||||
assert_eq!(v, Some(123));
|
||||
|
||||
let v = assert_ready!(rx.poll_recv(cx));
|
||||
assert!(v.is_none());
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn tx_close_gets_none() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (_, mut rx) = mpsc::channel::<i32>(10);
|
||||
|
||||
// Run on a task context
|
||||
t1.enter(|cx| {
|
||||
let v = assert_ready!(rx.poll_recv(cx));
|
||||
assert!(v.is_none());
|
||||
});
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn try_send_fail() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (mut tx, mut rx) = mpsc::channel(1);
|
||||
|
||||
tx.try_send("hello").unwrap();
|
||||
|
||||
// This should fail
|
||||
let err = assert_err!(tx.try_send("fail"));
|
||||
assert!(err.is_full());
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert_eq!(val, Some("hello"));
|
||||
|
||||
assert_ok!(tx.try_send("goodbye"));
|
||||
drop(tx);
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert_eq!(val, Some("goodbye"));
|
||||
|
||||
let val = assert_ready!(t1.enter(|cx| rx.poll_recv(cx)));
|
||||
assert!(val.is_none());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn drop_tx_with_permit_releases_permit() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
|
||||
// poll_ready reserves capacity, ensure that the capacity is released if tx
|
||||
// is dropped w/o sending a value.
|
||||
let (mut tx1, _rx) = mpsc::channel::<i32>(1);
|
||||
let mut tx2 = tx1.clone();
|
||||
|
||||
assert_ready_ok!(t1.enter(|cx| tx1.poll_ready(cx)));
|
||||
|
||||
t2.enter(|cx| {
|
||||
assert_pending!(tx2.poll_ready(cx));
|
||||
});
|
||||
|
||||
drop(tx1);
|
||||
|
||||
assert!(t2.is_woken());
|
||||
|
||||
assert_ready_ok!(t2.enter(|cx| tx2.poll_ready(cx)));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn dropping_rx_closes_channel() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let (mut tx, rx) = mpsc::channel(100);
|
||||
|
||||
let msg = Arc::new(());
|
||||
assert_ok!(tx.try_send(msg.clone()));
|
||||
|
||||
drop(rx);
|
||||
assert_ready_err!(t1.enter(|cx| tx.poll_ready(cx)));
|
||||
|
||||
assert_eq!(1, Arc::strong_count(&msg));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn dropping_rx_closes_channel_for_try() {
|
||||
let (mut tx, rx) = mpsc::channel(100);
|
||||
|
||||
let msg = Arc::new(());
|
||||
tx.try_send(msg.clone()).unwrap();
|
||||
|
||||
drop(rx);
|
||||
|
||||
{
|
||||
let err = assert_err!(tx.try_send(msg.clone()));
|
||||
assert!(err.is_closed());
|
||||
}
|
||||
|
||||
assert_eq!(1, Arc::strong_count(&msg));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn unconsumed_messages_are_dropped() {
|
||||
let msg = Arc::new(());
|
||||
|
||||
let (mut tx, rx) = mpsc::channel(100);
|
||||
|
||||
tx.try_send(msg.clone()).unwrap();
|
||||
|
||||
assert_eq!(2, Arc::strong_count(&msg));
|
||||
|
||||
drop((tx, rx));
|
||||
|
||||
assert_eq!(1, Arc::strong_count(&msg));
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::Mutex;
|
||||
use tokio_test::task::spawn;
|
||||
use tokio_test::{assert_pending, assert_ready};
|
||||
|
||||
use std::sync::Arc;
|
||||
|
||||
#[test]
|
||||
fn straight_execution() {
|
||||
let l = Mutex::new(100);
|
||||
|
||||
{
|
||||
let mut t = spawn(l.lock());
|
||||
let mut g = assert_ready!(t.poll());
|
||||
assert_eq!(&*g, &100);
|
||||
*g = 99;
|
||||
}
|
||||
{
|
||||
let mut t = spawn(l.lock());
|
||||
let mut g = assert_ready!(t.poll());
|
||||
assert_eq!(&*g, &99);
|
||||
*g = 98;
|
||||
}
|
||||
{
|
||||
let mut t = spawn(l.lock());
|
||||
let g = assert_ready!(t.poll());
|
||||
assert_eq!(&*g, &98);
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn readiness() {
|
||||
let l1 = Arc::new(Mutex::new(100));
|
||||
let l2 = Arc::clone(&l1);
|
||||
let mut t1 = spawn(l1.lock());
|
||||
let mut t2 = spawn(l2.lock());
|
||||
|
||||
let g = assert_ready!(t1.poll());
|
||||
|
||||
// We can't now acquire the lease since it's already held in g
|
||||
assert_pending!(t2.poll());
|
||||
|
||||
// But once g unlocks, we can acquire it
|
||||
drop(g);
|
||||
assert!(t2.is_woken());
|
||||
assert_ready!(t2.poll());
|
||||
}
|
||||
|
||||
/*
|
||||
#[test]
|
||||
#[ignore]
|
||||
fn lock() {
|
||||
let mut lock = Mutex::new(false);
|
||||
|
||||
let mut lock2 = lock.clone();
|
||||
std::thread::spawn(move || {
|
||||
let l = lock2.lock();
|
||||
pin_mut!(l);
|
||||
|
||||
let mut task = MockTask::new();
|
||||
let mut g = assert_ready!(task.poll(&mut l));
|
||||
std::thread::sleep(std::time::Duration::from_millis(500));
|
||||
*g = true;
|
||||
drop(g);
|
||||
});
|
||||
|
||||
std::thread::sleep(std::time::Duration::from_millis(50));
|
||||
let mut task = MockTask::new();
|
||||
let l = lock.lock();
|
||||
pin_mut!(l);
|
||||
|
||||
assert_pending!(task.poll(&mut l));
|
||||
|
||||
std::thread::sleep(std::time::Duration::from_millis(500));
|
||||
assert!(task.is_woken());
|
||||
let result = assert_ready!(task.poll(&mut l));
|
||||
assert!(*result);
|
||||
}
|
||||
*/
|
||||
@@ -0,0 +1,228 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::oneshot;
|
||||
use tokio_test::task::MockTask;
|
||||
use tokio_test::*;
|
||||
|
||||
trait AssertSend: Send {}
|
||||
impl AssertSend for oneshot::Sender<i32> {}
|
||||
impl AssertSend for oneshot::Receiver<i32> {}
|
||||
|
||||
#[test]
|
||||
fn send_recv() {
|
||||
let (tx, mut rx) = oneshot::channel();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
assert_pending!(task.poll(&mut rx));
|
||||
|
||||
assert_ok!(tx.send(1));
|
||||
|
||||
assert!(task.is_woken());
|
||||
|
||||
let val = assert_ready_ok!(task.poll(&mut rx));
|
||||
assert_eq!(val, 1);
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn async_send_recv() {
|
||||
let (tx, rx) = oneshot::channel();
|
||||
|
||||
assert_ok!(tx.send(1));
|
||||
assert_eq!(1, assert_ok!(rx.await));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn close_tx() {
|
||||
let (tx, mut rx) = oneshot::channel::<i32>();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
assert_pending!(task.poll(&mut rx));
|
||||
|
||||
drop(tx);
|
||||
|
||||
assert!(task.is_woken());
|
||||
assert_ready_err!(task.poll(&mut rx));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn close_rx() {
|
||||
// First, without checking poll_closed()
|
||||
//
|
||||
let (tx, _) = oneshot::channel();
|
||||
|
||||
assert_err!(tx.send(1));
|
||||
|
||||
// Second, via poll_closed();
|
||||
|
||||
let (mut tx, rx) = oneshot::channel();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
assert_pending!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
drop(rx);
|
||||
|
||||
assert!(task.is_woken());
|
||||
assert!(tx.is_closed());
|
||||
assert_ready!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
assert_err!(tx.send(1));
|
||||
}
|
||||
|
||||
#[tokio::test]
|
||||
async fn async_rx_closed() {
|
||||
let (mut tx, rx) = oneshot::channel::<()>();
|
||||
|
||||
tokio::spawn(async move {
|
||||
drop(rx);
|
||||
});
|
||||
|
||||
tx.closed().await;
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn explicit_close_poll() {
|
||||
// First, with message sent
|
||||
let (tx, mut rx) = oneshot::channel();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
assert_ok!(tx.send(1));
|
||||
|
||||
rx.close();
|
||||
|
||||
let value = assert_ready_ok!(task.poll(&mut rx));
|
||||
assert_eq!(value, 1);
|
||||
|
||||
// Second, without the message sent
|
||||
let (mut tx, mut rx) = oneshot::channel::<i32>();
|
||||
|
||||
assert_pending!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
rx.close();
|
||||
|
||||
assert!(task.is_woken());
|
||||
assert!(tx.is_closed());
|
||||
assert_ready!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
assert_err!(tx.send(1));
|
||||
assert_ready_err!(task.poll(&mut rx));
|
||||
|
||||
// Again, but without sending the value this time
|
||||
let (mut tx, mut rx) = oneshot::channel::<i32>();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
assert_pending!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
rx.close();
|
||||
|
||||
assert!(task.is_woken());
|
||||
assert!(tx.is_closed());
|
||||
assert_ready!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
assert_ready_err!(task.poll(&mut rx));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn explicit_close_try_recv() {
|
||||
// First, with message sent
|
||||
let (tx, mut rx) = oneshot::channel();
|
||||
|
||||
assert_ok!(tx.send(1));
|
||||
|
||||
rx.close();
|
||||
|
||||
let val = assert_ok!(rx.try_recv());
|
||||
assert_eq!(1, val);
|
||||
|
||||
// Second, without the message sent
|
||||
let (mut tx, mut rx) = oneshot::channel::<i32>();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
assert_pending!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
rx.close();
|
||||
|
||||
assert!(task.is_woken());
|
||||
assert!(tx.is_closed());
|
||||
assert_ready!(task.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
assert_err!(rx.try_recv());
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[should_panic]
|
||||
fn close_try_recv_poll() {
|
||||
let (_tx, mut rx) = oneshot::channel::<i32>();
|
||||
let mut task = MockTask::new();
|
||||
|
||||
rx.close();
|
||||
|
||||
assert_err!(rx.try_recv());
|
||||
|
||||
let _ = task.poll(&mut rx);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn drops_tasks() {
|
||||
let (mut tx, mut rx) = oneshot::channel::<i32>();
|
||||
let mut tx_task = MockTask::new();
|
||||
let mut rx_task = MockTask::new();
|
||||
|
||||
assert_pending!(tx_task.enter(|cx| tx.poll_closed(cx)));
|
||||
assert_pending!(rx_task.poll(&mut rx));
|
||||
|
||||
drop(tx);
|
||||
drop(rx);
|
||||
|
||||
assert_eq!(1, tx_task.waker_ref_count());
|
||||
assert_eq!(1, rx_task.waker_ref_count());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn receiver_changes_task() {
|
||||
let (tx, mut rx) = oneshot::channel();
|
||||
|
||||
let mut task1 = MockTask::new();
|
||||
let mut task2 = MockTask::new();
|
||||
|
||||
assert_pending!(task1.poll(&mut rx));
|
||||
|
||||
assert_eq!(2, task1.waker_ref_count());
|
||||
assert_eq!(1, task2.waker_ref_count());
|
||||
|
||||
assert_pending!(task2.poll(&mut rx));
|
||||
|
||||
assert_eq!(1, task1.waker_ref_count());
|
||||
assert_eq!(2, task2.waker_ref_count());
|
||||
|
||||
assert_ok!(tx.send(1));
|
||||
|
||||
assert!(!task1.is_woken());
|
||||
assert!(task2.is_woken());
|
||||
|
||||
assert_ready_ok!(task2.poll(&mut rx));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn sender_changes_task() {
|
||||
let (mut tx, rx) = oneshot::channel::<i32>();
|
||||
|
||||
let mut task1 = MockTask::new();
|
||||
let mut task2 = MockTask::new();
|
||||
|
||||
assert_pending!(task1.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
assert_eq!(2, task1.waker_ref_count());
|
||||
assert_eq!(1, task2.waker_ref_count());
|
||||
|
||||
assert_pending!(task2.enter(|cx| tx.poll_closed(cx)));
|
||||
|
||||
assert_eq!(1, task1.waker_ref_count());
|
||||
assert_eq!(2, task2.waker_ref_count());
|
||||
|
||||
drop(rx);
|
||||
|
||||
assert!(!task1.is_woken());
|
||||
assert!(task2.is_woken());
|
||||
|
||||
assert_ready!(task2.enter(|cx| tx.poll_closed(cx)));
|
||||
}
|
||||
@@ -0,0 +1,153 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::semaphore::{Permit, Semaphore};
|
||||
use tokio_test::task::MockTask;
|
||||
use tokio_test::{assert_pending, assert_ready_err, assert_ready_ok};
|
||||
|
||||
#[test]
|
||||
fn available_permits() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let s = Semaphore::new(100);
|
||||
assert_eq!(s.available_permits(), 100);
|
||||
|
||||
// Polling for a permit succeeds immediately
|
||||
let mut permit = Permit::new();
|
||||
assert!(!permit.is_acquired());
|
||||
|
||||
assert_ready_ok!(t1.enter(|cx| permit.poll_acquire(cx, &s)));
|
||||
assert_eq!(s.available_permits(), 99);
|
||||
assert!(permit.is_acquired());
|
||||
|
||||
// Polling again on the same waiter does not claim a new permit
|
||||
assert_ready_ok!(t1.enter(|cx| permit.poll_acquire(cx, &s)));
|
||||
assert_eq!(s.available_permits(), 99);
|
||||
assert!(permit.is_acquired());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn unavailable_permits() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
let s = Semaphore::new(1);
|
||||
|
||||
let mut permit_1 = Permit::new();
|
||||
let mut permit_2 = Permit::new();
|
||||
|
||||
// Acquire the first permit
|
||||
assert_ready_ok!(t1.enter(|cx| permit_1.poll_acquire(cx, &s)));
|
||||
assert_eq!(s.available_permits(), 0);
|
||||
|
||||
t2.enter(|cx| {
|
||||
// Try to acquire the second permit
|
||||
assert_pending!(permit_2.poll_acquire(cx, &s));
|
||||
});
|
||||
|
||||
permit_1.release(&s);
|
||||
|
||||
assert_eq!(s.available_permits(), 0);
|
||||
assert!(t2.is_woken());
|
||||
assert_ready_ok!(t2.enter(|cx| permit_2.poll_acquire(cx, &s)));
|
||||
|
||||
permit_2.release(&s);
|
||||
assert_eq!(s.available_permits(), 1);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn zero_permits() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let s = Semaphore::new(0);
|
||||
assert_eq!(s.available_permits(), 0);
|
||||
|
||||
let mut permit = Permit::new();
|
||||
|
||||
// Try to acquire the permit
|
||||
t1.enter(|cx| {
|
||||
assert_pending!(permit.poll_acquire(cx, &s));
|
||||
});
|
||||
|
||||
s.add_permits(1);
|
||||
|
||||
assert!(t1.is_woken());
|
||||
assert_ready_ok!(t1.enter(|cx| permit.poll_acquire(cx, &s)));
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[should_panic]
|
||||
fn validates_max_permits() {
|
||||
use std::usize;
|
||||
Semaphore::new((usize::MAX >> 2) + 1);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn close_semaphore_prevents_acquire() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let s = Semaphore::new(1);
|
||||
s.close();
|
||||
|
||||
assert_eq!(1, s.available_permits());
|
||||
|
||||
let mut permit = Permit::new();
|
||||
|
||||
assert_ready_err!(t1.enter(|cx| permit.poll_acquire(cx, &s)));
|
||||
assert_eq!(1, s.available_permits());
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn close_semaphore_notifies_permit1() {
|
||||
let mut t1 = MockTask::new();
|
||||
|
||||
let s = Semaphore::new(0);
|
||||
let mut permit = Permit::new();
|
||||
|
||||
assert_pending!(t1.enter(|cx| permit.poll_acquire(cx, &s)));
|
||||
|
||||
s.close();
|
||||
|
||||
assert!(t1.is_woken());
|
||||
assert_ready_err!(t1.enter(|cx| permit.poll_acquire(cx, &s)));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn close_semaphore_notifies_permit2() {
|
||||
let mut t1 = MockTask::new();
|
||||
let mut t2 = MockTask::new();
|
||||
let mut t3 = MockTask::new();
|
||||
let mut t4 = MockTask::new();
|
||||
|
||||
let s = Semaphore::new(2);
|
||||
|
||||
let mut permit1 = Permit::new();
|
||||
let mut permit2 = Permit::new();
|
||||
let mut permit3 = Permit::new();
|
||||
let mut permit4 = Permit::new();
|
||||
|
||||
// Acquire a couple of permits
|
||||
assert_ready_ok!(t1.enter(|cx| permit1.poll_acquire(cx, &s)));
|
||||
assert_ready_ok!(t2.enter(|cx| permit2.poll_acquire(cx, &s)));
|
||||
|
||||
assert_pending!(t3.enter(|cx| permit3.poll_acquire(cx, &s)));
|
||||
assert_pending!(t4.enter(|cx| permit4.poll_acquire(cx, &s)));
|
||||
|
||||
s.close();
|
||||
|
||||
assert!(t3.is_woken());
|
||||
assert!(t4.is_woken());
|
||||
|
||||
assert_ready_err!(t3.enter(|cx| permit3.poll_acquire(cx, &s)));
|
||||
assert_ready_err!(t4.enter(|cx| permit4.poll_acquire(cx, &s)));
|
||||
|
||||
assert_eq!(0, s.available_permits());
|
||||
|
||||
permit1.release(&s);
|
||||
|
||||
assert_eq!(1, s.available_permits());
|
||||
|
||||
assert_ready_err!(t1.enter(|cx| permit1.poll_acquire(cx, &s)));
|
||||
|
||||
permit2.release(&s);
|
||||
|
||||
assert_eq!(2, s.available_permits());
|
||||
}
|
||||
@@ -0,0 +1,264 @@
|
||||
#![warn(rust_2018_idioms)]
|
||||
|
||||
use tokio::sync::watch;
|
||||
use tokio_test::task::spawn;
|
||||
use tokio_test::{assert_pending, assert_ready};
|
||||
|
||||
#[test]
|
||||
fn single_rx_recv_ref() {
|
||||
let (tx, mut rx) = watch::channel("one");
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.recv_ref());
|
||||
let v = assert_ready!(t.poll()).unwrap();
|
||||
assert_eq!(*v, "one");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.recv_ref());
|
||||
|
||||
assert_pending!(t.poll());
|
||||
|
||||
tx.broadcast("two").unwrap();
|
||||
|
||||
assert!(t.is_woken());
|
||||
|
||||
let v = assert_ready!(t.poll()).unwrap();
|
||||
assert_eq!(*v, "two");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.recv_ref());
|
||||
|
||||
assert_pending!(t.poll());
|
||||
|
||||
drop(tx);
|
||||
|
||||
let res = assert_ready!(t.poll());
|
||||
assert!(res.is_none());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn single_rx_recv() {
|
||||
let (tx, mut rx) = watch::channel("one");
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.recv());
|
||||
let v = assert_ready!(t.poll()).unwrap();
|
||||
assert_eq!(v, "one");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.recv());
|
||||
|
||||
assert_pending!(t.poll());
|
||||
|
||||
tx.broadcast("two").unwrap();
|
||||
|
||||
assert!(t.is_woken());
|
||||
|
||||
let v = assert_ready!(t.poll()).unwrap();
|
||||
assert_eq!(v, "two");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.recv());
|
||||
|
||||
assert_pending!(t.poll());
|
||||
|
||||
drop(tx);
|
||||
|
||||
let res = assert_ready!(t.poll());
|
||||
assert!(res.is_none());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn stream_impl() {
|
||||
use tokio::prelude::*;
|
||||
|
||||
let (tx, mut rx) = watch::channel("one");
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.next());
|
||||
let v = assert_ready!(t.poll()).unwrap();
|
||||
assert_eq!(v, "one");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.next());
|
||||
|
||||
assert_pending!(t.poll());
|
||||
|
||||
tx.broadcast("two").unwrap();
|
||||
|
||||
assert!(t.is_woken());
|
||||
|
||||
let v = assert_ready!(t.poll()).unwrap();
|
||||
assert_eq!(v, "two");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t = spawn(rx.next());
|
||||
|
||||
assert_pending!(t.poll());
|
||||
|
||||
drop(tx);
|
||||
|
||||
let res = assert_ready!(t.poll());
|
||||
assert!(res.is_none());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn multi_rx() {
|
||||
let (tx, mut rx1) = watch::channel("one");
|
||||
let mut rx2 = rx1.clone();
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx1.recv_ref());
|
||||
let mut t2 = spawn(rx2.recv_ref());
|
||||
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "one");
|
||||
|
||||
let res = assert_ready!(t2.poll());
|
||||
assert_eq!(*res.unwrap(), "one");
|
||||
}
|
||||
|
||||
let mut t2 = spawn(rx2.recv_ref());
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx1.recv_ref());
|
||||
|
||||
assert_pending!(t1.poll());
|
||||
assert_pending!(t2.poll());
|
||||
|
||||
tx.broadcast("two").unwrap();
|
||||
|
||||
assert!(t1.is_woken());
|
||||
assert!(t2.is_woken());
|
||||
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "two");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx1.recv_ref());
|
||||
|
||||
assert_pending!(t1.poll());
|
||||
|
||||
tx.broadcast("three").unwrap();
|
||||
|
||||
assert!(t1.is_woken());
|
||||
assert!(t2.is_woken());
|
||||
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "three");
|
||||
|
||||
let res = assert_ready!(t2.poll());
|
||||
assert_eq!(*res.unwrap(), "three");
|
||||
}
|
||||
|
||||
drop(t2);
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx1.recv_ref());
|
||||
let mut t2 = spawn(rx2.recv_ref());
|
||||
|
||||
assert_pending!(t1.poll());
|
||||
assert_pending!(t2.poll());
|
||||
|
||||
tx.broadcast("four").unwrap();
|
||||
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "four");
|
||||
drop(t1);
|
||||
|
||||
let mut t1 = spawn(rx1.recv_ref());
|
||||
assert_pending!(t1.poll());
|
||||
|
||||
drop(tx);
|
||||
|
||||
assert!(t1.is_woken());
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert!(res.is_none());
|
||||
|
||||
let res = assert_ready!(t2.poll());
|
||||
assert_eq!(*res.unwrap(), "four");
|
||||
|
||||
drop(t2);
|
||||
let mut t2 = spawn(rx2.recv_ref());
|
||||
let res = assert_ready!(t2.poll());
|
||||
assert!(res.is_none());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn rx_observes_final_value() {
|
||||
// Initial value
|
||||
|
||||
let (tx, mut rx) = watch::channel("one");
|
||||
drop(tx);
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx.recv_ref());
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "one");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx.recv_ref());
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert!(res.is_none());
|
||||
}
|
||||
|
||||
// Sending a value
|
||||
|
||||
let (tx, mut rx) = watch::channel("one");
|
||||
|
||||
tx.broadcast("two").unwrap();
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx.recv_ref());
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "two");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx.recv_ref());
|
||||
assert_pending!(t1.poll());
|
||||
|
||||
tx.broadcast("three").unwrap();
|
||||
drop(tx);
|
||||
|
||||
assert!(t1.is_woken());
|
||||
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert_eq!(*res.unwrap(), "three");
|
||||
}
|
||||
|
||||
{
|
||||
let mut t1 = spawn(rx.recv_ref());
|
||||
let res = assert_ready!(t1.poll());
|
||||
assert!(res.is_none());
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn poll_close() {
|
||||
let (mut tx, rx) = watch::channel("one");
|
||||
|
||||
{
|
||||
let mut t = spawn(tx.closed());
|
||||
assert_pending!(t.poll());
|
||||
|
||||
drop(rx);
|
||||
|
||||
assert!(t.is_woken());
|
||||
assert_ready!(t.poll());
|
||||
}
|
||||
|
||||
assert!(tx.broadcast("two").is_err());
|
||||
}
|
||||
@@ -274,7 +274,7 @@ fn panic_in_task() {
|
||||
|
||||
#[test]
|
||||
fn multi_threadpool() {
|
||||
use tokio_sync::oneshot;
|
||||
use tokio::sync::oneshot;
|
||||
|
||||
let pool1 = new_pool();
|
||||
let pool2 = new_pool();
|
||||
|
||||
@@ -129,7 +129,6 @@ fn deadline_future_elapses() {
|
||||
});
|
||||
}
|
||||
|
||||
#[cfg(feature = "async-traits")]
|
||||
macro_rules! poll {
|
||||
($task:ident, $stream:ident) => {{
|
||||
use futures_core::Stream;
|
||||
@@ -138,9 +137,8 @@ macro_rules! poll {
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[cfg(feature = "async-traits")]
|
||||
fn stream_and_timeout_in_future() {
|
||||
use tokio_sync::mpsc;
|
||||
use tokio::sync::mpsc;
|
||||
|
||||
let mut t = MockTask::new();
|
||||
|
||||
@@ -168,9 +166,8 @@ fn stream_and_timeout_in_future() {
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[cfg(feature = "async-traits")]
|
||||
fn idle_stream_timesout_periodically() {
|
||||
use tokio_sync::mpsc;
|
||||
use tokio::sync::mpsc;
|
||||
|
||||
let mut t = MockTask::new();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user