Make Send and Sync traits unsafe
This commit is contained in:
parent
686ce664da
commit
f436f9ca29
32 changed files with 73 additions and 55 deletions
|
@ -129,9 +129,9 @@ pub struct Weak<T> {
|
||||||
_ptr: *mut ArcInner<T>,
|
_ptr: *mut ArcInner<T>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: Sync + Send> Send for Arc<T> { }
|
unsafe impl<T: Sync + Send> Send for Arc<T> { }
|
||||||
|
|
||||||
impl<T: Sync + Send> Sync for Arc<T> { }
|
unsafe impl<T: Sync + Send> Sync for Arc<T> { }
|
||||||
|
|
||||||
struct ArcInner<T> {
|
struct ArcInner<T> {
|
||||||
strong: atomic::AtomicUint,
|
strong: atomic::AtomicUint,
|
||||||
|
|
|
@ -577,6 +577,6 @@ impl<T> RacyCell<T> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T:Send> Send for RacyCell<T> { }
|
unsafe impl<T:Send> Send for RacyCell<T> { }
|
||||||
|
|
||||||
impl<T> Sync for RacyCell<T> { } // Oh dear
|
unsafe impl<T> Sync for RacyCell<T> { } // Oh dear
|
||||||
|
|
|
@ -19,7 +19,7 @@
|
||||||
|
|
||||||
/// Types able to be transferred across task boundaries.
|
/// Types able to be transferred across task boundaries.
|
||||||
#[lang="send"]
|
#[lang="send"]
|
||||||
pub trait Send for Sized? : 'static {
|
pub unsafe trait Send for Sized? : 'static {
|
||||||
// empty.
|
// empty.
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -81,7 +81,7 @@ pub trait Copy for Sized? {
|
||||||
/// reference; not doing this is undefined behaviour (for example,
|
/// reference; not doing this is undefined behaviour (for example,
|
||||||
/// `transmute`-ing from `&T` to `&mut T` is illegal).
|
/// `transmute`-ing from `&T` to `&mut T` is illegal).
|
||||||
#[lang="sync"]
|
#[lang="sync"]
|
||||||
pub trait Sync for Sized? {
|
pub unsafe trait Sync for Sized? {
|
||||||
// Empty
|
// Empty
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -515,13 +515,13 @@ pub struct UniquePtr<T>(pub *mut T);
|
||||||
/// reference is unaliased. Note that this aliasing invariant is
|
/// reference is unaliased. Note that this aliasing invariant is
|
||||||
/// unenforced by the type system; the abstraction using the
|
/// unenforced by the type system; the abstraction using the
|
||||||
/// `UniquePtr` must enforce it.
|
/// `UniquePtr` must enforce it.
|
||||||
impl<T:Send> Send for UniquePtr<T> { }
|
unsafe impl<T:Send> Send for UniquePtr<T> { }
|
||||||
|
|
||||||
/// `UniquePtr` pointers are `Sync` if `T` is `Sync` because the data they
|
/// `UniquePtr` pointers are `Sync` if `T` is `Sync` because the data they
|
||||||
/// reference is unaliased. Note that this aliasing invariant is
|
/// reference is unaliased. Note that this aliasing invariant is
|
||||||
/// unenforced by the type system; the abstraction using the
|
/// unenforced by the type system; the abstraction using the
|
||||||
/// `UniquePtr` must enforce it.
|
/// `UniquePtr` must enforce it.
|
||||||
impl<T:Sync> Sync for UniquePtr<T> { }
|
unsafe impl<T:Sync> Sync for UniquePtr<T> { }
|
||||||
|
|
||||||
impl<T> UniquePtr<T> {
|
impl<T> UniquePtr<T> {
|
||||||
/// Returns a null UniquePtr.
|
/// Returns a null UniquePtr.
|
||||||
|
|
|
@ -281,7 +281,7 @@ struct ModuleConfig {
|
||||||
time_passes: bool,
|
time_passes: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Send for ModuleConfig { }
|
unsafe impl Send for ModuleConfig { }
|
||||||
|
|
||||||
impl ModuleConfig {
|
impl ModuleConfig {
|
||||||
fn new(tm: TargetMachineRef, passes: Vec<String>) -> ModuleConfig {
|
fn new(tm: TargetMachineRef, passes: Vec<String>) -> ModuleConfig {
|
||||||
|
|
|
@ -60,8 +60,8 @@ pub struct ModuleTranslation {
|
||||||
pub llmod: ModuleRef,
|
pub llmod: ModuleRef,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Send for ModuleTranslation { }
|
unsafe impl Send for ModuleTranslation { }
|
||||||
impl Sync for ModuleTranslation { }
|
unsafe impl Sync for ModuleTranslation { }
|
||||||
|
|
||||||
pub struct CrateTranslation {
|
pub struct CrateTranslation {
|
||||||
pub modules: Vec<ModuleTranslation>,
|
pub modules: Vec<ModuleTranslation>,
|
||||||
|
|
|
@ -89,8 +89,8 @@ pub struct CString {
|
||||||
owns_buffer_: bool,
|
owns_buffer_: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Send for CString { }
|
unsafe impl Send for CString { }
|
||||||
impl Sync for CString { }
|
unsafe impl Sync for CString { }
|
||||||
|
|
||||||
impl Clone for CString {
|
impl Clone for CString {
|
||||||
/// Clone this CString into a new, uniquely owned CString. For safety
|
/// Clone this CString into a new, uniquely owned CString. For safety
|
||||||
|
|
|
@ -13,16 +13,19 @@
|
||||||
use thread::Thread;
|
use thread::Thread;
|
||||||
use sync::atomic::{AtomicBool, INIT_ATOMIC_BOOL, Ordering};
|
use sync::atomic::{AtomicBool, INIT_ATOMIC_BOOL, Ordering};
|
||||||
use sync::Arc;
|
use sync::Arc;
|
||||||
|
use kinds::{Sync, Send};
|
||||||
use kinds::marker::{NoSend, NoSync};
|
use kinds::marker::{NoSend, NoSync};
|
||||||
use mem;
|
use mem;
|
||||||
use clone::Clone;
|
use clone::Clone;
|
||||||
|
|
||||||
#[deriving(Send, Sync)]
|
|
||||||
struct Inner {
|
struct Inner {
|
||||||
thread: Thread,
|
thread: Thread,
|
||||||
woken: AtomicBool,
|
woken: AtomicBool,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Send for Inner {}
|
||||||
|
unsafe impl Sync for Inner {}
|
||||||
|
|
||||||
#[deriving(Clone)]
|
#[deriving(Clone)]
|
||||||
pub struct SignalToken {
|
pub struct SignalToken {
|
||||||
inner: Arc<Inner>,
|
inner: Arc<Inner>,
|
||||||
|
|
|
@ -363,7 +363,7 @@ pub struct Receiver<T> {
|
||||||
|
|
||||||
// The receiver port can be sent from place to place, so long as it
|
// The receiver port can be sent from place to place, so long as it
|
||||||
// is not used to receive non-sendable things.
|
// is not used to receive non-sendable things.
|
||||||
impl<T:Send> Send for Receiver<T> { }
|
unsafe impl<T:Send> Send for Receiver<T> { }
|
||||||
|
|
||||||
/// An iterator over messages on a receiver, this iterator will block
|
/// An iterator over messages on a receiver, this iterator will block
|
||||||
/// whenever `next` is called, waiting for a new message, and `None` will be
|
/// whenever `next` is called, waiting for a new message, and `None` will be
|
||||||
|
@ -382,7 +382,7 @@ pub struct Sender<T> {
|
||||||
|
|
||||||
// The send port can be sent from place to place, so long as it
|
// The send port can be sent from place to place, so long as it
|
||||||
// is not used to send non-sendable things.
|
// is not used to send non-sendable things.
|
||||||
impl<T:Send> Send for Sender<T> { }
|
unsafe impl<T:Send> Send for Sender<T> { }
|
||||||
|
|
||||||
/// The sending-half of Rust's synchronous channel type. This half can only be
|
/// The sending-half of Rust's synchronous channel type. This half can only be
|
||||||
/// owned by one task, but it can be cloned to send to other tasks.
|
/// owned by one task, but it can be cloned to send to other tasks.
|
||||||
|
|
|
@ -76,8 +76,8 @@ pub struct Queue<T> {
|
||||||
tail: UnsafeCell<*mut Node<T>>,
|
tail: UnsafeCell<*mut Node<T>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T:Send> Send for Queue<T> { }
|
unsafe impl<T:Send> Send for Queue<T> { }
|
||||||
impl<T:Send> Sync for Queue<T> { }
|
unsafe impl<T:Send> Sync for Queue<T> { }
|
||||||
|
|
||||||
impl<T> Node<T> {
|
impl<T> Node<T> {
|
||||||
unsafe fn new(v: Option<T>) -> *mut Node<T> {
|
unsafe fn new(v: Option<T>) -> *mut Node<T> {
|
||||||
|
|
|
@ -73,9 +73,9 @@ pub struct Queue<T> {
|
||||||
cache_subtractions: AtomicUint,
|
cache_subtractions: AtomicUint,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: Send> Send for Queue<T> { }
|
unsafe impl<T: Send> Send for Queue<T> { }
|
||||||
|
|
||||||
impl<T: Send> Sync for Queue<T> { }
|
unsafe impl<T: Send> Sync for Queue<T> { }
|
||||||
|
|
||||||
impl<T: Send> Node<T> {
|
impl<T: Send> Node<T> {
|
||||||
fn new() -> *mut Node<T> {
|
fn new() -> *mut Node<T> {
|
||||||
|
|
|
@ -53,11 +53,10 @@ pub struct Packet<T> {
|
||||||
lock: Mutex<State<T>>,
|
lock: Mutex<State<T>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T:Send> Send for Packet<T> { }
|
unsafe impl<T:Send> Send for Packet<T> { }
|
||||||
|
|
||||||
impl<T:Send> Sync for Packet<T> { }
|
unsafe impl<T:Send> Sync for Packet<T> { }
|
||||||
|
|
||||||
#[deriving(Send)]
|
|
||||||
struct State<T> {
|
struct State<T> {
|
||||||
disconnected: bool, // Is the channel disconnected yet?
|
disconnected: bool, // Is the channel disconnected yet?
|
||||||
queue: Queue, // queue of senders waiting to send data
|
queue: Queue, // queue of senders waiting to send data
|
||||||
|
@ -74,6 +73,8 @@ struct State<T> {
|
||||||
canceled: Option<&'static mut bool>,
|
canceled: Option<&'static mut bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl<T: Send> Send for State<T> {}
|
||||||
|
|
||||||
/// Possible flavors of threads who can be blocked on this channel.
|
/// Possible flavors of threads who can be blocked on this channel.
|
||||||
enum Blocker {
|
enum Blocker {
|
||||||
BlockedSender(SignalToken),
|
BlockedSender(SignalToken),
|
||||||
|
@ -93,7 +94,7 @@ struct Node {
|
||||||
next: *mut Node,
|
next: *mut Node,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Send for Node {}
|
unsafe impl Send for Node {}
|
||||||
|
|
||||||
/// A simple ring-buffer
|
/// A simple ring-buffer
|
||||||
struct Buffer<T> {
|
struct Buffer<T> {
|
||||||
|
|
|
@ -26,9 +26,9 @@ pub struct Exclusive<T> {
|
||||||
data: UnsafeCell<T>,
|
data: UnsafeCell<T>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T:Send> Send for Exclusive<T> { }
|
unsafe impl<T:Send> Send for Exclusive<T> { }
|
||||||
|
|
||||||
impl<T:Send> Sync for Exclusive<T> { }
|
unsafe impl<T:Send> Sync for Exclusive<T> { }
|
||||||
|
|
||||||
/// An RAII guard returned via `lock`
|
/// An RAII guard returned via `lock`
|
||||||
pub struct ExclusiveGuard<'a, T:'a> {
|
pub struct ExclusiveGuard<'a, T:'a> {
|
||||||
|
|
|
@ -11,7 +11,7 @@
|
||||||
use prelude::*;
|
use prelude::*;
|
||||||
|
|
||||||
use cell::{UnsafeCell, RacyCell};
|
use cell::{UnsafeCell, RacyCell};
|
||||||
use kinds::marker;
|
use kinds::{marker, Sync};
|
||||||
use sync::{poison, AsMutexGuard};
|
use sync::{poison, AsMutexGuard};
|
||||||
use sys_common::mutex as sys;
|
use sys_common::mutex as sys;
|
||||||
|
|
||||||
|
@ -73,9 +73,9 @@ pub struct Mutex<T> {
|
||||||
data: RacyCell<T>,
|
data: RacyCell<T>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T:Send> Send for Mutex<T> { }
|
unsafe impl<T:Send> Send for Mutex<T> { }
|
||||||
|
|
||||||
impl<T:Send> Sync for Mutex<T> { }
|
unsafe impl<T:Send> Sync for Mutex<T> { }
|
||||||
|
|
||||||
/// The static mutex type is provided to allow for static allocation of mutexes.
|
/// The static mutex type is provided to allow for static allocation of mutexes.
|
||||||
///
|
///
|
||||||
|
@ -98,12 +98,13 @@ impl<T:Send> Sync for Mutex<T> { }
|
||||||
/// }
|
/// }
|
||||||
/// // lock is unlocked here.
|
/// // lock is unlocked here.
|
||||||
/// ```
|
/// ```
|
||||||
#[deriving(Sync)]
|
|
||||||
pub struct StaticMutex {
|
pub struct StaticMutex {
|
||||||
lock: sys::Mutex,
|
lock: sys::Mutex,
|
||||||
poison: RacyCell<poison::Flag>,
|
poison: RacyCell<poison::Flag>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for StaticMutex {}
|
||||||
|
|
||||||
/// An RAII implementation of a "scoped lock" of a mutex. When this structure is
|
/// An RAII implementation of a "scoped lock" of a mutex. When this structure is
|
||||||
/// dropped (falls out of scope), the lock will be unlocked.
|
/// dropped (falls out of scope), the lock will be unlocked.
|
||||||
///
|
///
|
||||||
|
|
|
@ -14,6 +14,7 @@
|
||||||
//! example use case would be for initializing an FFI library.
|
//! example use case would be for initializing an FFI library.
|
||||||
|
|
||||||
use int;
|
use int;
|
||||||
|
use kinds::Sync;
|
||||||
use mem::drop;
|
use mem::drop;
|
||||||
use ops::FnOnce;
|
use ops::FnOnce;
|
||||||
use sync::atomic;
|
use sync::atomic;
|
||||||
|
@ -35,13 +36,14 @@ use sync::{StaticMutex, MUTEX_INIT};
|
||||||
/// // run initialization here
|
/// // run initialization here
|
||||||
/// });
|
/// });
|
||||||
/// ```
|
/// ```
|
||||||
#[deriving(Sync)]
|
|
||||||
pub struct Once {
|
pub struct Once {
|
||||||
mutex: StaticMutex,
|
mutex: StaticMutex,
|
||||||
cnt: atomic::AtomicInt,
|
cnt: atomic::AtomicInt,
|
||||||
lock_cnt: atomic::AtomicInt,
|
lock_cnt: atomic::AtomicInt,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for Once {}
|
||||||
|
|
||||||
/// Initialization value for static `Once` values.
|
/// Initialization value for static `Once` values.
|
||||||
pub const ONCE_INIT: Once = Once {
|
pub const ONCE_INIT: Once = Once {
|
||||||
mutex: MUTEX_INIT,
|
mutex: MUTEX_INIT,
|
||||||
|
|
|
@ -59,9 +59,9 @@ pub struct Helper<M> {
|
||||||
pub shutdown: UnsafeCell<bool>,
|
pub shutdown: UnsafeCell<bool>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<M:Send> Send for Helper<M> { }
|
unsafe impl<M:Send> Send for Helper<M> { }
|
||||||
|
|
||||||
impl<M:Send> Sync for Helper<M> { }
|
unsafe impl<M:Send> Sync for Helper<M> { }
|
||||||
|
|
||||||
impl<M: Send> Helper<M> {
|
impl<M: Send> Helper<M> {
|
||||||
/// Lazily boots a helper thread, becoming a no-op if the helper has already
|
/// Lazily boots a helper thread, becoming a no-op if the helper has already
|
||||||
|
|
|
@ -8,6 +8,7 @@
|
||||||
// option. This file may not be copied, modified, or distributed
|
// option. This file may not be copied, modified, or distributed
|
||||||
// except according to those terms.
|
// except according to those terms.
|
||||||
|
|
||||||
|
use kinds::Sync;
|
||||||
use sys::mutex as imp;
|
use sys::mutex as imp;
|
||||||
|
|
||||||
/// An OS-based mutual exclusion lock.
|
/// An OS-based mutual exclusion lock.
|
||||||
|
@ -15,9 +16,10 @@ use sys::mutex as imp;
|
||||||
/// This is the thinnest cross-platform wrapper around OS mutexes. All usage of
|
/// This is the thinnest cross-platform wrapper around OS mutexes. All usage of
|
||||||
/// this mutex is unsafe and it is recommended to instead use the safe wrapper
|
/// this mutex is unsafe and it is recommended to instead use the safe wrapper
|
||||||
/// at the top level of the crate instead of this type.
|
/// at the top level of the crate instead of this type.
|
||||||
#[deriving(Sync)]
|
|
||||||
pub struct Mutex(imp::Mutex);
|
pub struct Mutex(imp::Mutex);
|
||||||
|
|
||||||
|
unsafe impl Sync for Mutex {}
|
||||||
|
|
||||||
/// Constant initializer for statically allocated mutexes.
|
/// Constant initializer for statically allocated mutexes.
|
||||||
pub const MUTEX_INIT: Mutex = Mutex(imp::MUTEX_INIT);
|
pub const MUTEX_INIT: Mutex = Mutex(imp::MUTEX_INIT);
|
||||||
|
|
||||||
|
|
|
@ -162,8 +162,8 @@ mod signal {
|
||||||
sa_restorer: *mut libc::c_void,
|
sa_restorer: *mut libc::c_void,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl ::kinds::Send for sigaction { }
|
unsafe impl ::kinds::Send for sigaction { }
|
||||||
impl ::kinds::Sync for sigaction { }
|
unsafe impl ::kinds::Sync for sigaction { }
|
||||||
|
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
#[cfg(target_word_size = "32")]
|
#[cfg(target_word_size = "32")]
|
||||||
|
|
|
@ -8,11 +8,11 @@
|
||||||
// option. This file may not be copied, modified, or distributed
|
// option. This file may not be copied, modified, or distributed
|
||||||
// except according to those terms.
|
// except according to those terms.
|
||||||
|
|
||||||
|
use kinds::Sync;
|
||||||
use cell::{UnsafeCell, RacyCell};
|
use cell::{UnsafeCell, RacyCell};
|
||||||
use sys::sync as ffi;
|
use sys::sync as ffi;
|
||||||
use sys_common::mutex;
|
use sys_common::mutex;
|
||||||
|
|
||||||
#[deriving(Sync)]
|
|
||||||
pub struct Mutex { inner: RacyCell<ffi::pthread_mutex_t> }
|
pub struct Mutex { inner: RacyCell<ffi::pthread_mutex_t> }
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
|
@ -24,6 +24,8 @@ pub const MUTEX_INIT: Mutex = Mutex {
|
||||||
inner: RacyCell(UnsafeCell { value: ffi::PTHREAD_MUTEX_INITIALIZER }),
|
inner: RacyCell(UnsafeCell { value: ffi::PTHREAD_MUTEX_INITIALIZER }),
|
||||||
};
|
};
|
||||||
|
|
||||||
|
unsafe impl Sync for Mutex {}
|
||||||
|
|
||||||
impl Mutex {
|
impl Mutex {
|
||||||
#[inline]
|
#[inline]
|
||||||
pub unsafe fn new() -> Mutex {
|
pub unsafe fn new() -> Mutex {
|
||||||
|
|
|
@ -210,12 +210,13 @@ impl Clone for UnixStream {
|
||||||
// Unix Listener
|
// Unix Listener
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#[deriving(Sync)]
|
|
||||||
pub struct UnixListener {
|
pub struct UnixListener {
|
||||||
inner: Inner,
|
inner: Inner,
|
||||||
path: CString,
|
path: CString,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for UnixListener {}
|
||||||
|
|
||||||
impl UnixListener {
|
impl UnixListener {
|
||||||
pub fn bind(addr: &CString) -> IoResult<UnixListener> {
|
pub fn bind(addr: &CString) -> IoResult<UnixListener> {
|
||||||
bind(addr, libc::SOCK_STREAM).map(|fd| {
|
bind(addr, libc::SOCK_STREAM).map(|fd| {
|
||||||
|
@ -253,7 +254,6 @@ pub struct UnixAcceptor {
|
||||||
deadline: u64,
|
deadline: u64,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[deriving(Sync)]
|
|
||||||
struct AcceptorInner {
|
struct AcceptorInner {
|
||||||
listener: UnixListener,
|
listener: UnixListener,
|
||||||
reader: FileDesc,
|
reader: FileDesc,
|
||||||
|
@ -261,6 +261,8 @@ struct AcceptorInner {
|
||||||
closed: atomic::AtomicBool,
|
closed: atomic::AtomicBool,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for AcceptorInner {}
|
||||||
|
|
||||||
impl UnixAcceptor {
|
impl UnixAcceptor {
|
||||||
pub fn fd(&self) -> fd_t { self.inner.listener.fd() }
|
pub fn fd(&self) -> fd_t { self.inner.listener.fd() }
|
||||||
|
|
||||||
|
|
|
@ -29,11 +29,12 @@ pub use sys_common::net::TcpStream;
|
||||||
// TCP listeners
|
// TCP listeners
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
#[deriving(Sync)]
|
|
||||||
pub struct TcpListener {
|
pub struct TcpListener {
|
||||||
pub inner: FileDesc,
|
pub inner: FileDesc,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for TcpListener {}
|
||||||
|
|
||||||
impl TcpListener {
|
impl TcpListener {
|
||||||
pub fn bind(addr: ip::SocketAddr) -> IoResult<TcpListener> {
|
pub fn bind(addr: ip::SocketAddr) -> IoResult<TcpListener> {
|
||||||
let fd = try!(net::socket(addr, libc::SOCK_STREAM));
|
let fd = try!(net::socket(addr, libc::SOCK_STREAM));
|
||||||
|
@ -90,7 +91,6 @@ pub struct TcpAcceptor {
|
||||||
deadline: u64,
|
deadline: u64,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[deriving(Sync)]
|
|
||||||
struct AcceptorInner {
|
struct AcceptorInner {
|
||||||
listener: TcpListener,
|
listener: TcpListener,
|
||||||
reader: FileDesc,
|
reader: FileDesc,
|
||||||
|
@ -98,6 +98,8 @@ struct AcceptorInner {
|
||||||
closed: atomic::AtomicBool,
|
closed: atomic::AtomicBool,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for AcceptorInner {}
|
||||||
|
|
||||||
impl TcpAcceptor {
|
impl TcpAcceptor {
|
||||||
pub fn fd(&self) -> sock_t { self.inner.listener.fd() }
|
pub fn fd(&self) -> sock_t { self.inner.listener.fd() }
|
||||||
|
|
||||||
|
|
|
@ -283,19 +283,22 @@ impl Builder {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
#[deriving(Sync)]
|
|
||||||
struct Inner {
|
struct Inner {
|
||||||
name: Option<String>,
|
name: Option<String>,
|
||||||
lock: Mutex<bool>, // true when there is a buffered unpark
|
lock: Mutex<bool>, // true when there is a buffered unpark
|
||||||
cvar: Condvar,
|
cvar: Condvar,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[deriving(Clone, Sync)]
|
unsafe impl Sync for Inner {}
|
||||||
|
|
||||||
|
#[deriving(Clone)]
|
||||||
/// A handle to a thread.
|
/// A handle to a thread.
|
||||||
pub struct Thread {
|
pub struct Thread {
|
||||||
inner: Arc<Inner>,
|
inner: Arc<Inner>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsafe impl Sync for Thread {}
|
||||||
|
|
||||||
impl Thread {
|
impl Thread {
|
||||||
// Used only internally to construct a thread object without spawning
|
// Used only internally to construct a thread object without spawning
|
||||||
fn new(name: Option<String>) -> Thread {
|
fn new(name: Option<String>) -> Thread {
|
||||||
|
|
|
@ -280,7 +280,7 @@ mod imp {
|
||||||
pub dtor_running: UnsafeCell<bool>, // should be Cell
|
pub dtor_running: UnsafeCell<bool>, // should be Cell
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T> ::kinds::Sync for Key<T> { }
|
unsafe impl<T> ::kinds::Sync for Key<T> { }
|
||||||
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
impl<T> Key<T> {
|
impl<T> Key<T> {
|
||||||
|
@ -412,7 +412,7 @@ mod imp {
|
||||||
pub os: OsStaticKey,
|
pub os: OsStaticKey,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T> ::kinds::Sync for Key<T> { }
|
unsafe impl<T> ::kinds::Sync for Key<T> { }
|
||||||
|
|
||||||
struct Value<T: 'static> {
|
struct Value<T: 'static> {
|
||||||
key: &'static Key<T>,
|
key: &'static Key<T>,
|
||||||
|
|
|
@ -202,7 +202,7 @@ mod imp {
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
pub struct KeyInner<T> { pub inner: UnsafeCell<*mut T> }
|
pub struct KeyInner<T> { pub inner: UnsafeCell<*mut T> }
|
||||||
|
|
||||||
#[cfg(not(stage0))] impl<T> ::kinds::Sync for KeyInner<T> { }
|
unsafe impl<T> ::kinds::Sync for KeyInner<T> { }
|
||||||
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
impl<T> KeyInner<T> {
|
impl<T> KeyInner<T> {
|
||||||
|
@ -224,7 +224,7 @@ mod imp {
|
||||||
pub marker: marker::InvariantType<T>,
|
pub marker: marker::InvariantType<T>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(stage0))] impl<T> ::kinds::Sync for KeyInner<T> { }
|
unsafe impl<T> ::kinds::Sync for KeyInner<T> { }
|
||||||
|
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
impl<T> KeyInner<T> {
|
impl<T> KeyInner<T> {
|
||||||
|
|
|
@ -976,7 +976,7 @@ enum TestEvent {
|
||||||
|
|
||||||
pub type MonitorMsg = (TestDesc, TestResult, Vec<u8> );
|
pub type MonitorMsg = (TestDesc, TestResult, Vec<u8> );
|
||||||
|
|
||||||
impl Send for MonitorMsg {}
|
unsafe impl Send for MonitorMsg {}
|
||||||
|
|
||||||
fn run_tests<F>(opts: &TestOpts,
|
fn run_tests<F>(opts: &TestOpts,
|
||||||
tests: Vec<TestDescAndFn> ,
|
tests: Vec<TestDescAndFn> ,
|
||||||
|
|
|
@ -18,7 +18,7 @@ struct Foo {
|
||||||
b: *const ()
|
b: *const ()
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Sync for Foo {}
|
unsafe impl Sync for Foo {}
|
||||||
|
|
||||||
fn foo<T>(a: T) -> T {
|
fn foo<T>(a: T) -> T {
|
||||||
a
|
a
|
||||||
|
|
|
@ -14,7 +14,7 @@ struct TestStruct {
|
||||||
x: *const u8
|
x: *const u8
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Sync for TestStruct {}
|
unsafe impl Sync for TestStruct {}
|
||||||
|
|
||||||
static a: TestStruct = TestStruct{x: 0 as *const u8};
|
static a: TestStruct = TestStruct{x: 0 as *const u8};
|
||||||
|
|
||||||
|
|
|
@ -14,7 +14,7 @@ struct TestStruct {
|
||||||
x: *const libc::c_void
|
x: *const libc::c_void
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Sync for TestStruct {}
|
unsafe impl Sync for TestStruct {}
|
||||||
|
|
||||||
extern fn foo() {}
|
extern fn foo() {}
|
||||||
const x: extern "C" fn() = foo;
|
const x: extern "C" fn() = foo;
|
||||||
|
|
|
@ -12,7 +12,7 @@ struct TestStruct {
|
||||||
x: *const [int; 2]
|
x: *const [int; 2]
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Sync for TestStruct {}
|
unsafe impl Sync for TestStruct {}
|
||||||
|
|
||||||
static TEST_VALUE : TestStruct = TestStruct{x: 0x1234 as *const [int; 2]};
|
static TEST_VALUE : TestStruct = TestStruct{x: 0x1234 as *const [int; 2]};
|
||||||
|
|
||||||
|
|
|
@ -36,7 +36,7 @@ struct Wrap<T> {
|
||||||
value: T
|
value: T
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T: Send> Sync for Wrap<T> {}
|
unsafe impl<T: Send> Sync for Wrap<T> {}
|
||||||
|
|
||||||
static UNSAFE: RacyCell<int> = RacyCell(UnsafeCell{value: 1});
|
static UNSAFE: RacyCell<int> = RacyCell(UnsafeCell{value: 1});
|
||||||
static WRAPPED_UNSAFE: Wrap<&'static RacyCell<int>> = Wrap { value: &UNSAFE };
|
static WRAPPED_UNSAFE: Wrap<&'static RacyCell<int>> = Wrap { value: &UNSAFE };
|
||||||
|
|
|
@ -46,7 +46,7 @@ pub mod pipes {
|
||||||
payload: Option<T>
|
payload: Option<T>
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<T:Send> Send for packet<T> {}
|
unsafe impl<T:Send> Send for packet<T> {}
|
||||||
|
|
||||||
pub fn packet<T:Send>() -> *const packet<T> {
|
pub fn packet<T:Send>() -> *const packet<T> {
|
||||||
unsafe {
|
unsafe {
|
||||||
|
|
|
@ -15,7 +15,7 @@ struct TestStruct {
|
||||||
x: *const int
|
x: *const int
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Sync for TestStruct {}
|
unsafe impl Sync for TestStruct {}
|
||||||
|
|
||||||
static CONSTEXPR: TestStruct = TestStruct{x: &413 as *const _};
|
static CONSTEXPR: TestStruct = TestStruct{x: &413 as *const _};
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue