Skip to content

Commit d26b37a

Browse files
committed
Auto merge of #201 - cuviper:safe-drain, r=Amanieu
Make `RawTable::drain` safe The documentation indicated a safety question of the lifetime, but there is a lifetime parameter on `RawDrain` to ensure that. Also, the similar `par_drain` is already a safe method. I also adjusted the safety comments on `drain_iter_from`/`into_iter_from`. The safety contract for these methods is really about the validity of the given `RawIter` for this `RawTable`. Once that's established, the lifetime is no longer a concern, since `RawDrain<'_, T>` has a borrow and `RawIntoIter<T>` is a consuming owner.
2 parents 0f38616 + a56db69 commit d26b37a

File tree

2 files changed

+13
-22
lines changed

2 files changed

+13
-22
lines changed

src/map.rs

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -548,11 +548,8 @@ impl<K, V, S> HashMap<K, V, S> {
548548
/// ```
549549
#[cfg_attr(feature = "inline-more", inline)]
550550
pub fn drain(&mut self) -> Drain<'_, K, V> {
551-
// Here we tie the lifetime of self to the iter.
552-
unsafe {
553-
Drain {
554-
inner: self.table.drain(),
555-
}
551+
Drain {
552+
inner: self.table.drain(),
556553
}
557554
}
558555

src/raw/mod.rs

Lines changed: 11 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1062,25 +1062,21 @@ impl<T> RawTable<T> {
10621062

10631063
/// Returns an iterator which removes all elements from the table without
10641064
/// freeing the memory.
1065-
///
1066-
/// It is up to the caller to ensure that the `RawTable` outlives the `RawDrain`.
1067-
/// Because we cannot make the `next` method unsafe on the `RawDrain`,
1068-
/// we have to make the `drain` method unsafe.
10691065
#[cfg_attr(feature = "inline-more", inline)]
1070-
pub unsafe fn drain(&mut self) -> RawDrain<'_, T> {
1071-
let iter = self.iter();
1072-
self.drain_iter_from(iter)
1066+
pub fn drain(&mut self) -> RawDrain<'_, T> {
1067+
unsafe {
1068+
let iter = self.iter();
1069+
self.drain_iter_from(iter)
1070+
}
10731071
}
10741072

10751073
/// Returns an iterator which removes all elements from the table without
10761074
/// freeing the memory.
10771075
///
1078-
/// It is up to the caller to ensure that the `RawTable` outlives the `RawDrain`.
1079-
/// Because we cannot make the `next` method unsafe on the `RawDrain`,
1080-
/// we have to make the `drain` method unsafe.
1081-
///
10821076
/// Iteration starts at the provided iterator's current location.
1083-
/// You must ensure that the iterator covers all items that remain in the table.
1077+
///
1078+
/// It is up to the caller to ensure that the iterator is valid for this
1079+
/// `RawTable` and covers all items that remain in the table.
10841080
#[cfg_attr(feature = "inline-more", inline)]
10851081
pub unsafe fn drain_iter_from(&mut self, iter: RawIter<T>) -> RawDrain<'_, T> {
10861082
debug_assert_eq!(iter.len(), self.len());
@@ -1094,12 +1090,10 @@ impl<T> RawTable<T> {
10941090

10951091
/// Returns an iterator which consumes all elements from the table.
10961092
///
1097-
/// It is up to the caller to ensure that the `RawTable` outlives the `RawIntoIter`.
1098-
/// Because we cannot make the `next` method unsafe on the `RawIntoIter`,
1099-
/// we have to make the `into_iter_from` method unsafe.
1100-
///
11011093
/// Iteration starts at the provided iterator's current location.
1102-
/// You must ensure that the iterator covers all items that remain in the table.
1094+
///
1095+
/// It is up to the caller to ensure that the iterator is valid for this
1096+
/// `RawTable` and covers all items that remain in the table.
11031097
pub unsafe fn into_iter_from(self, iter: RawIter<T>) -> RawIntoIter<T> {
11041098
debug_assert_eq!(iter.len(), self.len());
11051099

0 commit comments

Comments
 (0)