Skip to content

Commit 497f64f

Browse files
committed
When growing a GcVec, actually copy the memory
Also remove the Drop impl from GcRawVec. Dropping is the responsibility of the underlying RawVecRepr.
1 parent 54223ca commit 497f64f

File tree

1 file changed

+14
-12
lines changed

1 file changed

+14
-12
lines changed

src/vec.rs

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -123,8 +123,18 @@ impl<'gc, T: GcSafe, Ctx: GcSimpleAlloc> GcVec<'gc, T, Ctx> {
123123
Err(ReallocFailedError::SizeUnsupported) => {} // fallthrough to realloc
124124
}
125125
}
126-
// Just allocate a new one!
127-
self.raw = self.context.alloc_vec_with_capacity(new_capacity).raw;
126+
// Just allocate a new one, copying from the old
127+
let mut new_mem = self.context.alloc_vec_with_capacity(new_capacity).raw;
128+
// TODO: Write barriers
129+
unsafe {
130+
(new_mem.as_repr_mut().ptr() as *mut T).copy_from_nonoverlapping(
131+
self.raw.as_ptr() as *const T,
132+
self.raw.len()
133+
);
134+
new_mem.as_repr_mut().set_len(self.raw.len());
135+
let mut old_mem = std::mem::replace(&mut self.raw, new_mem);
136+
old_mem.as_repr_mut().set_len(0); // We don't want to drop the old elements
137+
}
128138
}
129139
}
130140
unsafe_gc_impl!(
@@ -259,7 +269,7 @@ impl<'gc, T: GcSafe, Id: CollectorId> GcRawVec<'gc, T, Id> {
259269
unsafe {
260270
// TODO: Write barriers....
261271
(self.as_ptr() as *mut T).add(old_len).write(val);
262-
self.repr.set_len(old_len);
272+
self.repr.set_len(old_len + 1);
263273
}
264274
Ok(())
265275
} else {
@@ -310,14 +320,6 @@ impl<'gc, T: GcSafe, Id: CollectorId> Deref for GcRawVec<'gc, T, Id> {
310320
self.as_slice() // &'gc > &'self
311321
}
312322
}
313-
impl<'gc, T: GcSafe, Id: CollectorId> Drop for GcRawVec<'gc, T, Id> {
314-
fn drop(&mut self) {
315-
unsafe { std::ptr::drop_in_place(std::ptr::slice_from_raw_parts_mut(
316-
self.as_ptr() as *mut T,
317-
self.len()
318-
)) }
319-
}
320-
}
321323
unsafe_gc_impl!(
322324
target => GcRawVec<'gc, T, Id>,
323325
params => ['gc, T: GcSafe, Id: CollectorId],
@@ -337,7 +339,7 @@ unsafe_gc_impl!(
337339
erased_type => GcRawVec<'min, <T as GcErase<'min, Id>>::Erased, Id>,
338340
null_trace => never,
339341
NEEDS_TRACE => true,
340-
NEEDS_DROP => T::NEEDS_DROP /* if our inner type needs a drop */,
342+
NEEDS_DROP => false, // GcVecRepr is responsible for Drop
341343
trace_mut => |self, visitor| {
342344
unsafe { visitor.visit_vec::<T, Id>(self.as_repr_mut()) }
343345
},

0 commit comments

Comments
 (0)