summaryrefslogtreecommitdiff
path: root/vendor/flume/tests/select_macro.rs
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/flume/tests/select_macro.rs')
-rw-r--r--vendor/flume/tests/select_macro.rs1440
1 files changed, 1440 insertions, 0 deletions
diff --git a/vendor/flume/tests/select_macro.rs b/vendor/flume/tests/select_macro.rs
new file mode 100644
index 0000000..367d8dd
--- /dev/null
+++ b/vendor/flume/tests/select_macro.rs
@@ -0,0 +1,1440 @@
+// //! Tests for the `select!` macro.
+
+// #![deny(unsafe_code)]
+
+// #[macro_use]
+// extern crate crossbeam_channel;
+// extern crate crossbeam_utils;
+
+// use std::any::Any;
+// use std::cell::Cell;
+// use std::ops::Deref;
+// use std::thread;
+// use std::time::{Duration, Instant};
+
+// use crossbeam_channel::{after, bounded, never, tick, unbounded};
+// use crossbeam_channel::{Receiver, RecvError, SendError, Sender, TryRecvError};
+// use crossbeam_utils::thread::scope;
+
+// fn ms(ms: u64) -> Duration {
+// Duration::from_millis(ms)
+// }
+
+// #[test]
+// fn smoke1() {
+// let (s1, r1) = unbounded::<usize>();
+// let (s2, r2) = unbounded::<usize>();
+
+// s1.send(1).unwrap();
+
+// select! {
+// recv(r1) -> v => assert_eq!(v, Ok(1)),
+// recv(r2) -> _ => panic!(),
+// }
+
+// s2.send(2).unwrap();
+
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> v => assert_eq!(v, Ok(2)),
+// }
+// }
+
+// #[test]
+// fn smoke2() {
+// let (_s1, r1) = unbounded::<i32>();
+// let (_s2, r2) = unbounded::<i32>();
+// let (_s3, r3) = unbounded::<i32>();
+// let (_s4, r4) = unbounded::<i32>();
+// let (s5, r5) = unbounded::<i32>();
+
+// s5.send(5).unwrap();
+
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> _ => panic!(),
+// recv(r3) -> _ => panic!(),
+// recv(r4) -> _ => panic!(),
+// recv(r5) -> v => assert_eq!(v, Ok(5)),
+// }
+// }
+
+// #[test]
+// fn disconnected() {
+// let (s1, r1) = unbounded::<i32>();
+// let (s2, r2) = unbounded::<i32>();
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// drop(s1);
+// thread::sleep(ms(500));
+// s2.send(5).unwrap();
+// });
+
+// select! {
+// recv(r1) -> v => assert!(v.is_err()),
+// recv(r2) -> _ => panic!(),
+// default(ms(1000)) => panic!(),
+// }
+
+// r2.recv().unwrap();
+// })
+// .unwrap();
+
+// select! {
+// recv(r1) -> v => assert!(v.is_err()),
+// recv(r2) -> _ => panic!(),
+// default(ms(1000)) => panic!(),
+// }
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// thread::sleep(ms(500));
+// drop(s2);
+// });
+
+// select! {
+// recv(r2) -> v => assert!(v.is_err()),
+// default(ms(1000)) => panic!(),
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn default() {
+// let (s1, r1) = unbounded::<i32>();
+// let (s2, r2) = unbounded::<i32>();
+
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> _ => panic!(),
+// default => {}
+// }
+
+// drop(s1);
+
+// select! {
+// recv(r1) -> v => assert!(v.is_err()),
+// recv(r2) -> _ => panic!(),
+// default => panic!(),
+// }
+
+// s2.send(2).unwrap();
+
+// select! {
+// recv(r2) -> v => assert_eq!(v, Ok(2)),
+// default => panic!(),
+// }
+
+// select! {
+// recv(r2) -> _ => panic!(),
+// default => {},
+// }
+
+// select! {
+// default => {},
+// }
+// }
+
+// #[test]
+// fn timeout() {
+// let (_s1, r1) = unbounded::<i32>();
+// let (s2, r2) = unbounded::<i32>();
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// thread::sleep(ms(1500));
+// s2.send(2).unwrap();
+// });
+
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> _ => panic!(),
+// default(ms(1000)) => {},
+// }
+
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> v => assert_eq!(v, Ok(2)),
+// default(ms(1000)) => panic!(),
+// }
+// })
+// .unwrap();
+
+// scope(|scope| {
+// let (s, r) = unbounded::<i32>();
+
+// scope.spawn(move |_| {
+// thread::sleep(ms(500));
+// drop(s);
+// });
+
+// select! {
+// default(ms(1000)) => {
+// select! {
+// recv(r) -> v => assert!(v.is_err()),
+// default => panic!(),
+// }
+// }
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn default_when_disconnected() {
+// let (_, r) = unbounded::<i32>();
+
+// select! {
+// recv(r) -> res => assert!(res.is_err()),
+// default => panic!(),
+// }
+
+// let (_, r) = unbounded::<i32>();
+
+// select! {
+// recv(r) -> res => assert!(res.is_err()),
+// default(ms(1000)) => panic!(),
+// }
+
+// let (s, _) = bounded::<i32>(0);
+
+// select! {
+// send(s, 0) -> res => assert!(res.is_err()),
+// default => panic!(),
+// }
+
+// let (s, _) = bounded::<i32>(0);
+
+// select! {
+// send(s, 0) -> res => assert!(res.is_err()),
+// default(ms(1000)) => panic!(),
+// }
+// }
+
+// #[test]
+// fn default_only() {
+// let start = Instant::now();
+// select! {
+// default => {}
+// }
+// let now = Instant::now();
+// assert!(now - start <= ms(50));
+
+// let start = Instant::now();
+// select! {
+// default(ms(500)) => {}
+// }
+// let now = Instant::now();
+// assert!(now - start >= ms(450));
+// assert!(now - start <= ms(550));
+// }
+
+// #[test]
+// fn unblocks() {
+// let (s1, r1) = bounded::<i32>(0);
+// let (s2, r2) = bounded::<i32>(0);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// thread::sleep(ms(500));
+// s2.send(2).unwrap();
+// });
+
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> v => assert_eq!(v, Ok(2)),
+// default(ms(1000)) => panic!(),
+// }
+// })
+// .unwrap();
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// thread::sleep(ms(500));
+// assert_eq!(r1.recv().unwrap(), 1);
+// });
+
+// select! {
+// send(s1, 1) -> _ => {},
+// send(s2, 2) -> _ => panic!(),
+// default(ms(1000)) => panic!(),
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn both_ready() {
+// let (s1, r1) = bounded(0);
+// let (s2, r2) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// thread::sleep(ms(500));
+// s1.send(1).unwrap();
+// assert_eq!(r2.recv().unwrap(), 2);
+// });
+
+// for _ in 0..2 {
+// select! {
+// recv(r1) -> v => assert_eq!(v, Ok(1)),
+// send(s2, 2) -> _ => {},
+// }
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn loop_try() {
+// const RUNS: usize = 20;
+
+// for _ in 0..RUNS {
+// let (s1, r1) = bounded::<i32>(0);
+// let (s2, r2) = bounded::<i32>(0);
+// let (s_end, r_end) = bounded::<()>(0);
+
+// scope(|scope| {
+// scope.spawn(|_| loop {
+// select! {
+// send(s1, 1) -> _ => break,
+// default => {}
+// }
+
+// select! {
+// recv(r_end) -> _ => break,
+// default => {}
+// }
+// });
+
+// scope.spawn(|_| loop {
+// if let Ok(x) = r2.try_recv() {
+// assert_eq!(x, 2);
+// break;
+// }
+
+// select! {
+// recv(r_end) -> _ => break,
+// default => {}
+// }
+// });
+
+// scope.spawn(|_| {
+// thread::sleep(ms(500));
+
+// select! {
+// recv(r1) -> v => assert_eq!(v, Ok(1)),
+// send(s2, 2) -> _ => {},
+// default(ms(500)) => panic!(),
+// }
+
+// drop(s_end);
+// });
+// })
+// .unwrap();
+// }
+// }
+
+// #[test]
+// fn cloning1() {
+// scope(|scope| {
+// let (s1, r1) = unbounded::<i32>();
+// let (_s2, r2) = unbounded::<i32>();
+// let (s3, r3) = unbounded::<()>();
+
+// scope.spawn(move |_| {
+// r3.recv().unwrap();
+// drop(s1.clone());
+// assert_eq!(r3.try_recv(), Err(TryRecvError::Empty));
+// s1.send(1).unwrap();
+// r3.recv().unwrap();
+// });
+
+// s3.send(()).unwrap();
+
+// select! {
+// recv(r1) -> _ => {},
+// recv(r2) -> _ => {},
+// }
+
+// s3.send(()).unwrap();
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn cloning2() {
+// let (s1, r1) = unbounded::<()>();
+// let (s2, r2) = unbounded::<()>();
+// let (_s3, _r3) = unbounded::<()>();
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// recv(r1) -> _ => panic!(),
+// recv(r2) -> _ => {},
+// }
+// });
+
+// thread::sleep(ms(500));
+// drop(s1.clone());
+// s2.send(()).unwrap();
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn preflight1() {
+// let (s, r) = unbounded();
+// s.send(()).unwrap();
+
+// select! {
+// recv(r) -> _ => {}
+// }
+// }
+
+// #[test]
+// fn preflight2() {
+// let (s, r) = unbounded();
+// drop(s.clone());
+// s.send(()).unwrap();
+// drop(s);
+
+// select! {
+// recv(r) -> v => assert!(v.is_ok()),
+// }
+// assert_eq!(r.try_recv(), Err(TryRecvError::Disconnected));
+// }
+
+// #[test]
+// fn preflight3() {
+// let (s, r) = unbounded();
+// drop(s.clone());
+// s.send(()).unwrap();
+// drop(s);
+// r.recv().unwrap();
+
+// select! {
+// recv(r) -> v => assert!(v.is_err())
+// }
+// }
+
+// #[test]
+// fn duplicate_operations() {
+// let (s, r) = unbounded::<i32>();
+// let mut hit = [false; 4];
+
+// while hit.iter().any(|hit| !hit) {
+// select! {
+// recv(r) -> _ => hit[0] = true,
+// recv(r) -> _ => hit[1] = true,
+// send(s, 0) -> _ => hit[2] = true,
+// send(s, 0) -> _ => hit[3] = true,
+// }
+// }
+// }
+
+// #[test]
+// fn nesting() {
+// let (s, r) = unbounded::<i32>();
+
+// select! {
+// send(s, 0) -> _ => {
+// select! {
+// recv(r) -> v => {
+// assert_eq!(v, Ok(0));
+// select! {
+// send(s, 1) -> _ => {
+// select! {
+// recv(r) -> v => {
+// assert_eq!(v, Ok(1));
+// }
+// }
+// }
+// }
+// }
+// }
+// }
+// }
+// }
+
+// #[test]
+// #[should_panic(expected = "send panicked")]
+// fn panic_sender() {
+// fn get() -> Sender<i32> {
+// panic!("send panicked")
+// }
+
+// #[allow(unreachable_code)]
+// {
+// select! {
+// send(get(), panic!()) -> _ => {}
+// }
+// }
+// }
+
+// #[test]
+// #[should_panic(expected = "recv panicked")]
+// fn panic_receiver() {
+// fn get() -> Receiver<i32> {
+// panic!("recv panicked")
+// }
+
+// select! {
+// recv(get()) -> _ => {}
+// }
+// }
+
+// #[test]
+// fn stress_recv() {
+// const COUNT: usize = 10_000;
+
+// let (s1, r1) = unbounded();
+// let (s2, r2) = bounded(5);
+// let (s3, r3) = bounded(100);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// for i in 0..COUNT {
+// s1.send(i).unwrap();
+// r3.recv().unwrap();
+
+// s2.send(i).unwrap();
+// r3.recv().unwrap();
+// }
+// });
+
+// for i in 0..COUNT {
+// for _ in 0..2 {
+// select! {
+// recv(r1) -> v => assert_eq!(v, Ok(i)),
+// recv(r2) -> v => assert_eq!(v, Ok(i)),
+// }
+
+// s3.send(()).unwrap();
+// }
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn stress_send() {
+// const COUNT: usize = 10_000;
+
+// let (s1, r1) = bounded(0);
+// let (s2, r2) = bounded(0);
+// let (s3, r3) = bounded(100);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// for i in 0..COUNT {
+// assert_eq!(r1.recv().unwrap(), i);
+// assert_eq!(r2.recv().unwrap(), i);
+// r3.recv().unwrap();
+// }
+// });
+
+// for i in 0..COUNT {
+// for _ in 0..2 {
+// select! {
+// send(s1, i) -> _ => {},
+// send(s2, i) -> _ => {},
+// }
+// }
+// s3.send(()).unwrap();
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn stress_mixed() {
+// const COUNT: usize = 10_000;
+
+// let (s1, r1) = bounded(0);
+// let (s2, r2) = bounded(0);
+// let (s3, r3) = bounded(100);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// for i in 0..COUNT {
+// s1.send(i).unwrap();
+// assert_eq!(r2.recv().unwrap(), i);
+// r3.recv().unwrap();
+// }
+// });
+
+// for i in 0..COUNT {
+// for _ in 0..2 {
+// select! {
+// recv(r1) -> v => assert_eq!(v, Ok(i)),
+// send(s2, i) -> _ => {},
+// }
+// }
+// s3.send(()).unwrap();
+// }
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn stress_timeout_two_threads() {
+// const COUNT: usize = 20;
+
+// let (s, r) = bounded(2);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// for i in 0..COUNT {
+// if i % 2 == 0 {
+// thread::sleep(ms(500));
+// }
+
+// loop {
+// select! {
+// send(s, i) -> _ => break,
+// default(ms(100)) => {}
+// }
+// }
+// }
+// });
+
+// scope.spawn(|_| {
+// for i in 0..COUNT {
+// if i % 2 == 0 {
+// thread::sleep(ms(500));
+// }
+
+// loop {
+// select! {
+// recv(r) -> v => {
+// assert_eq!(v, Ok(i));
+// break;
+// }
+// default(ms(100)) => {}
+// }
+// }
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn send_recv_same_channel() {
+// let (s, r) = bounded::<i32>(0);
+// select! {
+// send(s, 0) -> _ => panic!(),
+// recv(r) -> _ => panic!(),
+// default(ms(500)) => {}
+// }
+
+// let (s, r) = unbounded::<i32>();
+// select! {
+// send(s, 0) -> _ => {},
+// recv(r) -> _ => panic!(),
+// default(ms(500)) => panic!(),
+// }
+// }
+
+// #[test]
+// fn matching() {
+// const THREADS: usize = 44;
+
+// let (s, r) = &bounded::<usize>(0);
+
+// scope(|scope| {
+// for i in 0..THREADS {
+// scope.spawn(move |_| {
+// select! {
+// recv(r) -> v => assert_ne!(v.unwrap(), i),
+// send(s, i) -> _ => {},
+// }
+// });
+// }
+// })
+// .unwrap();
+
+// assert_eq!(r.try_recv(), Err(TryRecvError::Empty));
+// }
+
+// #[test]
+// fn matching_with_leftover() {
+// const THREADS: usize = 55;
+
+// let (s, r) = &bounded::<usize>(0);
+
+// scope(|scope| {
+// for i in 0..THREADS {
+// scope.spawn(move |_| {
+// select! {
+// recv(r) -> v => assert_ne!(v.unwrap(), i),
+// send(s, i) -> _ => {},
+// }
+// });
+// }
+// s.send(!0).unwrap();
+// })
+// .unwrap();
+
+// assert_eq!(r.try_recv(), Err(TryRecvError::Empty));
+// }
+
+// #[test]
+// fn channel_through_channel() {
+// const COUNT: usize = 1000;
+
+// type T = Box<dyn Any + Send>;
+
+// for cap in 0..3 {
+// let (s, r) = bounded::<T>(cap);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// let mut s = s;
+
+// for _ in 0..COUNT {
+// let (new_s, new_r) = bounded(cap);
+// let new_r: T = Box::new(Some(new_r));
+
+// select! {
+// send(s, new_r) -> _ => {}
+// }
+
+// s = new_s;
+// }
+// });
+
+// scope.spawn(move |_| {
+// let mut r = r;
+
+// for _ in 0..COUNT {
+// r = select! {
+// recv(r) -> msg => {
+// msg.unwrap()
+// .downcast_mut::<Option<Receiver<T>>>()
+// .unwrap()
+// .take()
+// .unwrap()
+// }
+// }
+// }
+// });
+// })
+// .unwrap();
+// }
+// }
+
+// #[test]
+// fn linearizable_default() {
+// const COUNT: usize = 100_000;
+
+// for step in 0..2 {
+// let (start_s, start_r) = bounded::<()>(0);
+// let (end_s, end_r) = bounded::<()>(0);
+
+// let ((s1, r1), (s2, r2)) = if step == 0 {
+// (bounded::<i32>(1), bounded::<i32>(1))
+// } else {
+// (unbounded::<i32>(), unbounded::<i32>())
+// };
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// for _ in 0..COUNT {
+// start_s.send(()).unwrap();
+
+// s1.send(1).unwrap();
+// select! {
+// recv(r1) -> _ => {}
+// recv(r2) -> _ => {}
+// default => unreachable!()
+// }
+
+// end_s.send(()).unwrap();
+// let _ = r2.try_recv();
+// }
+// });
+
+// for _ in 0..COUNT {
+// start_r.recv().unwrap();
+
+// s2.send(1).unwrap();
+// let _ = r1.try_recv();
+
+// end_r.recv().unwrap();
+// }
+// })
+// .unwrap();
+// }
+// }
+
+// #[test]
+// fn linearizable_timeout() {
+// const COUNT: usize = 100_000;
+
+// for step in 0..2 {
+// let (start_s, start_r) = bounded::<()>(0);
+// let (end_s, end_r) = bounded::<()>(0);
+
+// let ((s1, r1), (s2, r2)) = if step == 0 {
+// (bounded::<i32>(1), bounded::<i32>(1))
+// } else {
+// (unbounded::<i32>(), unbounded::<i32>())
+// };
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// for _ in 0..COUNT {
+// start_s.send(()).unwrap();
+
+// s1.send(1).unwrap();
+// select! {
+// recv(r1) -> _ => {}
+// recv(r2) -> _ => {}
+// default(ms(0)) => unreachable!()
+// }
+
+// end_s.send(()).unwrap();
+// let _ = r2.try_recv();
+// }
+// });
+
+// for _ in 0..COUNT {
+// start_r.recv().unwrap();
+
+// s2.send(1).unwrap();
+// let _ = r1.try_recv();
+
+// end_r.recv().unwrap();
+// }
+// })
+// .unwrap();
+// }
+// }
+
+// #[test]
+// fn fairness1() {
+// const COUNT: usize = 10_000;
+
+// let (s1, r1) = bounded::<()>(COUNT);
+// let (s2, r2) = unbounded::<()>();
+
+// for _ in 0..COUNT {
+// s1.send(()).unwrap();
+// s2.send(()).unwrap();
+// }
+
+// let mut hits = [0usize; 4];
+// for _ in 0..COUNT {
+// select! {
+// recv(r1) -> _ => hits[0] += 1,
+// recv(r2) -> _ => hits[1] += 1,
+// recv(after(ms(0))) -> _ => hits[2] += 1,
+// recv(tick(ms(0))) -> _ => hits[3] += 1,
+// }
+// }
+// assert!(hits.iter().all(|x| *x >= COUNT / hits.len() / 2));
+// }
+
+// #[test]
+// fn fairness2() {
+// const COUNT: usize = 10_000;
+
+// let (s1, r1) = unbounded::<()>();
+// let (s2, r2) = bounded::<()>(1);
+// let (s3, r3) = bounded::<()>(0);
+
+// scope(|scope| {
+// scope.spawn(|_| {
+// let (hole, _r) = bounded(0);
+
+// for _ in 0..COUNT {
+// let s1 = if s1.is_empty() { &s1 } else { &hole };
+// let s2 = if s2.is_empty() { &s2 } else { &hole };
+
+// select! {
+// send(s1, ()) -> res => assert!(res.is_ok()),
+// send(s2, ()) -> res => assert!(res.is_ok()),
+// send(s3, ()) -> res => assert!(res.is_ok()),
+// }
+// }
+// });
+
+// let hits = vec![Cell::new(0usize); 3];
+// for _ in 0..COUNT {
+// select! {
+// recv(r1) -> _ => hits[0].set(hits[0].get() + 1),
+// recv(r2) -> _ => hits[1].set(hits[1].get() + 1),
+// recv(r3) -> _ => hits[2].set(hits[2].get() + 1),
+// }
+// }
+// assert!(hits.iter().all(|x| x.get() >= COUNT / hits.len() / 50));
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn fairness_recv() {
+// const COUNT: usize = 10_000;
+
+// let (s1, r1) = bounded::<()>(COUNT);
+// let (s2, r2) = unbounded::<()>();
+
+// for _ in 0..COUNT {
+// s1.send(()).unwrap();
+// s2.send(()).unwrap();
+// }
+
+// let mut hits = [0usize; 2];
+// while hits[0] + hits[1] < COUNT {
+// select! {
+// recv(r1) -> _ => hits[0] += 1,
+// recv(r2) -> _ => hits[1] += 1,
+// }
+// }
+// assert!(hits.iter().all(|x| *x >= COUNT / 4));
+// }
+
+// #[test]
+// fn fairness_send() {
+// const COUNT: usize = 10_000;
+
+// let (s1, _r1) = bounded::<()>(COUNT);
+// let (s2, _r2) = unbounded::<()>();
+
+// let mut hits = [0usize; 2];
+// for _ in 0..COUNT {
+// select! {
+// send(s1, ()) -> _ => hits[0] += 1,
+// send(s2, ()) -> _ => hits[1] += 1,
+// }
+// }
+// assert!(hits.iter().all(|x| *x >= COUNT / 4));
+// }
+
+// #[test]
+// fn references() {
+// let (s, r) = unbounded::<i32>();
+// select! {
+// send(s, 0) -> _ => {}
+// recv(r) -> _ => {}
+// }
+// select! {
+// send(&&&&s, 0) -> _ => {}
+// recv(&&&&r) -> _ => {}
+// }
+// select! {
+// recv(Some(&r).unwrap_or(&never())) -> _ => {},
+// default => {}
+// }
+// select! {
+// recv(Some(r).unwrap_or(never())) -> _ => {},
+// default => {}
+// }
+// }
+
+// #[test]
+// fn case_blocks() {
+// let (s, r) = unbounded::<i32>();
+
+// select! {
+// recv(r) -> _ => 3.0,
+// recv(r) -> _ => loop {
+// unreachable!()
+// },
+// recv(r) -> _ => match 7 + 3 {
+// _ => unreachable!()
+// },
+// default => 7.
+// };
+
+// select! {
+// recv(r) -> msg => if msg.is_ok() {
+// unreachable!()
+// },
+// default => ()
+// }
+
+// drop(s);
+// }
+
+// #[test]
+// fn move_handles() {
+// let (s, r) = unbounded::<i32>();
+// select! {
+// recv((move || r)()) -> _ => {}
+// send((move || s)(), 0) -> _ => {}
+// }
+// }
+
+// #[test]
+// fn infer_types() {
+// let (s, r) = unbounded();
+// select! {
+// recv(r) -> _ => {}
+// default => {}
+// }
+// s.send(()).unwrap();
+
+// let (s, r) = unbounded();
+// select! {
+// send(s, ()) -> _ => {}
+// }
+// r.recv().unwrap();
+// }
+
+// #[test]
+// fn default_syntax() {
+// let (s, r) = bounded::<i32>(0);
+
+// select! {
+// recv(r) -> _ => panic!(),
+// default => {}
+// }
+// select! {
+// send(s, 0) -> _ => panic!(),
+// default() => {}
+// }
+// select! {
+// default => {}
+// }
+// select! {
+// default() => {}
+// }
+// }
+
+// #[test]
+// fn same_variable_name() {
+// let (_, r) = unbounded::<i32>();
+// select! {
+// recv(r) -> r => assert!(r.is_err()),
+// }
+// }
+
+// #[test]
+// fn handles_on_heap() {
+// let (s, r) = unbounded::<i32>();
+// let (s, r) = (Box::new(s), Box::new(r));
+
+// select! {
+// send(*s, 0) -> _ => {}
+// recv(*r) -> _ => {}
+// default => {}
+// }
+
+// drop(s);
+// drop(r);
+// }
+
+// #[test]
+// fn once_blocks() {
+// let (s, r) = unbounded::<i32>();
+
+// let once = Box::new(());
+// select! {
+// send(s, 0) -> _ => drop(once),
+// }
+
+// let once = Box::new(());
+// select! {
+// recv(r) -> _ => drop(once),
+// }
+
+// let once1 = Box::new(());
+// let once2 = Box::new(());
+// select! {
+// send(s, 0) -> _ => drop(once1),
+// default => drop(once2),
+// }
+
+// let once1 = Box::new(());
+// let once2 = Box::new(());
+// select! {
+// recv(r) -> _ => drop(once1),
+// default => drop(once2),
+// }
+
+// let once1 = Box::new(());
+// let once2 = Box::new(());
+// select! {
+// recv(r) -> _ => drop(once1),
+// send(s, 0) -> _ => drop(once2),
+// }
+// }
+
+// #[test]
+// fn once_receiver() {
+// let (_, r) = unbounded::<i32>();
+
+// let once = Box::new(());
+// let get = move || {
+// drop(once);
+// r
+// };
+
+// select! {
+// recv(get()) -> _ => {}
+// }
+// }
+
+// #[test]
+// fn once_sender() {
+// let (s, _) = unbounded::<i32>();
+
+// let once = Box::new(());
+// let get = move || {
+// drop(once);
+// s
+// };
+
+// select! {
+// send(get(), 5) -> _ => {}
+// }
+// }
+
+// #[test]
+// fn parse_nesting() {
+// let (_, r) = unbounded::<i32>();
+
+// select! {
+// recv(r) -> _ => {}
+// recv(r) -> _ => {
+// select! {
+// recv(r) -> _ => {}
+// recv(r) -> _ => {
+// select! {
+// recv(r) -> _ => {}
+// recv(r) -> _ => {
+// select! {
+// default => {}
+// }
+// }
+// }
+// }
+// }
+// }
+// }
+// }
+
+// #[test]
+// fn evaluate() {
+// let (s, r) = unbounded::<i32>();
+
+// let v = select! {
+// recv(r) -> _ => "foo".into(),
+// send(s, 0) -> _ => "bar".to_owned(),
+// default => "baz".to_string(),
+// };
+// assert_eq!(v, "bar");
+
+// let v = select! {
+// recv(r) -> _ => "foo".into(),
+// default => "baz".to_string(),
+// };
+// assert_eq!(v, "foo");
+
+// let v = select! {
+// recv(r) -> _ => "foo".into(),
+// default => "baz".to_string(),
+// };
+// assert_eq!(v, "baz");
+// }
+
+// #[test]
+// fn deref() {
+// use crossbeam_channel as cc;
+
+// struct Sender<T>(cc::Sender<T>);
+// struct Receiver<T>(cc::Receiver<T>);
+
+// impl<T> Deref for Receiver<T> {
+// type Target = cc::Receiver<T>;
+
+// fn deref(&self) -> &Self::Target {
+// &self.0
+// }
+// }
+
+// impl<T> Deref for Sender<T> {
+// type Target = cc::Sender<T>;
+
+// fn deref(&self) -> &Self::Target {
+// &self.0
+// }
+// }
+
+// let (s, r) = bounded::<i32>(0);
+// let (s, r) = (Sender(s), Receiver(r));
+
+// select! {
+// send(s, 0) -> _ => panic!(),
+// recv(r) -> _ => panic!(),
+// default => {}
+// }
+// }
+
+// #[test]
+// fn result_types() {
+// let (s, _) = bounded::<i32>(0);
+// let (_, r) = bounded::<i32>(0);
+
+// select! {
+// recv(r) -> res => drop::<Result<i32, RecvError>>(res),
+// }
+// select! {
+// recv(r) -> res => drop::<Result<i32, RecvError>>(res),
+// default => {}
+// }
+// select! {
+// recv(r) -> res => drop::<Result<i32, RecvError>>(res),
+// default(ms(0)) => {}
+// }
+
+// select! {
+// send(s, 0) -> res => drop::<Result<(), SendError<i32>>>(res),
+// }
+// select! {
+// send(s, 0) -> res => drop::<Result<(), SendError<i32>>>(res),
+// default => {}
+// }
+// select! {
+// send(s, 0) -> res => drop::<Result<(), SendError<i32>>>(res),
+// default(ms(0)) => {}
+// }
+
+// select! {
+// send(s, 0) -> res => drop::<Result<(), SendError<i32>>>(res),
+// recv(r) -> res => drop::<Result<i32, RecvError>>(res),
+// }
+// }
+
+// #[test]
+// fn try_recv() {
+// let (s, r) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// recv(r) -> _ => panic!(),
+// default => {}
+// }
+// thread::sleep(ms(1500));
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(7)),
+// default => panic!(),
+// }
+// thread::sleep(ms(500));
+// select! {
+// recv(r) -> v => assert_eq!(v, Err(RecvError)),
+// default => panic!(),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1000));
+// select! {
+// send(s, 7) -> res => res.unwrap(),
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn recv() {
+// let (s, r) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(7)),
+// }
+// thread::sleep(ms(1000));
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(8)),
+// }
+// thread::sleep(ms(1000));
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(9)),
+// }
+// select! {
+// recv(r) -> v => assert_eq!(v, Err(RecvError)),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1500));
+// select! {
+// send(s, 7) -> res => res.unwrap(),
+// }
+// select! {
+// send(s, 8) -> res => res.unwrap(),
+// }
+// select! {
+// send(s, 9) -> res => res.unwrap(),
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn recv_timeout() {
+// let (s, r) = bounded::<i32>(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// recv(r) -> _ => panic!(),
+// default(ms(1000)) => {}
+// }
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(7)),
+// default(ms(1000)) => panic!(),
+// }
+// select! {
+// recv(r) -> v => assert_eq!(v, Err(RecvError)),
+// default(ms(1000)) => panic!(),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1500));
+// select! {
+// send(s, 7) -> res => res.unwrap(),
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn try_send() {
+// let (s, r) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// send(s, 7) -> _ => panic!(),
+// default => {}
+// }
+// thread::sleep(ms(1500));
+// select! {
+// send(s, 8) -> res => res.unwrap(),
+// default => panic!(),
+// }
+// thread::sleep(ms(500));
+// select! {
+// send(s, 8) -> res => assert_eq!(res, Err(SendError(8))),
+// default => panic!(),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1000));
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(8)),
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn send() {
+// let (s, r) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// send(s, 7) -> res => res.unwrap(),
+// }
+// thread::sleep(ms(1000));
+// select! {
+// send(s, 8) -> res => res.unwrap(),
+// }
+// thread::sleep(ms(1000));
+// select! {
+// send(s, 9) -> res => res.unwrap(),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1500));
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(7)),
+// }
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(8)),
+// }
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(9)),
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn send_timeout() {
+// let (s, r) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// send(s, 7) -> _ => panic!(),
+// default(ms(1000)) => {}
+// }
+// select! {
+// send(s, 8) -> res => res.unwrap(),
+// default(ms(1000)) => panic!(),
+// }
+// select! {
+// send(s, 9) -> res => assert_eq!(res, Err(SendError(9))),
+// default(ms(1000)) => panic!(),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1500));
+// select! {
+// recv(r) -> v => assert_eq!(v, Ok(8)),
+// }
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn disconnect_wakes_sender() {
+// let (s, r) = bounded(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// send(s, ()) -> res => assert_eq!(res, Err(SendError(()))),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1000));
+// drop(r);
+// });
+// })
+// .unwrap();
+// }
+
+// #[test]
+// fn disconnect_wakes_receiver() {
+// let (s, r) = bounded::<()>(0);
+
+// scope(|scope| {
+// scope.spawn(move |_| {
+// select! {
+// recv(r) -> res => assert_eq!(res, Err(RecvError)),
+// }
+// });
+// scope.spawn(move |_| {
+// thread::sleep(ms(1000));
+// drop(s);
+// });
+// })
+// .unwrap();
+// }