Bug 1595212 - Use MaybeUninit in nsString tests. r=SimonSapin
authorEmilio Cobos Álvarez <emilio@crisal.io>
Wed, 13 Nov 2019 12:39:23 +0000
changeset 501812 c17276cc50c4d18a28a8653028f9489ba998d9bc
parent 501811 da8d5a96f3c8f93be0a4ca787eedd410dcf3b0c8
child 501813 d791bfa31f08ec478b2ef6ca4f89b3a8849d723b
push id114172
push userdluca@mozilla.com
push dateTue, 19 Nov 2019 11:31:10 +0000
treeherdermozilla-inbound@b5c5ba07d3db [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersSimonSapin
bugs1595212
milestone72.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1595212 - Use MaybeUninit in nsString tests. r=SimonSapin Differential Revision: https://phabricator.services.mozilla.com/D52824
xpcom/rust/nsstring/src/lib.rs
--- a/xpcom/rust/nsstring/src/lib.rs
+++ b/xpcom/rust/nsstring/src/lib.rs
@@ -1365,67 +1365,52 @@ pub mod test_helpers {
 
     /// Generates a $[no_mangle] extern "C" function which returns the size,
     /// alignment and offset in the parent struct of a given member, with the
     /// given name.
     ///
     /// This method can trigger Undefined Behavior if the accessing the member
     /// $member on a given type would use that type's `Deref` implementation.
     macro_rules! member_check {
-        ($T:ty, $member:ident, $method:ident) => {
-            #[no_mangle]
-            #[allow(non_snake_case)]
-            pub extern fn $method(size: *mut usize,
-                                  align: *mut usize,
-                                  offset: *mut usize) {
-                unsafe {
-                    // Create a temporary value of type T to get offsets, sizes
-                    // and aligns off of
-                    let tmp: $T = mem::zeroed();
-                    *size = mem::size_of_val(&tmp.$member);
-                    *align = mem::align_of_val(&tmp.$member);
-                    *offset =
-                        (&tmp.$member as *const _ as usize) -
-                        (&tmp as *const _ as usize);
-                    mem::forget(tmp);
-                }
-            }
-        };
         ($T:ty, $U:ty, $V:ty, $member:ident, $method:ident) => {
             #[no_mangle]
             #[allow(non_snake_case)]
             pub extern fn $method(size: *mut usize,
                                   align: *mut usize,
                                   offset: *mut usize) {
                 unsafe {
                     // Create a temporary value of type T to get offsets, sizes
                     // and alignments from.
-                    let tmp: $T = mem::zeroed();
+                    let tmp: mem::MaybeUninit<$T> = mem::MaybeUninit::uninit();
+                    // FIXME: This should use &raw references when available,
+                    // this is technically UB as it creates a reference to
+                    // uninitialized memory, but there's no better way to do
+                    // this right now.
+                    let tmp = &*tmp.as_ptr();
                     *size = mem::size_of_val(&tmp.$member);
                     *align = mem::align_of_val(&tmp.$member);
                     *offset =
                         (&tmp.$member as *const _ as usize) -
-                        (&tmp as *const _ as usize);
-                    mem::forget(tmp);
+                        (tmp as *const $T as usize);
 
-                    let tmp: $U = mem::zeroed();
+                    let tmp: mem::MaybeUninit<$U> = mem::MaybeUninit::uninit();
+                    let tmp = &*tmp.as_ptr();
                     assert_eq!(*size, mem::size_of_val(&tmp.hdr.$member));
                     assert_eq!(*align, mem::align_of_val(&tmp.hdr.$member));
                     assert_eq!(*offset,
                                (&tmp.hdr.$member as *const _ as usize) -
-                               (&tmp as *const _ as usize));
-                    mem::forget(tmp);
+                               (tmp as *const $U as usize));
 
-                    let tmp: $V = mem::zeroed();
+                    let tmp: mem::MaybeUninit<$V> = mem::MaybeUninit::uninit();
+                    let tmp = &*tmp.as_ptr();
                     assert_eq!(*size, mem::size_of_val(&tmp.hdr.$member));
                     assert_eq!(*align, mem::align_of_val(&tmp.hdr.$member));
                     assert_eq!(*offset,
                                (&tmp.hdr.$member as *const _ as usize) -
-                               (&tmp as *const _ as usize));
-                    mem::forget(tmp);
+                               (tmp as *const $V as usize));
                 }
             }
         }
     }
 
     member_check!(nsStringRepr, nsString, nsStr<'static>,
                   data, Rust_Test_Member_nsString_mData);
     member_check!(nsStringRepr, nsString, nsStr<'static>,