SHARE
TWEET

Untitled

a guest Jul 18th, 2019 84 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. use std::sync::atomic::{AtomicUsize, Ordering};
  2.  
  3. // Usage: Make a 4 KiB file located at /mnt/tmpfstest/test.bin and run the
  4. // tool with `cargo run --release`
  5.  
  6. /// Runs multiple threads at a time incrementally displaying the syscall
  7. /// throughput of 4-KiB random reads to a `tmpfs` hosted mountpoint
  8. fn benchmark_random_read_scaling() {
  9.     for num_threads in 1..=256 {
  10.         /// Lock to wait for all threads to spawn
  11.         static THREAD_LOCKSTEPPER: AtomicUsize = AtomicUsize::new(0);
  12.  
  13.         /// CPU time spent (in cycles)
  14.         static CYCLES: AtomicUsize = AtomicUsize::new(0);
  15.  
  16.         /// Number of file accesses to perform per thread
  17.         const NUM_ACCESSES: usize = 4096;
  18.  
  19.         let mut threads = Vec::new();
  20.  
  21.         // Reset lock and performance information
  22.         THREAD_LOCKSTEPPER.store(0, Ordering::SeqCst);
  23.         CYCLES.store(0, Ordering::SeqCst);
  24.  
  25.         for thr in 0..num_threads {
  26.             threads.push(std::thread::spawn(move || {
  27.                 // Wait for all threads to come online in a busy loop
  28.                 THREAD_LOCKSTEPPER.fetch_add(1, Ordering::SeqCst);
  29.                 while THREAD_LOCKSTEPPER
  30.                     .load(Ordering::SeqCst) != num_threads {}
  31.  
  32.                 // Start a "timer" by storing the current CPU cycle count
  33.                 let start = unsafe { core::arch::x86_64::_rdtsc() };
  34.  
  35.                 for _ in 0..NUM_ACCESSES {
  36.                     assert!(std::fs::read("/mnt/tmpfstest/test.bin")
  37.                             .unwrap().len() == 4096);
  38.                 }
  39.  
  40.                 // Compute number of CPU cycles for the operation
  41.                 let elapsed = unsafe { core::arch::x86_64::_rdtsc() - start };
  42.  
  43.                 CYCLES.fetch_add(elapsed as usize, Ordering::SeqCst);
  44.             }));
  45.         }
  46.  
  47.         // Wait for all threads to complete
  48.         for thr in threads {
  49.             thr.join().unwrap();
  50.         }
  51.  
  52.         // Get number of cycles spent by all of the workers
  53.         let cycles = CYCLES.load(Ordering::SeqCst);
  54.  
  55.         print!("With {:4} active read threads: {:10.1} cycles/file read\n",
  56.             num_threads, cycles as f64 / (num_threads * NUM_ACCESSES) as f64);
  57.     }
  58. }
  59.  
  60. fn main() {
  61.     print!("Warning: This is a benchmarking tool, make sure you're using \
  62.            --release!\n");
  63.     benchmark_random_read_scaling();
  64. }
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
 
Top