about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMara Bos <m-ou.se@m-ou.se>2022-03-09 11:47:53 +0100
committerMara Bos <m-ou.se@m-ou.se>2022-03-09 11:47:53 +0100
commitb97d87518d19e418220f726e774ffceadb4d33b9 (patch)
treeeef0c8c6c7a7ef81f3d6447d1aaf08c96f53b3eb
parent1c06eb7c1f416055d7ede098f35bcf22cf85b7f8 (diff)
downloadrust-b97d87518d19e418220f726e774ffceadb4d33b9.tar.gz
rust-b97d87518d19e418220f726e774ffceadb4d33b9.zip
Add soundness test for dropping scoped thread results before joining.
-rw-r--r--library/std/src/thread/tests.rs25
1 files changed, 24 insertions, 1 deletions
diff --git a/library/std/src/thread/tests.rs b/library/std/src/thread/tests.rs
index 27eebd0ddf4..7386fe1c442 100644
--- a/library/std/src/thread/tests.rs
+++ b/library/std/src/thread/tests.rs
@@ -4,10 +4,11 @@ use crate::mem;
 use crate::panic::panic_any;
 use crate::result;
 use crate::sync::{
+    atomic::{AtomicBool, Ordering},
     mpsc::{channel, Sender},
     Arc, Barrier,
 };
-use crate::thread::{self, ThreadId};
+use crate::thread::{self, Scope, ThreadId};
 use crate::time::Duration;
 use crate::time::Instant;
 
@@ -293,3 +294,25 @@ fn test_thread_id_not_equal() {
     assert!(thread::current().id() != spawned_id);
 }
 
+#[test]
+fn test_scoped_threads_drop_result_before_join() {
+    let actually_finished = &AtomicBool::new(false);
+    struct X<'scope, 'env>(&'scope Scope<'scope, 'env>, &'env AtomicBool);
+    impl Drop for X<'_, '_> {
+        fn drop(&mut self) {
+            thread::sleep(Duration::from_millis(20));
+            let actually_finished = self.1;
+            self.0.spawn(move || {
+                thread::sleep(Duration::from_millis(20));
+                actually_finished.store(true, Ordering::Relaxed);
+            });
+        }
+    }
+    thread::scope(|s| {
+        s.spawn(move || {
+            thread::sleep(Duration::from_millis(20));
+            X(s, actually_finished)
+        });
+    });
+    assert!(actually_finished.load(Ordering::Relaxed));
+}