介紹
本系列錄制的視訊主要放在B站上Rust死靈書學習視訊
Rust 死靈書相關的源碼資料在https://github.com/anonymousGiga/Rustonomicon-Source
Send和Sync
當同一塊記憶體有多個别名,同時還可以改變記憶體的值的時候,它們就不是線程安全的。
Rust中根據Send和Sync trait擷取相關的資訊:
1、如果一個類型可以安全地傳遞給另一個線程,那麼這個類型是實作了Send這個trait了的;
2、如果一個類型可以安全地被多個線程共享,那麼這個類型就是Sync的。
Send和Sync是Rust并發機制的基礎,但是它們是非安全的trait。Send和Sync是标志trait(即沒有任何關聯方法),類型要實作它們其實就是滿足它們需要的内部特征。不正确的實作Send和Sync會導緻未定義行為。
Send和Sync是自動推到的trait,規則:
1、如果一個類型完全由Send或者Sync組成,那麼這個類型本身也是Send或者Sync的;
2、幾乎所有的基本類型都是Send和Sync的。
例外情況:
1、裸指針不是Send的,也不是Sync的;
2、UnsafeCell不是Sync的(Cell和RefCell也不是);
3、Rc不是Send或Sync的(引用計數是共享且非同步的)。
Rc和UnsafeCell是典型的非線程安全的,因為它們允許非同步地共享可變狀态。
不能自動推導的類型也可以很容易的實作Send和Sync:
struct MyBox(*mut u8);
unsafe impl Send for MyBox {}
unsafe impl Sync for MyBox {}
#![feature(negative_impls)]
// I have some magic semantics for some synchronization primitive!
struct SpecialThreadToken(u8);
impl !Send for SpecialThreadToken {}
impl !Sync for SpecialThreadToken {}