[futures.atomic_future] and notify_all_at_thread_exit.  This completes the header <future> and all of Chapter 30 (for C++0x enabled compilers).

git-svn-id: https://llvm.org/svn/llvm-project/libcxx/trunk@113017 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/src/condition_variable.cpp b/src/condition_variable.cpp
index 7373ec3..3bafa8c 100644
--- a/src/condition_variable.cpp
+++ b/src/condition_variable.cpp
@@ -61,4 +61,10 @@
         __throw_system_error(ec, "condition_variable timed_wait failed");
 }
 
+void
+notify_all_at_thread_exit(condition_variable& cond, unique_lock<mutex> lk)
+{
+    __thread_local_data->notify_all_at_thread_exit(&cond, lk.release());
+}
+
 _LIBCPP_END_NAMESPACE_STD
diff --git a/src/future.cpp b/src/future.cpp
index 924a684..ca30803 100644
--- a/src/future.cpp
+++ b/src/future.cpp
@@ -257,4 +257,39 @@
     return *this;
 }
 
+atomic_future<void>::~atomic_future()
+{
+    if (__state_)
+        __state_->__release_shared();
+}
+
+atomic_future<void>&
+atomic_future<void>::operator=(const atomic_future& __rhs)
+{
+    if (this != &__rhs)
+    {
+        unique_lock<mutex> __this(__mut_, defer_lock);
+        unique_lock<mutex> __that(__rhs.__mut_, defer_lock);
+        _STD::lock(__this, __that);
+        if (__rhs.__state_)
+            __rhs.__state_->__add_shared();
+        if (__state_)
+            __state_->__release_shared();
+        __state_ = __rhs.__state_;
+    }
+    return *this;
+}
+
+void
+atomic_future<void>::swap(atomic_future& __rhs)
+{
+    if (this != &__rhs)
+    {
+        unique_lock<mutex> __this(__mut_, defer_lock);
+        unique_lock<mutex> __that(__rhs.__mut_, defer_lock);
+        _STD::lock(__this, __that);
+        _STD::swap(__state_, __rhs.__state_);
+    }
+}
+
 _LIBCPP_END_NAMESPACE_STD
diff --git a/src/thread.cpp b/src/thread.cpp
index f840706..3d388e9 100644
--- a/src/thread.cpp
+++ b/src/thread.cpp
@@ -90,7 +90,10 @@
 class __thread_struct_imp
 {
     typedef vector<__assoc_sub_state*> _AsyncStates;
+    typedef vector<pair<condition_variable*, mutex*> > _Notify;
+
     _AsyncStates async_states_;
+    _Notify notify_;
 
     __thread_struct_imp(const __thread_struct_imp&);
     __thread_struct_imp& operator=(const __thread_struct_imp&);
@@ -98,11 +101,18 @@
     __thread_struct_imp() {}
     ~__thread_struct_imp();
 
+    void notify_all_at_thread_exit(condition_variable* cv, mutex* m);
     void __make_ready_at_thread_exit(__assoc_sub_state* __s);
 };
 
 __thread_struct_imp::~__thread_struct_imp()
 {
+    for (_Notify::iterator i = notify_.begin(), e = notify_.end();
+            i != e; ++i)
+    {
+        i->second->unlock();
+        i->first->notify_all();
+    }
     for (_AsyncStates::iterator i = async_states_.begin(), e = async_states_.end();
             i != e; ++i)
     {
@@ -112,6 +122,12 @@
 }
 
 void
+__thread_struct_imp::notify_all_at_thread_exit(condition_variable* cv, mutex* m)
+{
+    notify_.push_back(pair<condition_variable*, mutex*>(cv, m));
+}
+
+void
 __thread_struct_imp::__make_ready_at_thread_exit(__assoc_sub_state* __s)
 {
     async_states_.push_back(__s);
@@ -131,6 +147,12 @@
 }
 
 void
+__thread_struct::notify_all_at_thread_exit(condition_variable* cv, mutex* m)
+{
+    __p_->notify_all_at_thread_exit(cv, m);
+}
+
+void
 __thread_struct::__make_ready_at_thread_exit(__assoc_sub_state* __s)
 {
     __p_->__make_ready_at_thread_exit(__s);