diff options
author | 2022-04-29 14:53:01 +0200 | |
---|---|---|
committer | 2022-04-29 15:20:55 +0200 | |
commit | 477c53b25d1451e4771968fcf4c48a5f7381b04f (patch) | |
tree | 45310fa4129f7da40190fcbe9b1e3664d73e3d78 /tests/tsan.rs | |
parent | 9fb9cd70451bd8c4e6ccf51ca3c77b8cb033fc27 (diff) | |
download | heapless-477c53b25d1451e4771968fcf4c48a5f7381b04f.tar.gz heapless-477c53b25d1451e4771968fcf4c48a5f7381b04f.tar.zst heapless-477c53b25d1451e4771968fcf4c48a5f7381b04f.zip |
use std::thread::scope instead of scoped_threadpool
as it's easier to deal with TSAN false positives in the former API
as surfaced in PR 280 the current supression rules don't handle newer versions of the
scoped_threadpool crate
trying to update the supression rules related to scoped_threadpool in PR #282 revealed that the
supression rules are masking (hiding) real data races:
https://github.com/japaric/heapless/pull/282#issuecomment-1113173358
std::thread::scope requires less supression rules and does not mask real data races -- for instance,
the data race in the linked issue comment is not masked when using std::thread::scope
tradeoffs:
- pro: one less dev dependency
- pro: supressions file is simpler
- cons: std::thread::scope is only available on recent nightlies
Diffstat (limited to '')
-rw-r--r-- | tests/tsan.rs | 32 |
1 files changed, 16 insertions, 16 deletions
diff --git a/tests/tsan.rs b/tests/tsan.rs index 22a51958..a207e125 100644 --- a/tests/tsan.rs +++ b/tests/tsan.rs @@ -1,3 +1,4 @@ +#![feature(scoped_threads)] #![deny(rust_2018_compatibility)] #![deny(rust_2018_idioms)] #![deny(warnings)] @@ -5,7 +6,6 @@ use std::{sync::mpsc, thread}; use heapless::{mpmc::Q64, spsc}; -use scoped_threadpool::Pool; #[test] fn once() { @@ -59,12 +59,12 @@ fn scoped() { { let (mut p, mut c) = rb.split(); - Pool::new(2).scoped(move |scope| { - scope.execute(move || { + thread::scope(move |scope| { + scope.spawn(move || { p.enqueue(1).unwrap(); }); - scope.execute(move || { + scope.spawn(move || { c.dequeue().unwrap(); }); }); @@ -83,8 +83,8 @@ fn contention() { { let (mut p, mut c) = rb.split(); - Pool::new(2).scoped(move |scope| { - scope.execute(move || { + thread::scope(move |scope| { + scope.spawn(move || { let mut sum: u32 = 0; for i in 0..(2 * N) { @@ -95,7 +95,7 @@ fn contention() { println!("producer: {}", sum); }); - scope.execute(move || { + scope.spawn(move || { let mut sum: u32 = 0; for _ in 0..(2 * N) { @@ -126,9 +126,9 @@ fn mpmc_contention() { static Q: Q64<u32> = Q64::new(); let (s, r) = mpsc::channel(); - Pool::new(2).scoped(|scope| { + thread::scope(|scope| { let s1 = s.clone(); - scope.execute(move || { + scope.spawn(move || { let mut sum: u32 = 0; for i in 0..(16 * N) { @@ -141,7 +141,7 @@ fn mpmc_contention() { }); let s2 = s.clone(); - scope.execute(move || { + scope.spawn(move || { let mut sum: u32 = 0; for _ in 0..(16 * N) { @@ -178,14 +178,14 @@ fn unchecked() { { let (mut p, mut c) = rb.split(); - Pool::new(2).scoped(move |scope| { - scope.execute(move || { + thread::scope(move |scope| { + scope.spawn(move || { for _ in 0..N / 2 - 1 { p.enqueue(2).unwrap(); } }); - scope.execute(move || { + scope.spawn(move || { let mut sum: usize = 0; for _ in 0..N / 2 - 1 { @@ -246,8 +246,8 @@ fn pool() { A::grow(unsafe { &mut M }); - Pool::new(2).scoped(move |scope| { - scope.execute(move || { + thread::pool(move |scope| { + scope.spawn(move || { for _ in 0..N / 4 { let a = A::alloc().unwrap(); let b = A::alloc().unwrap(); @@ -257,7 +257,7 @@ fn pool() { } }); - scope.execute(move || { + scope.spawn(move || { for _ in 0..N / 2 { let a = A::alloc().unwrap(); let a = a.init([2; 8]); |