logo
pub fn single_threaded<F, R>(f: F) -> R where
    F: FnOnce() -> R, 
Expand description

Run a function single threaded. Note: This will fail badly if the called function panics or calls RF_error.

use extendr_api::prelude::*;
use std::sync::atomic::{AtomicU32, Ordering};
static GLOBAL_THREAD_COUNT: AtomicU32 = AtomicU32::new(0);

let threads : Vec<_> = (0..100).map(|_| {
   std::thread::spawn(move|| {
      single_threaded(|| {
        // check that we are single threaded.
        let old_thread_count = GLOBAL_THREAD_COUNT.fetch_add(1, Ordering::AcqRel);
        assert_eq!(old_thread_count, 0);
        std::thread::sleep(std::time::Duration::from_millis(1));
        GLOBAL_THREAD_COUNT.fetch_sub(1, Ordering::AcqRel);
        // recursive calls are ok.
        assert_eq!(single_threaded(|| {
          1
        }), 1);    
      })
   })
}).collect();