Implement P0084r2. Changing emplace return types.

llvm-svn: 276230
Cr-Mirrored-From: sso://chromium.googlesource.com/_direct/external/github.com/llvm/llvm-project
Cr-Mirrored-Commit: 0e411641a338b0effbdcbcd6f0772a0663729afd
diff --git a/include/deque b/include/deque
index 5765042..4c68813 100644
--- a/include/deque
+++ b/include/deque
@@ -110,8 +110,8 @@
     void push_front(value_type&& v);
     void push_back(const value_type& v);
     void push_back(value_type&& v);
-    template <class... Args> void emplace_front(Args&&... args);
-    template <class... Args> void emplace_back(Args&&... args);
+    template <class... Args> reference emplace_front(Args&&... args);
+    template <class... Args> reference emplace_back(Args&&... args);
     template <class... Args> iterator emplace(const_iterator p, Args&&... args);
     iterator insert(const_iterator p, const value_type& v);
     iterator insert(const_iterator p, value_type&& v);
@@ -1344,8 +1344,8 @@
     void push_back(const value_type& __v);
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 #ifndef _LIBCPP_HAS_NO_VARIADICS
-    template <class... _Args> void emplace_front(_Args&&... __args);
-    template <class... _Args> void emplace_back(_Args&&... __args);
+    template <class... _Args> reference emplace_front(_Args&&... __args);
+    template <class... _Args> reference emplace_back(_Args&&... __args);
     template <class... _Args> iterator emplace(const_iterator __p, _Args&&... __args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
     void push_front(value_type&& __v);
@@ -1824,15 +1824,17 @@
 
 template <class _Tp, class _Allocator>
 template <class... _Args>
-void
+typename deque<_Tp, _Allocator>::reference
 deque<_Tp, _Allocator>::emplace_back(_Args&&... __args)
 {
     allocator_type& __a = __base::__alloc();
     if (__back_spare() == 0)
         __add_back_capacity();
     // __back_spare() >= 1
-    __alloc_traits::construct(__a, _VSTD::addressof(*__base::end()), _VSTD::forward<_Args>(__args)...);
+    __alloc_traits::construct(__a, _VSTD::addressof(*__base::end()),
+                              _VSTD::forward<_Args>(__args)...);
     ++__base::size();
+    return *--__base::end();
 }
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
@@ -1870,7 +1872,7 @@
 
 template <class _Tp, class _Allocator>
 template <class... _Args>
-void
+typename deque<_Tp, _Allocator>::reference
 deque<_Tp, _Allocator>::emplace_front(_Args&&... __args)
 {
     allocator_type& __a = __base::__alloc();
@@ -1880,6 +1882,7 @@
     __alloc_traits::construct(__a, _VSTD::addressof(*--__base::begin()), _VSTD::forward<_Args>(__args)...);
     --__base::__start_;
     ++__base::size();
+    return *__base::begin();
 }
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
diff --git a/include/forward_list b/include/forward_list
index 18b300d..41b4b46 100644
--- a/include/forward_list
+++ b/include/forward_list
@@ -87,7 +87,7 @@
     reference       front();
     const_reference front() const;
 
-    template <class... Args> void emplace_front(Args&&... args);
+    template <class... Args> reference emplace_front(Args&&... args);
     void push_front(const value_type& v);
     void push_front(value_type&& v);
 
@@ -744,7 +744,7 @@
 
 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
 #ifndef _LIBCPP_HAS_NO_VARIADICS
-    template <class... _Args> void emplace_front(_Args&&... __args);
+    template <class... _Args> reference emplace_front(_Args&&... __args);
 #endif
     void push_front(value_type&& __v);
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
@@ -1099,7 +1099,7 @@
 
 template <class _Tp, class _Alloc>
 template <class... _Args>
-void
+typename forward_list<_Tp, _Alloc>::reference
 forward_list<_Tp, _Alloc>::emplace_front(_Args&&... __args)
 {
     __node_allocator& __a = base::__alloc();
@@ -1109,6 +1109,7 @@
                                   _VSTD::forward<_Args>(__args)...);
     __h->__next_ = base::__before_begin()->__next_;
     base::__before_begin()->__next_ = __h.release();
+    return base::__before_begin()->__next_->__value_;
 }
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
diff --git a/include/list b/include/list
index cff0a85..95a0bee 100644
--- a/include/list
+++ b/include/list
@@ -93,10 +93,10 @@
     size_type max_size() const noexcept;
 
     template <class... Args>
-        void emplace_front(Args&&... args);
+        reference emplace_front(Args&&... args);
     void pop_front();
     template <class... Args>
-        void emplace_back(Args&&... args);
+        reference emplace_back(Args&&... args);
     void pop_back();
     void push_front(const value_type& x);
     void push_front(value_type&& x);
@@ -968,9 +968,9 @@
     void push_back(value_type&& __x);
 #ifndef _LIBCPP_HAS_NO_VARIADICS
     template <class... _Args>
-       void emplace_front(_Args&&... __args);
+       reference emplace_front(_Args&&... __args);
     template <class... _Args>
-        void emplace_back(_Args&&... __args);
+        reference emplace_back(_Args&&... __args);
     template <class... _Args>
         iterator emplace(const_iterator __p, _Args&&... __args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
@@ -1593,7 +1593,7 @@
 
 template <class _Tp, class _Alloc>
 template <class... _Args>
-void
+typename list<_Tp, _Alloc>::reference
 list<_Tp, _Alloc>::emplace_front(_Args&&... __args)
 {
     __node_allocator& __na = base::__node_alloc();
@@ -1602,12 +1602,12 @@
     __node_alloc_traits::construct(__na, _VSTD::addressof(__hold->__value_), _VSTD::forward<_Args>(__args)...);
     __link_nodes_at_front(__hold.get()->__as_link(), __hold.get()->__as_link());
     ++base::__sz();
-    __hold.release();
+    return __hold.release()->__value_;
 }
 
 template <class _Tp, class _Alloc>
 template <class... _Args>
-void
+typename list<_Tp, _Alloc>::reference
 list<_Tp, _Alloc>::emplace_back(_Args&&... __args)
 {
     __node_allocator& __na = base::__node_alloc();
@@ -1617,7 +1617,7 @@
     __link_pointer __nl = __hold->__as_link();
     __link_nodes_at_back(__nl, __nl);
     ++base::__sz();
-    __hold.release();
+    return __hold.release()->__value_;
 }
 
 template <class _Tp, class _Alloc>
diff --git a/include/queue b/include/queue
index c657b52..01247a2 100644
--- a/include/queue
+++ b/include/queue
@@ -63,7 +63,7 @@
 
     void push(const value_type& v);
     void push(value_type&& v);
-    template <class... Args> void emplace(Args&&... args);
+    template <class... Args> reference emplace(Args&&... args);
     void pop();
 
     void swap(queue& q) noexcept(is_nothrow_swappable_v<Container>)
@@ -292,8 +292,8 @@
 #ifndef _LIBCPP_HAS_NO_VARIADICS
     template <class... _Args>
         _LIBCPP_INLINE_VISIBILITY
-        void emplace(_Args&&... __args)
-            {c.emplace_back(_VSTD::forward<_Args>(__args)...);}
+        reference emplace(_Args&&... __args)
+            { return c.emplace_back(_VSTD::forward<_Args>(__args)...);}
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
diff --git a/include/stack b/include/stack
index 48b3b0d..ee3fac8 100644
--- a/include/stack
+++ b/include/stack
@@ -55,7 +55,7 @@
 
     void push(const value_type& x);
     void push(value_type&& x);
-    template <class... Args> void emplace(Args&&... args);
+    template <class... Args> reference emplace(Args&&... args);
     void pop();
 
     void swap(stack& c) noexcept(is_nothrow_swappable_v<Container>)
@@ -199,8 +199,8 @@
 #ifndef _LIBCPP_HAS_NO_VARIADICS
     template <class... _Args>
         _LIBCPP_INLINE_VISIBILITY
-        void emplace(_Args&&... __args)
-        {c.emplace_back(_VSTD::forward<_Args>(__args)...);}
+        reference emplace(_Args&&... __args)
+        { return c.emplace_back(_VSTD::forward<_Args>(__args)...);}
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
diff --git a/include/vector b/include/vector
index 021bbfb..16d48ae 100644
--- a/include/vector
+++ b/include/vector
@@ -99,7 +99,7 @@
     void push_back(const value_type& x);
     void push_back(value_type&& x);
     template <class... Args>
-        void emplace_back(Args&&... args);
+        reference emplace_back(Args&&... args);
     void pop_back();
 
     template <class... Args> iterator emplace(const_iterator position, Args&&... args);
@@ -218,7 +218,7 @@
     const_reference back() const;
 
     void push_back(const value_type& x);
-    template <class... Args> void emplace_back(Args&&... args);  // C++14
+    template <class... Args> reference emplace_back(Args&&... args);  // C++14
     void pop_back();
 
     template <class... Args> iterator emplace(const_iterator position, Args&&... args);  // C++14
@@ -687,7 +687,7 @@
 #ifndef _LIBCPP_HAS_NO_VARIADICS
     template <class... _Args>
         _LIBCPP_INLINE_VISIBILITY
-        void emplace_back(_Args&&... __args);
+        reference emplace_back(_Args&&... __args);
 #endif  // _LIBCPP_HAS_NO_VARIADICS
 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
     _LIBCPP_INLINE_VISIBILITY
@@ -1632,7 +1632,7 @@
 template <class _Tp, class _Allocator>
 template <class... _Args>
 inline
-void
+typename vector<_Tp, _Allocator>::reference
 vector<_Tp, _Allocator>::emplace_back(_Args&&... __args)
 {
     if (this->__end_ < this->__end_cap())
@@ -1646,6 +1646,7 @@
     }
     else
         __emplace_back_slow_path(_VSTD::forward<_Args>(__args)...);
+    return this->back();
 }
 
 #endif  // _LIBCPP_HAS_NO_VARIADICS
@@ -2314,8 +2315,10 @@
     void push_back(const value_type& __x);
 #if _LIBCPP_STD_VER > 11
     template <class... _Args>
-    _LIBCPP_INLINE_VISIBILITY void emplace_back(_Args&&... __args)
-        { push_back ( value_type ( _VSTD::forward<_Args>(__args)... )); }
+    _LIBCPP_INLINE_VISIBILITY reference emplace_back(_Args&&... __args) {
+        push_back ( value_type ( _VSTD::forward<_Args>(__args)... ));
+        return this->back();
+    }
 #endif
 
     _LIBCPP_INLINE_VISIBILITY void pop_back() {--__size_;}
diff --git a/test/std/containers/container.adaptors/queue/queue.defn/emplace.pass.cpp b/test/std/containers/container.adaptors/queue/queue.defn/emplace.pass.cpp
index 1d9c08b..77d822a 100644
--- a/test/std/containers/container.adaptors/queue/queue.defn/emplace.pass.cpp
+++ b/test/std/containers/container.adaptors/queue/queue.defn/emplace.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <queue>
 
-// template <class... Args> void emplace(Args&&... args);
+// template <class... Args> reference emplace(Args&&... args);
 
 #include <queue>
 #include <cassert>
@@ -18,13 +20,17 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    typedef Emplaceable T;
     std::queue<Emplaceable> q;
-    q.emplace(1, 2.5);
-    q.emplace(2, 3.5);
-    q.emplace(3, 4.5);
+    T& r1 = q.emplace(1, 2.5);
+    assert(&r1 == &q.back());
+    T& r2 = q.emplace(2, 3.5);
+    assert(&r2 == &q.back());
+    T& r3 = q.emplace(3, 4.5);
+    assert(&r3 == &q.back());
     assert(q.size() == 3);
     assert(q.front() == Emplaceable(1, 2.5));
     assert(q.back() == Emplaceable(3, 4.5));
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    assert(&r3 == &q.back());
+    assert(&r1 == &q.front());
 }
diff --git a/test/std/containers/container.adaptors/stack/stack.defn/emplace.pass.cpp b/test/std/containers/container.adaptors/stack/stack.defn/emplace.pass.cpp
index 3573c22..71fe903 100644
--- a/test/std/containers/container.adaptors/stack/stack.defn/emplace.pass.cpp
+++ b/test/std/containers/container.adaptors/stack/stack.defn/emplace.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <stack>
 
-// template <class... Args> void emplace(Args&&... args);
+// template <class... Args> reference emplace(Args&&... args);
 
 #include <stack>
 #include <cassert>
@@ -18,12 +20,14 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
+    typedef Emplaceable T;
     std::stack<Emplaceable> q;
-    q.emplace(1, 2.5);
-    q.emplace(2, 3.5);
-    q.emplace(3, 4.5);
+    T& r1 = q.emplace(1, 2.5);
+    assert(&r1 == &q.top());
+    T& r2 = q.emplace(2, 3.5);
+    assert(&r2 == &q.top());
+    T& r3 = q.emplace(3, 4.5);
+    assert(&r3 == &q.top());
     assert(q.size() == 3);
     assert(q.top() == Emplaceable(3, 4.5));
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/deque/deque.modifiers/emplace_back.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/emplace_back.pass.cpp
index 784b3a3..f81cdf9 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/emplace_back.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/emplace_back.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <deque>
 
-// template <class... Args> void emplace_back(Args&&... args);
+// template <class... Args> reference emplace_back(Args&&... args);
 
 #include <deque>
 #include <cassert>
@@ -18,8 +20,6 @@
 #include "min_allocator.h"
 #include "test_allocator.h"
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 template <class C>
 C
 make(int size, int start = 0 )
@@ -47,12 +47,14 @@
 test(C& c1)
 {
     typedef typename C::iterator I;
+    typedef typename C::reference Ref;
     std::size_t c1_osize = c1.size();
-    c1.emplace_back(Emplaceable(1, 2.5));
+    Ref ref = c1.emplace_back(Emplaceable(1, 2.5));
     assert(c1.size() == c1_osize + 1);
     assert(distance(c1.begin(), c1.end()) == c1.size());
     I i = c1.end();
     assert(*--i == Emplaceable(1, 2.5));
+    assert(&(*i) == &ref);
 }
 
 template <class C>
@@ -63,11 +65,8 @@
     test(c1);
 }
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -75,7 +74,6 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<Emplaceable> >(rng[i], rng[j]);
     }
-#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -94,6 +92,4 @@
         c.emplace_front(1, 2, 3);
         assert(c.size() == 4);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/deque/deque.modifiers/emplace_front.pass.cpp b/test/std/containers/sequences/deque/deque.modifiers/emplace_front.pass.cpp
index afc0e49..668062d 100644
--- a/test/std/containers/sequences/deque/deque.modifiers/emplace_front.pass.cpp
+++ b/test/std/containers/sequences/deque/deque.modifiers/emplace_front.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <deque>
 
-// template <class... Args> void emplace_front(Args&&... args);
+// template <class... Args> reference emplace_front(Args&&... args);
 
 #include <deque>
 #include <cassert>
@@ -17,8 +19,6 @@
 #include "../../../Emplaceable.h"
 #include "min_allocator.h"
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 template <class C>
 C
 make(int size, int start = 0 )
@@ -46,12 +46,14 @@
 test(C& c1)
 {
     typedef typename C::iterator I;
+    typedef typename C::reference Ref;
     std::size_t c1_osize = c1.size();
-    c1.emplace_front(Emplaceable(1, 2.5));
+    Ref res_ref = c1.emplace_front(Emplaceable(1, 2.5));
     assert(c1.size() == c1_osize + 1);
     assert(distance(c1.begin(), c1.end()) == c1.size());
     I i = c1.begin();
     assert(*i == Emplaceable(1, 2.5));
+    assert(&res_ref == &(*i));
 }
 
 template <class C>
@@ -62,11 +64,9 @@
     test(c1);
 }
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -74,7 +74,6 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<Emplaceable> >(rng[i], rng[j]);
     }
-#if TEST_STD_VER >= 11
     {
     int rng[] = {0, 1, 2, 3, 1023, 1024, 1025, 2047, 2048, 2049};
     const int N = sizeof(rng)/sizeof(rng[0]);
@@ -82,6 +81,4 @@
         for (int j = 0; j < N; ++j)
             testN<std::deque<Emplaceable, min_allocator<Emplaceable>> >(rng[i], rng[j]);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/forwardlist/forwardlist.modifiers/emplace_front.pass.cpp b/test/std/containers/sequences/forwardlist/forwardlist.modifiers/emplace_front.pass.cpp
index 18ed69d..589e718 100644
--- a/test/std/containers/sequences/forwardlist/forwardlist.modifiers/emplace_front.pass.cpp
+++ b/test/std/containers/sequences/forwardlist/forwardlist.modifiers/emplace_front.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <forward_list>
 
-// template <class... Args> void emplace_front(Args&&... args);
+// template <class... Args> reference emplace_front(Args&&... args);
 
 #include <forward_list>
 #include <cassert>
@@ -19,32 +21,32 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
         typedef Emplaceable T;
         typedef std::forward_list<T> C;
         C c;
-        c.emplace_front();
+        T& r1 = c.emplace_front();
         assert(c.front() == Emplaceable());
+        assert(&r1 == &c.front());
         assert(distance(c.begin(), c.end()) == 1);
-        c.emplace_front(1, 2.5);
+        T& r2 = c.emplace_front(1, 2.5);
         assert(c.front() == Emplaceable(1, 2.5));
+        assert(&r2 == &c.front());
         assert(*next(c.begin()) == Emplaceable());
         assert(distance(c.begin(), c.end()) == 2);
     }
-#if TEST_STD_VER >= 11
     {
         typedef Emplaceable T;
         typedef std::forward_list<T, min_allocator<T>> C;
         C c;
-        c.emplace_front();
+        T& r1 = c.emplace_front();
         assert(c.front() == Emplaceable());
+        assert(&r1 == &c.front());
         assert(distance(c.begin(), c.end()) == 1);
-        c.emplace_front(1, 2.5);
+        T& r2 = c.emplace_front(1, 2.5);
         assert(c.front() == Emplaceable(1, 2.5));
+        assert(&r2 == &c.front());
         assert(*next(c.begin()) == Emplaceable());
         assert(distance(c.begin(), c.end()) == 2);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/list/list.modifiers/emplace_back.pass.cpp b/test/std/containers/sequences/list/list.modifiers/emplace_back.pass.cpp
index 2ff01f1..2aae2b9 100644
--- a/test/std/containers/sequences/list/list.modifiers/emplace_back.pass.cpp
+++ b/test/std/containers/sequences/list/list.modifiers/emplace_back.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <list>
 
-// template <class... Args> void emplace_back(Args&&... args);
+// template <class... Args> reference emplace_back(Args&&... args);
 
 #include <list>
 #include <cassert>
@@ -33,34 +35,34 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
     std::list<A> c;
-    c.emplace_back(2, 3.5);
+    A& r1 = c.emplace_back(2, 3.5);
     assert(c.size() == 1);
+    assert(&r1 == &c.back());
     assert(c.front().geti() == 2);
     assert(c.front().getd() == 3.5);
-    c.emplace_back(3, 4.5);
+    A& r2 = c.emplace_back(3, 4.5);
     assert(c.size() == 2);
+    assert(&r2 == &c.back());
     assert(c.front().geti() == 2);
     assert(c.front().getd() == 3.5);
     assert(c.back().geti() == 3);
     assert(c.back().getd() == 4.5);
     }
-#if TEST_STD_VER >= 11
     {
     std::list<A, min_allocator<A>> c;
-    c.emplace_back(2, 3.5);
+    A& r1 = c.emplace_back(2, 3.5);
     assert(c.size() == 1);
+    assert(&r1 == &c.back());
     assert(c.front().geti() == 2);
     assert(c.front().getd() == 3.5);
-    c.emplace_back(3, 4.5);
+    A& r2 = c.emplace_back(3, 4.5);
     assert(c.size() == 2);
+    assert(&r2 == &c.back());
     assert(c.front().geti() == 2);
     assert(c.front().getd() == 3.5);
     assert(c.back().geti() == 3);
     assert(c.back().getd() == 4.5);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/list/list.modifiers/emplace_front.pass.cpp b/test/std/containers/sequences/list/list.modifiers/emplace_front.pass.cpp
index 8a3df46..994dac2 100644
--- a/test/std/containers/sequences/list/list.modifiers/emplace_front.pass.cpp
+++ b/test/std/containers/sequences/list/list.modifiers/emplace_front.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <list>
 
-// template <class... Args> void emplace_front(Args&&... args);
+// template <class... Args> reference emplace_front(Args&&... args);
 
 #include <list>
 #include <cassert>
@@ -33,34 +35,34 @@
 
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
     std::list<A> c;
-    c.emplace_front(2, 3.5);
+    A& r1 = c.emplace_front(2, 3.5);
     assert(c.size() == 1);
+    assert(&r1 == &c.front());
     assert(c.front().geti() == 2);
     assert(c.front().getd() == 3.5);
-    c.emplace_front(3, 4.5);
+    A& r2 = c.emplace_front(3, 4.5);
     assert(c.size() == 2);
+    assert(&r2 == &c.front());
     assert(c.front().geti() == 3);
     assert(c.front().getd() == 4.5);
     assert(c.back().geti() == 2);
     assert(c.back().getd() == 3.5);
     }
-#if TEST_STD_VER >= 11
     {
     std::list<A, min_allocator<A>> c;
-    c.emplace_front(2, 3.5);
+    A& r1 = c.emplace_front(2, 3.5);
     assert(c.size() == 1);
+    assert(&r1 == &c.front());
     assert(c.front().geti() == 2);
     assert(c.front().getd() == 3.5);
-    c.emplace_front(3, 4.5);
+    A& r2 = c.emplace_front(3, 4.5);
     assert(c.size() == 2);
+    assert(&r2 == &c.front());
     assert(c.front().geti() == 3);
     assert(c.front().getd() == 4.5);
     assert(c.back().geti() == 2);
     assert(c.back().getd() == 3.5);
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/test/std/containers/sequences/vector.bool/emplace_back.pass.cpp b/test/std/containers/sequences/vector.bool/emplace_back.pass.cpp
index 2950ee3..24005be 100644
--- a/test/std/containers/sequences/vector.bool/emplace_back.pass.cpp
+++ b/test/std/containers/sequences/vector.bool/emplace_back.pass.cpp
@@ -11,42 +11,57 @@
 // <vector>
 //  vector.bool
 
-// template <class... Args> void emplace_back(Args&&... args);
+// template <class... Args> reference emplace_back(Args&&... args);
 
 #include <vector>
 #include <cassert>
 #include "min_allocator.h"
 
-
 int main()
 {
     {
         typedef std::vector<bool> C;
+        typedef C::reference Ref;
         C c;
-        c.emplace_back();
+        Ref r1 = c.emplace_back();
         assert(c.size() == 1);
         assert(c.front() == false);
-        c.emplace_back(true);
+        r1 = true;
+        assert(c.front() == true);
+        r1 = false;
+        Ref r2 = c.emplace_back(true);
         assert(c.size() == 2);
         assert(c.front() == false);
         assert(c.back() == true);
-        c.emplace_back(1 == 1);
+        r2 = false;
+        assert(c.back() == false);
+        r2 = true;
+        Ref r3 = c.emplace_back(1 == 1);
         assert(c.size() == 3);
         assert(c.front() == false);
         assert(c[1] == true);
         assert(c.back() == true);
+        r3 = false;
+        assert(c.back() == false);
     }
     {
         typedef std::vector<bool, min_allocator<bool>> C;
+        typedef C::reference Ref;
         C c;
 
-        c.emplace_back();
+        Ref r1 = c.emplace_back();
         assert(c.size() == 1);
         assert(c.front() == false);
-        c.emplace_back(true);
+        r1 = true;
+        assert(c.front() == true);
+        r1 = false;
+        Ref r2 = c.emplace_back(true);
         assert(c.size() == 2);
         assert(c.front() == false);
         assert(c.back() == true);
+        r2 = false;
+        assert(c.back() == false);
+        r2 = true;
         c.emplace_back(1 == 1);
         assert(c.size() == 3);
         assert(c.front() == false);
diff --git a/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp b/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp
index 61ccade..6b43548 100644
--- a/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp
+++ b/test/std/containers/sequences/vector/vector.modifiers/emplace_back.pass.cpp
@@ -7,9 +7,11 @@
 //
 //===----------------------------------------------------------------------===//
 
+// UNSUPPORTED: c++98, c++03
+
 // <vector>
 
-// template <class... Args> void emplace_back(Args&&... args);
+// template <class... Args> reference emplace_back(Args&&... args);
 
 #include <vector>
 #include <cassert>
@@ -18,8 +20,6 @@
 #include "test_allocator.h"
 #include "asan_testing.h"
 
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 class A
 {
     int i_;
@@ -52,20 +52,19 @@
     double getd() const {return d_;}
 };
 
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
-
 int main()
 {
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
     {
         std::vector<A> c;
-        c.emplace_back(2, 3.5);
+        A& r1 = c.emplace_back(2, 3.5);
         assert(c.size() == 1);
+        assert(&r1 == &c.back());
         assert(c.front().geti() == 2);
         assert(c.front().getd() == 3.5);
         assert(is_contiguous_container_asan_correct(c));
-        c.emplace_back(3, 4.5);
+        A& r2 = c.emplace_back(3, 4.5);
         assert(c.size() == 2);
+        assert(&r2 == &c.back());
         assert(c.front().geti() == 2);
         assert(c.front().getd() == 3.5);
         assert(c.back().geti() == 3);
@@ -74,29 +73,32 @@
     }
     {
         std::vector<A, stack_allocator<A, 4> > c;
-        c.emplace_back(2, 3.5);
+        A& r1 = c.emplace_back(2, 3.5);
         assert(c.size() == 1);
+        assert(&r1 == &c.back());
         assert(c.front().geti() == 2);
         assert(c.front().getd() == 3.5);
         assert(is_contiguous_container_asan_correct(c));
-        c.emplace_back(3, 4.5);
+        A& r2 = c.emplace_back(3, 4.5);
         assert(c.size() == 2);
+        assert(&r2 == &c.back());
         assert(c.front().geti() == 2);
         assert(c.front().getd() == 3.5);
         assert(c.back().geti() == 3);
         assert(c.back().getd() == 4.5);
         assert(is_contiguous_container_asan_correct(c));
     }
-#if TEST_STD_VER >= 11
     {
         std::vector<A, min_allocator<A>> c;
-        c.emplace_back(2, 3.5);
+        A& r1 = c.emplace_back(2, 3.5);
         assert(c.size() == 1);
+        assert(&r1 == &c.back());
         assert(c.front().geti() == 2);
         assert(c.front().getd() == 3.5);
         assert(is_contiguous_container_asan_correct(c));
-        c.emplace_back(3, 4.5);
+        A& r2 = c.emplace_back(3, 4.5);
         assert(c.size() == 2);
+        assert(&r2 == &c.back());
         assert(c.front().geti() == 2);
         assert(c.front().getd() == 3.5);
         assert(c.back().geti() == 3);
@@ -111,6 +113,4 @@
         assert(c.size() == 2);
         assert(is_contiguous_container_asan_correct(c));
     }
-#endif
-#endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
 }
diff --git a/www/cxx1z_status.html b/www/cxx1z_status.html
index dc6587a..18ed245 100644
--- a/www/cxx1z_status.html
+++ b/www/cxx1z_status.html
@@ -99,7 +99,7 @@
 	<tr><td><a href="http://wg21.link/p0063r3">p0063r3</a></td><td>LWG</td><td>C++17 should refer to C11 instead of C99</td><td>Oulu</td><td></td><td></td></tr>
 	<tr><td><a href="http://wg21.link/p0067r3">p0067r3</a></td><td>LWG</td><td>Elementary string conversions</td><td>Oulu</td><td>Postponed to Issaquah</td><td></td></tr>
 	<tr><td><a href="http://wg21.link/p0083r3">p0083r3</a></td><td>LWG</td><td>Splicing Maps and Sets</td><td>Oulu</td><td></td><td></td></tr>
-	<tr><td><a href="http://wg21.link/p0084r2">p0084r2</a></td><td>LWG</td><td>Emplace Return Type</td><td>Oulu</td><td></td><td></td></tr>
+	<tr><td><a href="http://wg21.link/p0084r2">p0084r2</a></td><td>LWG</td><td>Emplace Return Type</td><td>Oulu</td><td>Complete</td><td>4.0</td></tr>
 	<tr><td><a href="http://wg21.link/p0088r3">p0088r3</a></td><td>LWG</td><td>Variant: a type-safe union for C++17</td><td>Oulu</td><td></td><td></td></tr>
 	<tr><td><a href="http://wg21.link/p0163r0">p0163r0</a></td><td>LWG</td><td>shared_ptr::weak_type</td><td>Oulu</td><td>Complete</td><td>3.9</td></tr>
 	<tr><td><a href="http://wg21.link/p0174r2">p0174r2</a></td><td>LWG</td><td>Deprecating Vestigial Library Parts in C++17</td><td>Oulu</td><td></td><td></td></tr>