Created
July 16, 2015 23:51
-
-
Save MrAlert/f4317ec44768284670bf to your computer and use it in GitHub Desktop.
Rust mutex benchmark
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Based on http://preshing.com/20111118/locks-arent-slow-lock-contention-is/ | |
#![feature(const_fn, rand, test)] | |
extern crate rand; | |
extern crate test; | |
use rand::{ChaChaRng, Rng}; | |
use rand::distributions::{Exp, IndependentSample}; | |
use std::cmp::min; | |
use std::sync::{Arc, Mutex}; | |
use std::thread; | |
use test::Bencher; | |
fn mutex_bench(threads: u32, cycle_units: f64, duty_cycle: f64, total_units: u64) { | |
let thread_units = total_units / threads as u64; | |
let unlocked_units = cycle_units * (1.0 - duty_cycle); | |
let locked_units = cycle_units * duty_cycle; | |
let mutex: Arc<Mutex<u64>> = Arc::new(Mutex::new(0)); | |
let unlocked_dist = Exp::new(1.0 / unlocked_units); | |
let locked_dist = Exp::new(1.0 / locked_units); | |
let mut joins = Vec::with_capacity(threads as usize); | |
for i in 0..threads { | |
let mutex = mutex.clone(); | |
let join = thread::spawn(move || { | |
let mut rng = ChaChaRng::new_unseeded(); | |
rng.set_counter(0, i as u64); | |
let mut units_left = thread_units; | |
while units_left > 0 { | |
let units1 = min(unlocked_dist.ind_sample(&mut rng).round() as u64, units_left); | |
for _ in 0..units1 { | |
let _: u32 = rng.gen(); | |
} | |
units_left -= units1; | |
let mut l = mutex.lock().unwrap(); | |
let units2 = min(locked_dist.ind_sample(&mut rng).round() as u64, units_left); | |
for _ in 0..units2 { | |
let _: u32 = rng.gen(); | |
} | |
units_left -= units2; | |
*l += units1 + units2; | |
drop(l); | |
} | |
}); | |
joins.push(join); | |
} | |
for join in joins { | |
join.join().unwrap(); | |
} | |
assert_eq!(*mutex.lock().unwrap(), thread_units * threads as u64); | |
} | |
fn main() {} | |
macro_rules! benchtest {($nm:ident, $th:expr, $cu:expr, $dc:expr, $tu:expr) => ( | |
#[bench] | |
fn $nm(b: &mut Bencher) { | |
b.iter(|| mutex_bench($th, $cu, $dc, $tu)) | |
} | |
)} | |
benchtest!{mutex_1t_1c_25d, 1, 1.0, 0.25, 1000} | |
benchtest!{mutex_2t_1c_25d, 2, 1.0, 0.25, 1000} | |
benchtest!{mutex_3t_1c_25d, 3, 1.0, 0.25, 1000} | |
benchtest!{mutex_4t_1c_25d, 4, 1.0, 0.25, 1000} | |
benchtest!{mutex_1t_10c_25d, 1, 10.0, 0.25, 1000} | |
benchtest!{mutex_2t_10c_25d, 2, 10.0, 0.25, 1000} | |
benchtest!{mutex_3t_10c_25d, 3, 10.0, 0.25, 1000} | |
benchtest!{mutex_4t_10c_25d, 4, 10.0, 0.25, 1000} | |
benchtest!{mutex_1t_100c_25d, 1, 100.0, 0.25, 1000} | |
benchtest!{mutex_2t_100c_25d, 2, 100.0, 0.25, 1000} | |
benchtest!{mutex_3t_100c_25d, 3, 100.0, 0.25, 1000} | |
benchtest!{mutex_4t_100c_25d, 4, 100.0, 0.25, 1000} | |
benchtest!{mutex_1t_1c_50d, 1, 1.0, 0.50, 1000} | |
benchtest!{mutex_2t_1c_50d, 2, 1.0, 0.50, 1000} | |
benchtest!{mutex_3t_1c_50d, 3, 1.0, 0.50, 1000} | |
benchtest!{mutex_4t_1c_50d, 4, 1.0, 0.50, 1000} | |
benchtest!{mutex_1t_10c_50d, 1, 10.0, 0.50, 1000} | |
benchtest!{mutex_2t_10c_50d, 2, 10.0, 0.50, 1000} | |
benchtest!{mutex_3t_10c_50d, 3, 10.0, 0.50, 1000} | |
benchtest!{mutex_4t_10c_50d, 4, 10.0, 0.50, 1000} | |
benchtest!{mutex_1t_100c_50d, 1, 100.0, 0.50, 1000} | |
benchtest!{mutex_2t_100c_50d, 2, 100.0, 0.50, 1000} | |
benchtest!{mutex_3t_100c_50d, 3, 100.0, 0.50, 1000} | |
benchtest!{mutex_4t_100c_50d, 4, 100.0, 0.50, 1000} | |
benchtest!{mutex_1t_1c_75d, 1, 1.0, 0.75, 1000} | |
benchtest!{mutex_2t_1c_75d, 2, 1.0, 0.75, 1000} | |
benchtest!{mutex_3t_1c_75d, 3, 1.0, 0.75, 1000} | |
benchtest!{mutex_4t_1c_75d, 4, 1.0, 0.75, 1000} | |
benchtest!{mutex_1t_10c_75d, 1, 10.0, 0.75, 1000} | |
benchtest!{mutex_2t_10c_75d, 2, 10.0, 0.75, 1000} | |
benchtest!{mutex_3t_10c_75d, 3, 10.0, 0.75, 1000} | |
benchtest!{mutex_4t_10c_75d, 4, 10.0, 0.75, 1000} | |
benchtest!{mutex_1t_100c_75d, 1, 100.0, 0.75, 1000} | |
benchtest!{mutex_2t_100c_75d, 2, 100.0, 0.75, 1000} | |
benchtest!{mutex_3t_100c_75d, 3, 100.0, 0.75, 1000} | |
benchtest!{mutex_4t_100c_75d, 4, 100.0, 0.75, 1000} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment