Skip to content

Commit

Permalink
Fix a bug where cached stacks weren't re-used
Browse files Browse the repository at this point in the history
The condition was the wrong direction and it also didn't take equality into
account. Tests were added for both cases.

For the small benchmark of `task::try(proc() {}).unwrap()`, this takes the
iteration time on OSX from 15119 ns/iter to 6179 ns/iter (timed with
RUST_THREADS=1)

cc rust-lang#11389
  • Loading branch information
alexcrichton committed Feb 14, 2014
1 parent 89b1686 commit d5e0622
Showing 1 changed file with 32 additions and 2 deletions.
34 changes: 32 additions & 2 deletions src/libgreen/stack.rs
Original file line number Diff line number Diff line change
Expand Up @@ -138,9 +138,9 @@ impl StackPool {

pub fn take_stack(&mut self, min_size: uint) -> Stack {
// Ideally this would be a binary search
match self.stacks.iter().position(|s| s.min_size < min_size) {
match self.stacks.iter().position(|s| min_size <= s.min_size) {
Some(idx) => self.stacks.swap_remove(idx),
None => Stack::new(min_size)
None => Stack::new(min_size)
}
}

Expand All @@ -156,3 +156,33 @@ extern {
end: *libc::uintptr_t) -> libc::c_uint;
fn rust_valgrind_stack_deregister(id: libc::c_uint);
}

#[cfg(test)]
mod tests {
use super::StackPool;

#[test]
fn stack_pool_caches() {
let mut p = StackPool::new();
let s = p.take_stack(10);
p.give_stack(s);
let s = p.take_stack(4);
assert_eq!(s.min_size, 10);
p.give_stack(s);
let s = p.take_stack(14);
assert_eq!(s.min_size, 14);
p.give_stack(s);
}

#[test]
fn stack_pool_caches_exact() {
let mut p = StackPool::new();
let mut s = p.take_stack(10);
s.valgrind_id = 100;
p.give_stack(s);

let s = p.take_stack(10);
assert_eq!(s.min_size, 10);
assert_eq!(s.valgrind_id, 100);
}
}

0 comments on commit d5e0622

Please sign in to comment.