use std::any::Any;
use std::sync::atomic::{AtomicUsize, Ordering};
use std::thread::sleep;
use std::time::Duration;
use crossbeam_utils::thread;
const THREADS: usize = 10 ;
const SMALL_STACK_SIZE: usize = 20 ;
#[ test]
fn join() {
let counter = AtomicUsize::new(0 );
thread::scope(|scope| {
let handle = scope.spawn(|_| {
counter.store(1 , Ordering::Relaxed);
});
assert!(handle.join().is_ok());
let panic_handle = scope.spawn(|_| {
panic!("\" My honey is running out!\", said Pooh." );
});
assert!(panic_handle.join().is_err());
})
.unwrap();
// There should be sufficient synchronization.
assert_eq!(1 , counter.load(Ordering::Relaxed));
}
#[ test]
fn counter() {
let counter = AtomicUsize::new(0 );
thread::scope(|scope| {
for _ in 0 ..THREADS {
scope.spawn(|_| {
counter.fetch_add(1 , Ordering::Relaxed);
});
}
})
.unwrap();
assert_eq!(THREADS, counter.load(Ordering::Relaxed));
}
#[ test]
fn counter_builder() {
let counter = AtomicUsize::new(0 );
thread::scope(|scope| {
for i in 0 ..THREADS {
scope
.builder()
.name(format!("child-{}" , i))
.stack_size(SMALL_STACK_SIZE)
.spawn(|_| {
counter.fetch_add(1 , Ordering::Relaxed);
})
.unwrap();
}
})
.unwrap();
assert_eq!(THREADS, counter.load(Ordering::Relaxed));
}
#[ test]
fn counter_panic() {
let counter = AtomicUsize::new(0 );
let result = thread::scope(|scope| {
scope.spawn(|_| {
panic!("\" My honey is running out!\", said Pooh." );
});
sleep(Duration::from_millis(100 ));
for _ in 0 ..THREADS {
scope.spawn(|_| {
counter.fetch_add(1 , Ordering::Relaxed);
});
}
});
assert_eq!(THREADS, counter.load(Ordering::Relaxed));
assert!(result.is_err());
}
#[ test]
fn panic_twice() {
let result = thread::scope(|scope| {
scope.spawn(|_| {
sleep(Duration::from_millis(500 ));
panic!("thread #1" );
});
scope.spawn(|_| {
panic!("thread #2" );
});
});
let err = result.unwrap_err();
let vec = err
.downcast_ref::<Vec<Box <dyn Any + Send + 'static>>>()
.unwrap();
assert_eq!(2 , vec.len());
let first = vec[0 ].downcast_ref::<&str>().unwrap();
let second = vec[1 ].downcast_ref::<&str>().unwrap();
assert_eq!("thread #1" , *first);
assert_eq!("thread #2" , *second)
}
#[ test]
fn panic_many() {
let result = thread::scope(|scope| {
scope.spawn(|_| panic!("deliberate panic #1" ));
scope.spawn(|_| panic!("deliberate panic #2" ));
scope.spawn(|_| panic!("deliberate panic #3" ));
});
let err = result.unwrap_err();
let vec = err
.downcast_ref::<Vec<Box <dyn Any + Send + 'static>>>()
.unwrap();
assert_eq!(3 , vec.len());
for panic in vec.iter() {
let panic = panic.downcast_ref::<&str>().unwrap();
assert!(
*panic == "deliberate panic #1"
|| *panic == "deliberate panic #2"
|| *panic == "deliberate panic #3"
);
}
}
#[ test]
fn nesting() {
let var = "foo" .to_string();
struct Wrapper<'a> {
var: &'a String,
}
impl <'a> Wrapper<' a> {
fn recurse(&'a self, scope: &thread::Scope<' a>, depth: usize) {
assert_eq!(self .var, "foo" );
if depth > 0 {
scope.spawn(move |scope| {
self .recurse(scope, depth - 1 );
});
}
}
}
let wrapper = Wrapper { var: &var };
thread::scope(|scope| {
scope.spawn(|scope| {
scope.spawn(|scope| {
wrapper.recurse(scope, 5 );
});
});
})
.unwrap();
}
#[ test]
fn join_nested() {
thread::scope(|scope| {
scope.spawn(|scope| {
let handle = scope.spawn(|_| 7 );
sleep(Duration::from_millis(200 ));
handle.join().unwrap();
});
sleep(Duration::from_millis(100 ));
})
.unwrap();
}
#[ test]
fn scope_returns_ok() {
let result = thread::scope(|scope| scope.spawn(|_| 1234 ).join().unwrap()).unwrap();
assert_eq!(result, 1234 );
}
#[ cfg(unix)]
#[ test]
fn as_pthread_t() {
use std::os::unix::thread::JoinHandleExt;
thread::scope(|scope| {
let handle = scope.spawn(|_scope| {
sleep(Duration::from_millis(100 ));
42
});
let _pthread_t = handle.as_pthread_t();
handle.join().unwrap();
})
.unwrap();
}
#[ cfg(windows)]
#[ test]
fn as_raw_handle() {
use std::os::windows::io::AsRawHandle;
thread::scope(|scope| {
let handle = scope.spawn(|_scope| {
sleep(Duration::from_millis(100 ));
42
});
let _raw_handle = handle.as_raw_handle();
handle.join().unwrap();
})
.unwrap();
}
Messung V0.5 in Prozent C=100 H=94 G=96
¤ Dauer der Verarbeitung: 0.8 Sekunden
(vorverarbeitet am 2026-06-25)
¤
*© Formatika GbR, Deutschland