From 747dbcb3255399396ca16c8462c5a809423c7350 Mon Sep 17 00:00:00 2001 From: CAD97 Date: Sat, 9 Jan 2021 14:32:55 -0500 Subject: [PATCH] Provide reasoning for rc data_offset safety --- library/alloc/src/rc.rs | 10 ++++++---- library/alloc/src/sync.rs | 10 ++++++---- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/library/alloc/src/rc.rs b/library/alloc/src/rc.rs index ed22571409c..b9f3f357c1a 100644 --- a/library/alloc/src/rc.rs +++ b/library/alloc/src/rc.rs @@ -2314,10 +2314,12 @@ impl Unpin for Rc {} /// The pointer must point to (and have valid metadata for) a previously /// valid instance of T, but the T is allowed to be dropped. unsafe fn data_offset(ptr: *const T) -> isize { - // Align the unsized value to the end of the `RcBox`. - // Because it is ?Sized, it will always be the last field in memory. - // Note: This is a detail of the current implementation of the compiler, - // and is not a guaranteed language detail. Do not rely on it outside of std. + // Align the unsized value to the end of the RcBox. + // Because RcBox is repr(C), it will always be the last field in memory. + // SAFETY: since the only unsized types possible are slices, trait objects, + // and extern types, the input safety requirement is currently enough to + // satisfy the requirements of align_of_val_raw; this is an implementation + // detail of the language that may not be relied upon outside of std. unsafe { data_offset_align(align_of_val_raw(ptr)) } } diff --git a/library/alloc/src/sync.rs b/library/alloc/src/sync.rs index aa6acdbff34..c50f5270a4d 100644 --- a/library/alloc/src/sync.rs +++ b/library/alloc/src/sync.rs @@ -2464,10 +2464,12 @@ impl Unpin for Arc {} /// The pointer must point to (and have valid metadata for) a previously /// valid instance of T, but the T is allowed to be dropped. unsafe fn data_offset(ptr: *const T) -> isize { - // Align the unsized value to the end of the `ArcInner`. - // Because it is `?Sized`, it will always be the last field in memory. - // Note: This is a detail of the current implementation of the compiler, - // and is not a guaranteed language detail. Do not rely on it outside of std. + // Align the unsized value to the end of the ArcInner. + // Because RcBox is repr(C), it will always be the last field in memory. + // SAFETY: since the only unsized types possible are slices, trait objects, + // and extern types, the input safety requirement is currently enough to + // satisfy the requirements of align_of_val_raw; this is an implementation + // detail of the language that may not be relied upon outside of std. unsafe { data_offset_align(align_of_val_raw(ptr)) } }