diff options
| author | Jonathan S <gereeter@gmail.com> | 2014-06-06 15:24:14 -0500 |
|---|---|---|
| committer | Jonathan S <gereeter@gmail.com> | 2014-06-06 15:24:14 -0500 |
| commit | f2f1991c81825b542f77b4e4f2ac65d24a063a9c (patch) | |
| tree | 71c3fe1cdf55293ee29d6840ab786fcb9d564c5d /src/libsync | |
| parent | 566b7b93c6ca2c034f110fa670040de1a09195e4 (diff) | |
| download | rust-f2f1991c81825b542f77b4e4f2ac65d24a063a9c.tar.gz rust-f2f1991c81825b542f77b4e4f2ac65d24a063a9c.zip | |
Make sync::raw::Sem use Unsafe to manage mutability instead of transmuting an unsafe pointer
Diffstat (limited to 'src/libsync')
| -rw-r--r-- | src/libsync/raw.rs | 30 |
1 files changed, 8 insertions, 22 deletions
diff --git a/src/libsync/raw.rs b/src/libsync/raw.rs index aae790f887a..8fd10cdfa8b 100644 --- a/src/libsync/raw.rs +++ b/src/libsync/raw.rs @@ -18,6 +18,7 @@ use std::kinds::marker; use std::mem; use std::sync::atomics; +use std::ty::Unsafe; use std::finally::Finally; use mutex; @@ -85,11 +86,8 @@ struct Sem<Q> { // n.b, we need Sem to be `Share`, but the WaitQueue type is not send/share // (for good reason). We have an internal invariant on this semaphore, // however, that the queue is never accessed outside of a locked - // context. For this reason, we shove these behind a pointer which will - // be inferred to be `Share`. - // - // FIXME: this requires an extra allocation, which is bad. - inner: *() + // context. + inner: Unsafe<SemInner<Q>> } struct SemInner<Q> { @@ -107,22 +105,20 @@ struct SemGuard<'a, Q> { impl<Q: Send> Sem<Q> { fn new(count: int, q: Q) -> Sem<Q> { - let inner = unsafe { - mem::transmute(box SemInner { + Sem { + lock: mutex::Mutex::new(), + inner: Unsafe::new(SemInner { waiters: WaitQueue::new(), count: count, blocked: q, }) - }; - Sem { - lock: mutex::Mutex::new(), - inner: inner, } } unsafe fn with(&self, f: |&mut SemInner<Q>|) { let _g = self.lock.lock(); - f(&mut *(self.inner as *mut SemInner<Q>)) + // This &mut is safe because, due to the lock, we are the only one who can touch the data + f(&mut *self.inner.get()) } pub fn acquire(&self) { @@ -164,16 +160,6 @@ impl<Q: Send> Sem<Q> { } #[unsafe_destructor] -impl<Q: Send> Drop for Sem<Q> { - fn drop(&mut self) { - let _waiters: Box<SemInner<Q>> = unsafe { - mem::transmute(self.inner) - }; - self.inner = 0 as *(); - } -} - -#[unsafe_destructor] impl<'a, Q: Send> Drop for SemGuard<'a, Q> { fn drop(&mut self) { self.sem.release(); |
