Skip to content

Commit

Permalink
Rollup merge of rust-lang#76722 - ssomers:btree_send_sync, r=Mark-Sim…
Browse files Browse the repository at this point in the history
…ulacrum

Test and fix Send and Sync traits of BTreeMap artefacts

Fixes rust-lang#76686.

I'm not quite sure what all this implies. E.g. comparing with the definitions for `NodeRef` in node.rs,  maybe an extra bound `T: 'a` is useful for something. The test compiles on stable/beta (apart from `drain_filter`) so I bet `Sync` is equally desirable.

r? @Mark-Simulacrum
  • Loading branch information
RalfJung authored Sep 19, 2020
2 parents 3d32169 + 176956c commit cfd233f
Show file tree
Hide file tree
Showing 2 changed files with 143 additions and 0 deletions.
3 changes: 3 additions & 0 deletions library/alloc/src/collections/btree/borrow.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@ pub struct DormantMutRef<'a, T> {
_marker: PhantomData<&'a mut T>,
}

unsafe impl<'a, T> Sync for DormantMutRef<'a, T> where &'a mut T: Sync {}
unsafe impl<'a, T> Send for DormantMutRef<'a, T> where &'a mut T: Send {}

impl<'a, T> DormantMutRef<'a, T> {
/// Capture a unique borrow, and immediately reborrow it. For the compiler,
/// the lifetime of the new reference is the same as the lifetime of the
Expand Down
140 changes: 140 additions & 0 deletions library/alloc/src/collections/btree/map/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1418,6 +1418,146 @@ fn test_variance() {
}
}

#[test]
#[allow(dead_code)]
fn test_sync() {
fn map<T: Sync>(v: &BTreeMap<T, T>) -> impl Sync + '_ {
v
}

fn into_iter<T: Sync>(v: BTreeMap<T, T>) -> impl Sync {
v.into_iter()
}

fn into_keys<T: Sync + Ord>(v: BTreeMap<T, T>) -> impl Sync {
v.into_keys()
}

fn into_values<T: Sync + Ord>(v: BTreeMap<T, T>) -> impl Sync {
v.into_values()
}

fn drain_filter<T: Sync + Ord>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
v.drain_filter(|_, _| false)
}

fn iter<T: Sync>(v: &BTreeMap<T, T>) -> impl Sync + '_ {
v.iter()
}

fn iter_mut<T: Sync>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
v.iter_mut()
}

fn keys<T: Sync>(v: &BTreeMap<T, T>) -> impl Sync + '_ {
v.keys()
}

fn values<T: Sync>(v: &BTreeMap<T, T>) -> impl Sync + '_ {
v.values()
}

fn values_mut<T: Sync>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
v.values_mut()
}

fn range<T: Sync + Ord>(v: &BTreeMap<T, T>) -> impl Sync + '_ {
v.range(..)
}

fn range_mut<T: Sync + Ord>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
v.range_mut(..)
}

fn entry<T: Sync + Ord + Default>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
v.entry(Default::default())
}

fn occupied_entry<T: Sync + Ord + Default>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
match v.entry(Default::default()) {
Occupied(entry) => entry,
_ => unreachable!(),
}
}

fn vacant_entry<T: Sync + Ord + Default>(v: &mut BTreeMap<T, T>) -> impl Sync + '_ {
match v.entry(Default::default()) {
Vacant(entry) => entry,
_ => unreachable!(),
}
}
}

#[test]
#[allow(dead_code)]
fn test_send() {
fn map<T: Send>(v: BTreeMap<T, T>) -> impl Send {
v
}

fn into_iter<T: Send>(v: BTreeMap<T, T>) -> impl Send {
v.into_iter()
}

fn into_keys<T: Send + Ord>(v: BTreeMap<T, T>) -> impl Send {
v.into_keys()
}

fn into_values<T: Send + Ord>(v: BTreeMap<T, T>) -> impl Send {
v.into_values()
}

fn drain_filter<T: Send + Ord>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
v.drain_filter(|_, _| false)
}

fn iter<T: Send + Sync>(v: &BTreeMap<T, T>) -> impl Send + '_ {
v.iter()
}

fn iter_mut<T: Send + Sync>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
v.iter_mut()
}

fn keys<T: Send + Sync>(v: &BTreeMap<T, T>) -> impl Send + '_ {
v.keys()
}

fn values<T: Send + Sync>(v: &BTreeMap<T, T>) -> impl Send + '_ {
v.values()
}

fn values_mut<T: Send + Sync>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
v.values_mut()
}

fn range<T: Send + Sync + Ord>(v: &BTreeMap<T, T>) -> impl Send + '_ {
v.range(..)
}

fn range_mut<T: Send + Sync + Ord>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
v.range_mut(..)
}

fn entry<T: Send + Ord + Default>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
v.entry(Default::default())
}

fn occupied_entry<T: Send + Ord + Default>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
match v.entry(Default::default()) {
Occupied(entry) => entry,
_ => unreachable!(),
}
}

fn vacant_entry<T: Send + Ord + Default>(v: &mut BTreeMap<T, T>) -> impl Send + '_ {
match v.entry(Default::default()) {
Vacant(entry) => entry,
_ => unreachable!(),
}
}
}

#[test]
fn test_occupied_entry_key() {
let mut a = BTreeMap::new();
Expand Down

0 comments on commit cfd233f

Please sign in to comment.