|
71 | 71 | // drop any remaining values at the tail of the source
|
72 | 72 | // but prevent drop of the allocation itself once IntoIter goes out of scope
|
73 | 73 | // if the drop panics then we also leak any elements collected into dst_buf
|
| 74 | + // |
| 75 | + // FIXME: Since `SpecInPlaceCollect::collect_in_place` above might use |
| 76 | + // `__iterator_get_unchecked` internally, this call might be operating on |
| 77 | + // a `vec::IntoIter` with incorrect internal state regarding which elements |
| 78 | + // have already been “consumed”. However, the `TrustedRandomIteratorNoCoerce` |
| 79 | + // implementation of `vec::IntoIter` is only present if the `Vec` elements |
| 80 | + // don’t have a destructor, so it doesn’t matter if elements are “dropped multiple times” |
| 81 | + // in this case. |
| 82 | + // This argument technically currently lacks justification from the `# Safety` docs for |
| 83 | + // `SourceIter`/`InPlaceIterable` and/or `TrustedRandomAccess`, so it might be possible that |
| 84 | + // someone could inadvertently create new library unsoundness |
| 85 | + // involving this `.forget_allocation_drop_remaining()` call. |
74 | 86 | src.forget_allocation_drop_remaining();
|
75 | 87 |
|
76 | 88 | let vec = unsafe { Vec::from_raw_parts(dst_buf, len, cap) };
|
@@ -101,8 +113,11 @@ fn write_in_place_with_drop<T>(
|
101 | 113 | trait SpecInPlaceCollect<T, I>: Iterator<Item = T> {
|
102 | 114 | /// Collects an iterator (`self`) into the destination buffer (`dst`) and returns the number of items
|
103 | 115 | /// collected. `end` is the last writable element of the allocation and used for bounds checks.
|
104 |
| - // FIXME: Clarify safety conditions. Iterator must not be coerced to a subtype |
105 |
| - // after this call due to potential use of [`TrustedRandomAccessNoCoerce`]. |
| 116 | + /// |
| 117 | + /// This method is specialized and one of its implementations makes use of |
| 118 | + /// `Iterator::__iterator_get_unchecked` calls with a `TrustedRandomAccessNoCoerce` bound |
| 119 | + /// on `I` which means the caller of this method must take the safety conditions |
| 120 | + /// of that trait into consideration. |
106 | 121 | fn collect_in_place(&mut self, dst: *mut T, end: *const T) -> usize;
|
107 | 122 | }
|
108 | 123 |
|
|
0 commit comments