Skip to content

Commit 86be130

Browse files
committed
---
yaml --- r: 114357 b: refs/heads/master c: 7db02e2 h: refs/heads/master i: 114355: a432924 v: v3
1 parent 6623def commit 86be130

File tree

2 files changed

+28
-24
lines changed

2 files changed

+28
-24
lines changed

[refs]

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
---
2-
refs/heads/master: efbd3724c012d68afd428beaa22f0d5aabff007d
2+
refs/heads/master: 7db02e20f2140530a9402f7d7452b10cac6fdf7b
33
refs/heads/snap-stage1: e33de59e47c5076a89eadeb38f4934f58a3618a6
44
refs/heads/snap-stage3: ec0258a381b88b5574e3f8ce72ae553ac3a574b7
55
refs/heads/try: 7c6c492fb2af9a85f21ff952942df3523b22fd17

trunk/src/libstd/sync/mpmc_bounded_queue.rs

Lines changed: 27 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -29,13 +29,15 @@
2929

3030
// http://www.1024cores.net/home/lock-free-algorithms/queues/bounded-mpmc-queue
3131

32+
use alloc::arc::Arc;
33+
3234
use clone::Clone;
3335
use kinds::Send;
3436
use num::next_power_of_two;
3537
use option::{Option, Some, None};
36-
use sync::arc::UnsafeArc;
3738
use sync::atomics::{AtomicUint,Relaxed,Release,Acquire};
3839
use vec::Vec;
40+
use ty::Unsafe;
3941

4042
struct Node<T> {
4143
sequence: AtomicUint,
@@ -44,7 +46,7 @@ struct Node<T> {
4446

4547
struct State<T> {
4648
pad0: [u8, ..64],
47-
buffer: Vec<Node<T>>,
49+
buffer: Vec<Unsafe<Node<T>>>,
4850
mask: uint,
4951
pad1: [u8, ..64],
5052
enqueue_pos: AtomicUint,
@@ -54,7 +56,7 @@ struct State<T> {
5456
}
5557

5658
pub struct Queue<T> {
57-
state: UnsafeArc<State<T>>,
59+
state: Arc<State<T>>,
5860
}
5961

6062
impl<T: Send> State<T> {
@@ -70,7 +72,7 @@ impl<T: Send> State<T> {
7072
capacity
7173
};
7274
let buffer = Vec::from_fn(capacity, |i| {
73-
Node { sequence:AtomicUint::new(i), value: None }
75+
Unsafe::new(Node { sequence:AtomicUint::new(i), value: None })
7476
});
7577
State{
7678
pad0: [0, ..64],
@@ -84,19 +86,21 @@ impl<T: Send> State<T> {
8486
}
8587
}
8688

87-
fn push(&mut self, value: T) -> bool {
89+
fn push(&self, value: T) -> bool {
8890
let mask = self.mask;
8991
let mut pos = self.enqueue_pos.load(Relaxed);
9092
loop {
91-
let node = self.buffer.get_mut(pos & mask);
92-
let seq = node.sequence.load(Acquire);
93+
let node = self.buffer.get(pos & mask);
94+
let seq = unsafe { (*node.get()).sequence.load(Acquire) };
9395
let diff: int = seq as int - pos as int;
9496

9597
if diff == 0 {
9698
let enqueue_pos = self.enqueue_pos.compare_and_swap(pos, pos+1, Relaxed);
9799
if enqueue_pos == pos {
98-
node.value = Some(value);
99-
node.sequence.store(pos+1, Release);
100+
unsafe {
101+
(*node.get()).value = Some(value);
102+
(*node.get()).sequence.store(pos+1, Release);
103+
}
100104
break
101105
} else {
102106
pos = enqueue_pos;
@@ -110,19 +114,21 @@ impl<T: Send> State<T> {
110114
true
111115
}
112116

113-
fn pop(&mut self) -> Option<T> {
117+
fn pop(&self) -> Option<T> {
114118
let mask = self.mask;
115119
let mut pos = self.dequeue_pos.load(Relaxed);
116120
loop {
117-
let node = self.buffer.get_mut(pos & mask);
118-
let seq = node.sequence.load(Acquire);
121+
let node = self.buffer.get(pos & mask);
122+
let seq = unsafe { (*node.get()).sequence.load(Acquire) };
119123
let diff: int = seq as int - (pos + 1) as int;
120124
if diff == 0 {
121125
let dequeue_pos = self.dequeue_pos.compare_and_swap(pos, pos+1, Relaxed);
122126
if dequeue_pos == pos {
123-
let value = node.value.take();
124-
node.sequence.store(pos + mask + 1, Release);
125-
return value
127+
unsafe {
128+
let value = (*node.get()).value.take();
129+
(*node.get()).sequence.store(pos + mask + 1, Release);
130+
return value
131+
}
126132
} else {
127133
pos = dequeue_pos;
128134
}
@@ -138,24 +144,22 @@ impl<T: Send> State<T> {
138144
impl<T: Send> Queue<T> {
139145
pub fn with_capacity(capacity: uint) -> Queue<T> {
140146
Queue{
141-
state: UnsafeArc::new(State::with_capacity(capacity))
147+
state: Arc::new(State::with_capacity(capacity))
142148
}
143149
}
144150

145-
pub fn push(&mut self, value: T) -> bool {
146-
unsafe { (*self.state.get()).push(value) }
151+
pub fn push(&self, value: T) -> bool {
152+
self.state.push(value)
147153
}
148154

149-
pub fn pop(&mut self) -> Option<T> {
150-
unsafe { (*self.state.get()).pop() }
155+
pub fn pop(&self) -> Option<T> {
156+
self.state.pop()
151157
}
152158
}
153159

154160
impl<T: Send> Clone for Queue<T> {
155161
fn clone(&self) -> Queue<T> {
156-
Queue {
157-
state: self.state.clone()
158-
}
162+
Queue { state: self.state.clone() }
159163
}
160164
}
161165

0 commit comments

Comments
 (0)