diff --git a/src/liballoc/alloc.rs b/src/liballoc/alloc.rs
index 84bd275df347c..8b1081d30119e 100644
--- a/src/liballoc/alloc.rs
+++ b/src/liballoc/alloc.rs
@@ -40,10 +40,14 @@ extern "Rust" {
 /// This type implements the [`Alloc`] trait by forwarding calls
 /// to the allocator registered with the `#[global_allocator]` attribute
 /// if there is one, or the `std` crate’s default.
+#[cfg(not(test))]
 #[unstable(feature = "allocator_api", issue = "32838")]
 #[derive(Copy, Clone, Default, Debug)]
 pub struct Global;
 
+#[cfg(test)]
+pub use std::alloc::Global;
+
 /// Allocate memory with the global allocator.
 ///
 /// This function forwards calls to the [`GlobalAlloc::alloc`] method
@@ -116,6 +120,7 @@ pub unsafe fn alloc_zeroed(layout: Layout) -> *mut u8 {
     __rust_alloc_zeroed(layout.size(), layout.align())
 }
 
+#[cfg(not(test))]
 #[unstable(feature = "allocator_api", issue = "32838")]
 unsafe impl Alloc for Global {
     #[inline]
@@ -154,25 +159,23 @@ unsafe fn exchange_malloc(size: usize, align: usize) -> *mut u8 {
         align as *mut u8
     } else {
         let layout = Layout::from_size_align_unchecked(size, align);
-        let ptr = alloc(layout);
-        if !ptr.is_null() {
-            ptr
-        } else {
-            handle_alloc_error(layout)
+        match Global.alloc(layout) {
+            Ok(ptr) => ptr.as_ptr(),
+            Err(_) => handle_alloc_error(layout),
         }
     }
 }
 
 #[cfg_attr(not(test), lang = "box_free")]
 #[inline]
-pub(crate) unsafe fn box_free<T: ?Sized>(ptr: Unique<T>) {
+pub(crate) unsafe fn box_free<T: ?Sized, A: Alloc>(ptr: Unique<T>, mut a: A) {
     let ptr = ptr.as_ptr();
     let size = size_of_val(&*ptr);
     let align = min_align_of_val(&*ptr);
     // We do not allocate for Box<T> when T is ZST, so deallocation is also not necessary.
     if size != 0 {
         let layout = Layout::from_size_align_unchecked(size, align);
-        dealloc(ptr as *mut u8, layout);
+        a.dealloc(NonNull::new_unchecked(ptr).cast(), layout);
     }
 }
 
diff --git a/src/liballoc/boxed.rs b/src/liballoc/boxed.rs
index 44f15981137ba..ac27930462abd 100644
--- a/src/liballoc/boxed.rs
+++ b/src/liballoc/boxed.rs
@@ -69,6 +69,7 @@ use core::ops::{CoerceUnsized, Deref, DerefMut, Generator, GeneratorState};
 use core::ptr::{self, NonNull, Unique};
 use core::task::{Context, Poll};
 
+use alloc::{Alloc, Global, Layout, handle_alloc_error};
 use raw_vec::RawVec;
 use str::from_boxed_utf8_unchecked;
 
@@ -78,7 +79,7 @@ use str::from_boxed_utf8_unchecked;
 #[lang = "owned_box"]
 #[fundamental]
 #[stable(feature = "rust1", since = "1.0.0")]
-pub struct Box<T: ?Sized>(Unique<T>);
+pub struct Box<T: ?Sized, A: Alloc = Global>(Unique<T>, A);
 
 impl<T> Box<T> {
     /// Allocates memory on the heap and then places `x` into it.
@@ -97,6 +98,37 @@ impl<T> Box<T> {
     }
 }
 
+impl<T, A: Alloc> Box<T, A> {
+    /// Allocates memory in the given allocator and then places `x` into it.
+    ///
+    /// This doesn't actually allocate if `T` is zero-sized.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// # #![feature(allocator_api)]
+    /// use std::alloc::Global;
+    /// let five = Box::new_in(5, Global);
+    /// ```
+    #[unstable(feature = "allocator_api", issue = "32838")]
+    #[inline(always)]
+    pub fn new_in(x: T, a: A) -> Box<T, A> {
+        let mut a = a;
+        let layout = Layout::for_value(&x);
+        let size = layout.size();
+        let ptr = if size == 0 {
+            Unique::empty()
+        } else {
+            unsafe {
+                let ptr = a.alloc(layout).unwrap_or_else(|_| handle_alloc_error(layout));
+                ptr::write(ptr.as_ptr() as *mut T, x);
+                ptr.cast().into()
+            }
+        };
+        Box(ptr, a)
+    }
+}
+
 impl<T: ?Sized> Box<T> {
     /// Constructs a box from a raw pointer.
     ///
@@ -123,7 +155,35 @@ impl<T: ?Sized> Box<T> {
     #[stable(feature = "box_raw", since = "1.4.0")]
     #[inline]
     pub unsafe fn from_raw(raw: *mut T) -> Self {
-        Box(Unique::new_unchecked(raw))
+        Box(Unique::new_unchecked(raw), Global)
+    }
+}
+
+impl<T: ?Sized, A: Alloc> Box<T, A> {
+    /// Constructs a box from a raw pointer in the given allocator.
+    ///
+    /// This is similar to the [`Box::from_raw`] function, but assumes
+    /// the pointer was allocated with the given allocator.
+    ///
+    /// This function is unsafe because improper use may lead to
+    /// memory problems. For example, specifying the wrong allocator
+    /// may corrupt the allocator state.
+    ///
+    /// [`Box::from_raw`]: struct.Box.html#method.from_raw
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// # #![feature(allocator_api)]
+    /// use std::alloc::Global;
+    /// let x = Box::new_in(5, Global);
+    /// let ptr = Box::into_raw(x);
+    /// let x = unsafe { Box::from_raw_in(ptr, Global) };
+    /// ```
+    #[unstable(feature = "allocator_api", issue = "32838")]
+    #[inline]
+    pub unsafe fn from_raw_in(raw: *mut T, a: A) -> Self {
+        Box(Unique::new_unchecked(raw), a)
     }
 
     /// Consumes the `Box`, returning the wrapped raw pointer.
@@ -148,7 +208,7 @@ impl<T: ?Sized> Box<T> {
     /// ```
     #[stable(feature = "box_raw", since = "1.4.0")]
     #[inline]
-    pub fn into_raw(b: Box<T>) -> *mut T {
+    pub fn into_raw(b: Box<T, A>) -> *mut T {
         Box::into_raw_non_null(b).as_ptr()
     }
 
@@ -180,14 +240,14 @@ impl<T: ?Sized> Box<T> {
     /// ```
     #[unstable(feature = "box_into_raw_non_null", issue = "47336")]
     #[inline]
-    pub fn into_raw_non_null(b: Box<T>) -> NonNull<T> {
+    pub fn into_raw_non_null(b: Box<T, A>) -> NonNull<T> {
         Box::into_unique(b).into()
     }
 
     #[unstable(feature = "ptr_internals", issue = "0", reason = "use into_raw_non_null instead")]
     #[inline]
     #[doc(hidden)]
-    pub fn into_unique(b: Box<T>) -> Unique<T> {
+    pub fn into_unique(b: Box<T, A>) -> Unique<T> {
         let unique = b.0;
         mem::forget(b);
         unique
@@ -234,7 +294,7 @@ impl<T: ?Sized> Box<T> {
     /// ```
     #[stable(feature = "box_leak", since = "1.26.0")]
     #[inline]
-    pub fn leak<'a>(b: Box<T>) -> &'a mut T
+    pub fn leak<'a>(b: Box<T, A>) -> &'a mut T
     where
         T: 'a // Technically not needed, but kept to be explicit.
     {
@@ -243,7 +303,7 @@ impl<T: ?Sized> Box<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-unsafe impl<#[may_dangle] T: ?Sized> Drop for Box<T> {
+unsafe impl<#[may_dangle] T: ?Sized, A: Alloc> Drop for Box<T, A> {
     fn drop(&mut self) {
         // FIXME: Do nothing, drop is currently performed by compiler.
     }
@@ -257,10 +317,18 @@ impl<T: Default> Default for Box<T> {
     }
 }
 
+#[unstable(feature = "allocator_api", issue = "32838")]
+impl<T: Default, A: Alloc + Default> Default for Box<T, A> {
+    /// Creates a `Box<T, A>`, with the `Default` value for T.
+    default fn default() -> Box<T, A> {
+        Box::new_in(Default::default(), Default::default())
+    }
+}
+
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T> Default for Box<[T]> {
-    fn default() -> Box<[T]> {
-        Box::<[T; 0]>::new([])
+impl<T, A: Alloc + Default> Default for Box<[T], A> {
+    fn default() -> Box<[T], A> {
+        Box::<[T; 0], A>::new_in([], A::default())
     }
 }
 
@@ -286,6 +354,7 @@ impl<T: Clone> Clone for Box<T> {
     fn clone(&self) -> Box<T> {
         box { (**self).clone() }
     }
+
     /// Copies `source`'s contents into `self` without creating a new allocation.
     ///
     /// # Examples
@@ -304,6 +373,18 @@ impl<T: Clone> Clone for Box<T> {
     }
 }
 
+#[unstable(feature = "allocator_api", issue = "32838")]
+impl<T: Clone, A: Alloc + Clone> Clone for Box<T, A> {
+    #[inline]
+    default fn clone(&self) -> Box<T, A> {
+        Box::new_in((**self).clone(), self.1.clone())
+    }
+
+    #[inline]
+    default fn clone_from(&mut self, source: &Box<T, A>) {
+        (**self).clone_from(&(**source));
+    }
+}
 
 #[stable(feature = "box_slice_clone", since = "1.3.0")]
 impl Clone for Box<str> {
@@ -318,58 +399,58 @@ impl Clone for Box<str> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized + PartialEq> PartialEq for Box<T> {
+impl<T: ?Sized + PartialEq, A: Alloc> PartialEq for Box<T, A> {
     #[inline]
-    fn eq(&self, other: &Box<T>) -> bool {
+    fn eq(&self, other: &Box<T, A>) -> bool {
         PartialEq::eq(&**self, &**other)
     }
     #[inline]
-    fn ne(&self, other: &Box<T>) -> bool {
+    fn ne(&self, other: &Box<T, A>) -> bool {
         PartialEq::ne(&**self, &**other)
     }
 }
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized + PartialOrd> PartialOrd for Box<T> {
+impl<T: ?Sized + PartialOrd, A: Alloc> PartialOrd for Box<T, A> {
     #[inline]
-    fn partial_cmp(&self, other: &Box<T>) -> Option<Ordering> {
+    fn partial_cmp(&self, other: &Box<T, A>) -> Option<Ordering> {
         PartialOrd::partial_cmp(&**self, &**other)
     }
     #[inline]
-    fn lt(&self, other: &Box<T>) -> bool {
+    fn lt(&self, other: &Box<T, A>) -> bool {
         PartialOrd::lt(&**self, &**other)
     }
     #[inline]
-    fn le(&self, other: &Box<T>) -> bool {
+    fn le(&self, other: &Box<T, A>) -> bool {
         PartialOrd::le(&**self, &**other)
     }
     #[inline]
-    fn ge(&self, other: &Box<T>) -> bool {
+    fn ge(&self, other: &Box<T, A>) -> bool {
         PartialOrd::ge(&**self, &**other)
     }
     #[inline]
-    fn gt(&self, other: &Box<T>) -> bool {
+    fn gt(&self, other: &Box<T, A>) -> bool {
         PartialOrd::gt(&**self, &**other)
     }
 }
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized + Ord> Ord for Box<T> {
+impl<T: ?Sized + Ord, A: Alloc> Ord for Box<T, A> {
     #[inline]
-    fn cmp(&self, other: &Box<T>) -> Ordering {
+    fn cmp(&self, other: &Box<T, A>) -> Ordering {
         Ord::cmp(&**self, &**other)
     }
 }
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized + Eq> Eq for Box<T> {}
+impl<T: ?Sized + Eq, A: Alloc> Eq for Box<T, A> {}
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized + Hash> Hash for Box<T> {
+impl<T: ?Sized + Hash, A: Alloc> Hash for Box<T, A> {
     fn hash<H: Hasher>(&self, state: &mut H) {
         (**self).hash(state);
     }
 }
 
 #[stable(feature = "indirect_hasher_impl", since = "1.22.0")]
-impl<T: ?Sized + Hasher> Hasher for Box<T> {
+impl<T: ?Sized + Hasher, A: Alloc> Hasher for Box<T, A> {
     fn finish(&self) -> u64 {
         (**self).finish()
     }
@@ -421,10 +502,18 @@ impl<T> From<T> for Box<T> {
     }
 }
 
+#[unstable(feature = "allocator_api", issue = "32838")]
+impl<T, A: Alloc + Default> From<T> for Box<T, A> {
+    default fn from(t: T) -> Self {
+        Box::new_in(t, A::default())
+    }
+}
+
 #[stable(feature = "box_from_slice", since = "1.17.0")]
-impl<'a, T: Copy> From<&'a [T]> for Box<[T]> {
-    fn from(slice: &'a [T]) -> Box<[T]> {
-        let mut boxed = unsafe { RawVec::with_capacity(slice.len()).into_box() };
+impl<'a, T: Copy, A: Alloc + Default> From<&'a [T]> for Box<[T], A> {
+    fn from(slice: &'a [T]) -> Box<[T], A> {
+        let a = A::default();
+        let mut boxed = unsafe { RawVec::with_capacity_in(slice.len(), a).into_box() };
         boxed.copy_from_slice(slice);
         boxed
     }
@@ -511,21 +600,21 @@ impl Box<dyn Any + Send> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: fmt::Display + ?Sized> fmt::Display for Box<T> {
+impl<T: fmt::Display + ?Sized, A: Alloc> fmt::Display for Box<T, A> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         fmt::Display::fmt(&**self, f)
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: fmt::Debug + ?Sized> fmt::Debug for Box<T> {
+impl<T: fmt::Debug + ?Sized, A: Alloc> fmt::Debug for Box<T, A> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         fmt::Debug::fmt(&**self, f)
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> fmt::Pointer for Box<T> {
+impl<T: ?Sized, A: Alloc> fmt::Pointer for Box<T, A> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         // It's not possible to extract the inner Uniq directly from the Box,
         // instead we cast it to a *const which aliases the Unique
@@ -535,7 +624,7 @@ impl<T: ?Sized> fmt::Pointer for Box<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> Deref for Box<T> {
+impl<T: ?Sized, A: Alloc> Deref for Box<T, A> {
     type Target = T;
 
     fn deref(&self) -> &T {
@@ -544,14 +633,14 @@ impl<T: ?Sized> Deref for Box<T> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T: ?Sized> DerefMut for Box<T> {
+impl<T: ?Sized, A: Alloc> DerefMut for Box<T, A> {
     fn deref_mut(&mut self) -> &mut T {
         &mut **self
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<I: Iterator + ?Sized> Iterator for Box<I> {
+impl<I: Iterator + ?Sized, A: Alloc> Iterator for Box<I, A> {
     type Item = I::Item;
     fn next(&mut self) -> Option<I::Item> {
         (**self).next()
@@ -564,13 +653,13 @@ impl<I: Iterator + ?Sized> Iterator for Box<I> {
     }
 }
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<I: DoubleEndedIterator + ?Sized> DoubleEndedIterator for Box<I> {
+impl<I: DoubleEndedIterator + ?Sized, A: Alloc> DoubleEndedIterator for Box<I, A> {
     fn next_back(&mut self) -> Option<I::Item> {
         (**self).next_back()
     }
 }
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<I: ExactSizeIterator + ?Sized> ExactSizeIterator for Box<I> {
+impl<I: ExactSizeIterator + ?Sized, A: Alloc> ExactSizeIterator for Box<I, A> {
     fn len(&self) -> usize {
         (**self).len()
     }
@@ -580,7 +669,7 @@ impl<I: ExactSizeIterator + ?Sized> ExactSizeIterator for Box<I> {
 }
 
 #[stable(feature = "fused", since = "1.26.0")]
-impl<I: FusedIterator + ?Sized> FusedIterator for Box<I> {}
+impl<I: FusedIterator + ?Sized, A: Alloc> FusedIterator for Box<I, A> {}
 
 
 /// `FnBox` is a version of the `FnOnce` intended for use with boxed
@@ -662,13 +751,13 @@ impl<'a, A, R> FnOnce<A> for Box<dyn FnBox<A, Output = R> + Send + 'a> {
 }
 
 #[unstable(feature = "coerce_unsized", issue = "27732")]
-impl<T: ?Sized + Unsize<U>, U: ?Sized> CoerceUnsized<Box<U>> for Box<T> {}
+impl<T: ?Sized + Unsize<U>, U: ?Sized, A: Alloc> CoerceUnsized<Box<U, A>> for Box<T, A> {}
 
 #[stable(feature = "box_slice_clone", since = "1.3.0")]
-impl<T: Clone> Clone for Box<[T]> {
+impl<T: Clone, A: Alloc + Clone> Clone for Box<[T], A> {
     fn clone(&self) -> Self {
         let mut new = BoxBuilder {
-            data: RawVec::with_capacity(self.len()),
+            data: RawVec::with_capacity_in(self.len(), self.1.clone()),
             len: 0,
         };
 
@@ -686,20 +775,20 @@ impl<T: Clone> Clone for Box<[T]> {
         return unsafe { new.into_box() };
 
         // Helper type for responding to panics correctly.
-        struct BoxBuilder<T> {
-            data: RawVec<T>,
+        struct BoxBuilder<T, A: Alloc> {
+            data: RawVec<T, A>,
             len: usize,
         }
 
-        impl<T> BoxBuilder<T> {
-            unsafe fn into_box(self) -> Box<[T]> {
+        impl<T, A: Alloc> BoxBuilder<T, A> {
+            unsafe fn into_box(self) -> Box<[T], A> {
                 let raw = ptr::read(&self.data);
                 mem::forget(self);
                 raw.into_box()
             }
         }
 
-        impl<T> Drop for BoxBuilder<T> {
+        impl<T, A: Alloc> Drop for BoxBuilder<T, A> {
             fn drop(&mut self) {
                 let mut data = self.data.ptr();
                 let max = unsafe { data.offset(self.len as isize) };
@@ -716,35 +805,35 @@ impl<T: Clone> Clone for Box<[T]> {
 }
 
 #[stable(feature = "box_borrow", since = "1.1.0")]
-impl<T: ?Sized> borrow::Borrow<T> for Box<T> {
+impl<T: ?Sized, A: Alloc> borrow::Borrow<T> for Box<T, A> {
     fn borrow(&self) -> &T {
         &**self
     }
 }
 
 #[stable(feature = "box_borrow", since = "1.1.0")]
-impl<T: ?Sized> borrow::BorrowMut<T> for Box<T> {
+impl<T: ?Sized, A: Alloc> borrow::BorrowMut<T> for Box<T, A> {
     fn borrow_mut(&mut self) -> &mut T {
         &mut **self
     }
 }
 
 #[stable(since = "1.5.0", feature = "smart_ptr_as_ref")]
-impl<T: ?Sized> AsRef<T> for Box<T> {
+impl<T: ?Sized, A: Alloc> AsRef<T> for Box<T, A> {
     fn as_ref(&self) -> &T {
         &**self
     }
 }
 
 #[stable(since = "1.5.0", feature = "smart_ptr_as_ref")]
-impl<T: ?Sized> AsMut<T> for Box<T> {
+impl<T: ?Sized, A: Alloc> AsMut<T> for Box<T, A> {
     fn as_mut(&mut self) -> &mut T {
         &mut **self
     }
 }
 
 #[unstable(feature = "generator_trait", issue = "43122")]
-impl<T> Generator for Box<T>
+impl<T, A: Alloc> Generator for Box<T, A>
     where T: Generator + ?Sized
 {
     type Yield = T::Yield;
diff --git a/src/liballoc/raw_vec.rs b/src/liballoc/raw_vec.rs
index 4f2686abf4515..a800e78d4b49d 100644
--- a/src/liballoc/raw_vec.rs
+++ b/src/liballoc/raw_vec.rs
@@ -693,8 +693,8 @@ impl<T, A: Alloc> RawVec<T, A> {
 
 }
 
-impl<T> RawVec<T, Global> {
-    /// Converts the entire buffer into `Box<[T]>`.
+impl<T, A: Alloc> RawVec<T, A> {
+    /// Converts the entire buffer into `Box<[T], A>`.
     ///
     /// While it is not *strictly* Undefined Behavior to call
     /// this procedure while some of the RawVec is uninitialized,
@@ -702,10 +702,11 @@ impl<T> RawVec<T, Global> {
     ///
     /// Note that this will correctly reconstitute any `cap` changes
     /// that may have been performed. (see description of type for details)
-    pub unsafe fn into_box(self) -> Box<[T]> {
+    pub unsafe fn into_box(self) -> Box<[T], A> {
         // NOTE: not calling `cap()` here, actually using the real `cap` field!
         let slice = slice::from_raw_parts_mut(self.ptr(), self.cap);
-        let output: Box<[T]> = Box::from_raw(slice);
+        let a = ptr::read(&self.a);
+        let output: Box<[T], A> = Box::from_raw_in(slice, a);
         mem::forget(self);
         output
     }
diff --git a/src/liballoc/rc.rs b/src/liballoc/rc.rs
index be049eb6e5ef3..1fdb70d9a760e 100644
--- a/src/liballoc/rc.rs
+++ b/src/liballoc/rc.rs
@@ -690,7 +690,7 @@ impl<T: ?Sized> Rc<T> {
                 value_size);
 
             // Free the allocation without dropping its contents
-            box_free(box_unique);
+            box_free(box_unique, Global);
 
             Rc { ptr: NonNull::new_unchecked(ptr), phantom: PhantomData }
         }
diff --git a/src/liballoc/sync.rs b/src/liballoc/sync.rs
index a00b6b4e435f0..962e1251c2323 100644
--- a/src/liballoc/sync.rs
+++ b/src/liballoc/sync.rs
@@ -590,7 +590,7 @@ impl<T: ?Sized> Arc<T> {
                 value_size);
 
             // Free the allocation without dropping its contents
-            box_free(box_unique);
+            box_free(box_unique, Global);
 
             Arc { ptr: NonNull::new_unchecked(ptr), phantom: PhantomData }
         }
diff --git a/src/test/mir-opt/validate_2.rs b/src/test/mir-opt/validate_2.rs
index 3776a11b3ab82..46f0aaad47ce0 100644
--- a/src/test/mir-opt/validate_2.rs
+++ b/src/test/mir-opt/validate_2.rs
@@ -22,14 +22,14 @@ fn main() {
 // fn main() -> () {
 //     ...
 //     bb1: {
-//         Validate(Acquire, [_2: std::boxed::Box<[i32; 3]>]);
-//         Validate(Release, [_2: std::boxed::Box<[i32; 3]>]);
-//         _1 = move _2 as std::boxed::Box<[i32]> (Unsize);
-//         Validate(Acquire, [_1: std::boxed::Box<[i32]>]);
+//         Validate(Acquire, [_2: std::boxed::Box<[i32; 3], std::alloc::Global>]);
+//         Validate(Release, [_2: std::boxed::Box<[i32; 3], std::alloc::Global>]);
+//         _1 = move _2 as std::boxed::Box<[i32], std::alloc::Global> (Unsize);
+//         Validate(Acquire, [_1: std::boxed::Box<[i32], std::alloc::Global>]);
 //         StorageDead(_2);
 //         StorageDead(_3);
 //         _0 = ();
-//         Validate(Release, [_1: std::boxed::Box<[i32]>]);
+//         Validate(Release, [_1: std::boxed::Box<[i32], std::alloc::Global>]);
 //         drop(_1) -> [return: bb2, unwind: bb3];
 //     }
 //     ...
diff --git a/src/test/ui/e0119/conflict-with-std.stderr b/src/test/ui/e0119/conflict-with-std.stderr
index e8b2c84c0df0b..72db200637f6a 100644
--- a/src/test/ui/e0119/conflict-with-std.stderr
+++ b/src/test/ui/e0119/conflict-with-std.stderr
@@ -5,8 +5,8 @@ LL | impl AsRef<Q> for Box<Q> { //~ ERROR conflicting implementations
    | ^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: conflicting implementation in crate `alloc`:
-           - impl<T> std::convert::AsRef<T> for std::boxed::Box<T>
-             where T: ?Sized;
+           - impl<T, A> std::convert::AsRef<T> for std::boxed::Box<T, A>
+             where A: std::alloc::Alloc, T: ?Sized;
 
 error[E0119]: conflicting implementations of trait `std::convert::From<S>` for type `S`:
   --> $DIR/conflict-with-std.rs:24:1
diff --git a/src/test/ui/issue-14092.rs b/src/test/ui/issue-14092.rs
index 449de26769ff3..f4cd32611a549 100644
--- a/src/test/ui/issue-14092.rs
+++ b/src/test/ui/issue-14092.rs
@@ -9,6 +9,6 @@
 // except according to those terms.
 
 fn fn1(0: Box) {}
-        //~^ ERROR wrong number of type arguments: expected 1, found 0 [E0243]
+        //~^ ERROR wrong number of type arguments: expected at least 1, found 0 [E0243]
 
 fn main() {}
diff --git a/src/test/ui/issue-14092.stderr b/src/test/ui/issue-14092.stderr
index f90ea4776ab7c..c1d2ca1af1d6a 100644
--- a/src/test/ui/issue-14092.stderr
+++ b/src/test/ui/issue-14092.stderr
@@ -1,8 +1,8 @@
-error[E0243]: wrong number of type arguments: expected 1, found 0
+error[E0243]: wrong number of type arguments: expected at least 1, found 0
   --> $DIR/issue-14092.rs:11:11
    |
 LL | fn fn1(0: Box) {}
-   |           ^^^ expected 1 type argument
+   |           ^^^ expected at least 1 type argument
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/issue-41974.stderr b/src/test/ui/issue-41974.stderr
index eca40ed43557d..ae32be16befe0 100644
--- a/src/test/ui/issue-41974.stderr
+++ b/src/test/ui/issue-41974.stderr
@@ -1,13 +1,13 @@
-error[E0119]: conflicting implementations of trait `std::ops::Drop` for type `std::boxed::Box<_>`:
+error[E0119]: conflicting implementations of trait `std::ops::Drop` for type `std::boxed::Box<_, _>`:
   --> $DIR/issue-41974.rs:17:1
    |
 LL | impl<T> Drop for T where T: A { //~ ERROR E0119
    | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
    = note: conflicting implementation in crate `alloc`:
-           - impl<T> std::ops::Drop for std::boxed::Box<T>
-             where T: ?Sized;
-   = note: downstream crates may implement trait `A` for type `std::boxed::Box<_>`
+           - impl<T, A> std::ops::Drop for std::boxed::Box<T, A>
+             where A: std::alloc::Alloc, T: ?Sized;
+   = note: downstream crates may implement trait `A` for type `std::boxed::Box<_, _>`
 
 error[E0120]: the Drop trait may only be implemented on structures
   --> $DIR/issue-41974.rs:17:18
diff --git a/src/test/ui/nll/ty-outlives/projection-no-regions-closure.stderr b/src/test/ui/nll/ty-outlives/projection-no-regions-closure.stderr
index e07051135779a..022970d3b9cbe 100644
--- a/src/test/ui/nll/ty-outlives/projection-no-regions-closure.stderr
+++ b/src/test/ui/nll/ty-outlives/projection-no-regions-closure.stderr
@@ -20,7 +20,7 @@ LL |     with_signature(x, |mut y| Box::new(y.next()))
                '_#1r,
                T,
                i32,
-               extern "rust-call" fn((std::boxed::Box<T>,)) -> std::boxed::Box<(dyn Anything + '_#2r)>
+               extern "rust-call" fn((std::boxed::Box<T, std::alloc::Global>,)) -> std::boxed::Box<(dyn Anything + '_#2r), std::alloc::Global>
            ]
    = note: number of external vids: 3
    = note: where <T as std::iter::Iterator>::Item: '_#2r
@@ -60,7 +60,7 @@ LL |     with_signature(x, |mut y| Box::new(y.next()))
                '_#1r,
                T,
                i32,
-               extern "rust-call" fn((std::boxed::Box<T>,)) -> std::boxed::Box<(dyn Anything + '_#2r)>
+               extern "rust-call" fn((std::boxed::Box<T, std::alloc::Global>,)) -> std::boxed::Box<(dyn Anything + '_#2r), std::alloc::Global>
            ]
    = note: number of external vids: 3
    = note: where <T as std::iter::Iterator>::Item: '_#2r
@@ -92,7 +92,7 @@ LL |     with_signature(x, |mut y| Box::new(y.next()))
                '_#2r,
                T,
                i32,
-               extern "rust-call" fn((std::boxed::Box<T>,)) -> std::boxed::Box<(dyn Anything + '_#3r)>
+               extern "rust-call" fn((std::boxed::Box<T, std::alloc::Global>,)) -> std::boxed::Box<(dyn Anything + '_#3r), std::alloc::Global>
            ]
    = note: number of external vids: 4
    = note: where <T as std::iter::Iterator>::Item: '_#3r
@@ -134,7 +134,7 @@ LL |     with_signature(x, |mut y| Box::new(y.next()))
                '_#2r,
                T,
                i32,
-               extern "rust-call" fn((std::boxed::Box<T>,)) -> std::boxed::Box<(dyn Anything + '_#3r)>
+               extern "rust-call" fn((std::boxed::Box<T, std::alloc::Global>,)) -> std::boxed::Box<(dyn Anything + '_#3r), std::alloc::Global>
            ]
    = note: number of external vids: 4
    = note: where <T as std::iter::Iterator>::Item: '_#3r
diff --git a/src/test/ui/nll/ty-outlives/ty-param-closure-outlives-from-return-type.stderr b/src/test/ui/nll/ty-outlives/ty-param-closure-outlives-from-return-type.stderr
index 39ad96cc6cd8e..29e3db8336d20 100644
--- a/src/test/ui/nll/ty-outlives/ty-param-closure-outlives-from-return-type.stderr
+++ b/src/test/ui/nll/ty-outlives/ty-param-closure-outlives-from-return-type.stderr
@@ -20,7 +20,7 @@ LL |     with_signature(x, |y| y)
                '_#1r,
                T,
                i32,
-               extern "rust-call" fn((std::boxed::Box<T>,)) -> std::boxed::Box<(dyn std::fmt::Debug + '_#2r)>
+               extern "rust-call" fn((std::boxed::Box<T, std::alloc::Global>,)) -> std::boxed::Box<(dyn std::fmt::Debug + '_#2r), std::alloc::Global>
            ]
    = note: number of external vids: 3
    = note: where T: '_#2r