Skip to content

Commit 779bca8

Browse files
committed
Add a test asserting that concurrent panics work
1 parent 09a4786 commit 779bca8

File tree

2 files changed

+76
-0
lines changed

2 files changed

+76
-0
lines changed

Cargo.toml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -153,3 +153,8 @@ edition = '2018'
153153
name = "accuracy"
154154
required-features = ["std", "dbghelp", "libbacktrace", "libunwind"]
155155
edition = '2018'
156+
157+
[[test]]
158+
name = "concurrent-panics"
159+
required-features = ["std"]
160+
harness = false

tests/concurrent-panics.rs

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
use std::env;
2+
use std::panic;
3+
use std::process::Command;
4+
use std::sync::atomic::{AtomicBool, Ordering::SeqCst};
5+
use std::sync::Arc;
6+
use std::thread;
7+
8+
const PANICS: usize = 100;
9+
const THREADS: usize = 8;
10+
const VAR: &str = "__THE_TEST_YOU_ARE_LUKE";
11+
12+
fn main() {
13+
// These run in docker containers on CI where they can't re-exec the test,
14+
// so just skip these for CI. No other reason this can't run on those
15+
// platforms though.
16+
if cfg!(unix) && (cfg!(target_arch = "arm") || cfg!(target_arch = "aarch64")) {
17+
return;
18+
}
19+
20+
if env::var(VAR).is_err() {
21+
parent();
22+
} else {
23+
child();
24+
}
25+
}
26+
27+
fn parent() {
28+
let me = env::current_exe().unwrap();
29+
let result = Command::new(&me)
30+
.env("RUST_BACKTRACE", "1")
31+
.env(VAR, "1")
32+
.output()
33+
.unwrap();
34+
if result.status.success() {
35+
println!("test result: ok");
36+
return;
37+
}
38+
println!("stdout:\n{}", String::from_utf8_lossy(&result.stdout));
39+
println!("stderr:\n{}", String::from_utf8_lossy(&result.stderr));
40+
println!("code: {}", result.status);
41+
panic!();
42+
}
43+
44+
fn child() {
45+
let done = Arc::new(AtomicBool::new(false));
46+
let done2 = done.clone();
47+
let a = thread::spawn(move || {
48+
while !done2.load(SeqCst) {
49+
format!("{:?}", backtrace::Backtrace::new());
50+
}
51+
});
52+
53+
let threads = (0..THREADS)
54+
.map(|_| {
55+
thread::spawn(|| {
56+
for _ in 0..PANICS {
57+
assert!(panic::catch_unwind(|| {
58+
panic!();
59+
})
60+
.is_err());
61+
}
62+
})
63+
})
64+
.collect::<Vec<_>>();
65+
for thread in threads {
66+
thread.join().unwrap();
67+
}
68+
69+
done.store(true, SeqCst);
70+
a.join().unwrap();
71+
}

0 commit comments

Comments
 (0)