$include_dir="/home/hyper-archives/boost-commit/include"; include("$include_dir/msg-header.inc") ?>
From: anthony_at_[hidden]
Date: 2007-10-24 11:39:15
Author: anthonyw
Date: 2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
New Revision: 40424
URL: http://svn.boost.org/trac/boost/changeset/40424
Log:
updated pthreads code to support move and multiple joins
Text files modified: 
   trunk/boost/thread/pthread/condition_variable.hpp |     5                                         
   trunk/boost/thread/pthread/thread.hpp             |   199 ++++++++++++++++-                       
   trunk/boost/thread/win32/thread.hpp               |     8                                         
   trunk/libs/thread/src/pthread/thread.cpp          |   444 +++++++++++++++++++++++++-------------- 
   trunk/libs/thread/src/pthread/tss.cpp             |    59 -----                                   
   trunk/libs/thread/src/win32/thread.cpp            |     6                                         
   6 files changed, 474 insertions(+), 247 deletions(-)
Modified: trunk/boost/thread/pthread/condition_variable.hpp
==============================================================================
--- trunk/boost/thread/pthread/condition_variable.hpp	(original)
+++ trunk/boost/thread/pthread/condition_variable.hpp	2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
@@ -1,5 +1,5 @@
-#ifndef BOOST_THREAD_CONDITION_VARIABLE_WIN32_HPP
-#define BOOST_THREAD_CONDITION_VARIABLE_WIN32_HPP
+#ifndef BOOST_THREAD_CONDITION_VARIABLE_PTHREAD_HPP
+#define BOOST_THREAD_CONDITION_VARIABLE_PTHREAD_HPP
 // Distributed under the Boost Software License, Version 1.0. (See
 // accompanying file LICENSE_1_0.txt or copy at
 // http://www.boost.org/LICENSE_1_0.txt)
@@ -9,7 +9,6 @@
 #include <limits.h>
 #include <boost/assert.hpp>
 #include <algorithm>
-#include <boost/thread/thread.hpp>
 #include <boost/thread/thread_time.hpp>
 #include <pthread.h>
 #include "timespec.hpp"
Modified: trunk/boost/thread/pthread/thread.hpp
==============================================================================
--- trunk/boost/thread/pthread/thread.hpp	(original)
+++ trunk/boost/thread/pthread/thread.hpp	2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
@@ -1,3 +1,5 @@
+#ifndef BOOST_THREAD_THREAD_PTHREAD_HPP
+#define BOOST_THREAD_THREAD_PTHREAD_HPP
 // Copyright (C) 2001-2003
 // William E. Kempf
 // Copyright (C) 2007 Anthony Williams
@@ -5,21 +7,22 @@
 //  Distributed under the Boost Software License, Version 1.0. (See accompanying 
 //  file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
 
-#ifndef BOOST_THREAD_WEK070601_HPP
-#define BOOST_THREAD_WEK070601_HPP
-
 #include <boost/thread/detail/config.hpp>
 
 #include <boost/utility.hpp>
 #include <boost/function.hpp>
 #include <boost/thread/mutex.hpp>
+#include <boost/thread/condition_variable.hpp>
 #include <list>
 #include <memory>
 
 #include <pthread.h>
 #include <boost/optional.hpp>
+#include <boost/thread/detail/move.hpp>
+#include <boost/shared_ptr.hpp>
 
-namespace boost {
+namespace boost
+{
 
     class thread;
 
@@ -78,40 +81,198 @@
         };
     }
 
+    class thread_cancelled
+    {};
+
+    namespace detail
+    {
+        struct thread_exit_callback_node;
+        
+        struct thread_data_base
+        {
+            boost::shared_ptr<thread_data_base> self;
+            pthread_t thread_handle;
+            boost::mutex done_mutex;
+            boost::condition_variable done_condition;
+            bool done;
+            bool join_started;
+            bool joined;
+            boost::detail::thread_exit_callback_node* thread_exit_callbacks;
+            bool cancel_enabled;
+
+            thread_data_base():
+                done(false),join_started(false),joined(false),
+                thread_exit_callbacks(0),
+                cancel_enabled(true)
+            {}
+            virtual ~thread_data_base()
+            {}
+
+            virtual void run()=0;
+        };
+    }
+
     struct xtime;
-    class BOOST_THREAD_DECL thread : private noncopyable
+    class BOOST_THREAD_DECL thread
     {
+    private:
+        thread(thread&);
+        thread& operator=(thread&);
+
+        template<typename F>
+        struct thread_data:
+            detail::thread_data_base
+        {
+            F f;
+
+            thread_data(F f_):
+                f(f_)
+            {}
+            thread_data(boost::move_t<F> f_):
+                f(f_)
+            {}
+            
+            void run()
+            {
+                f();
+            }
+        };
+        
+        mutable boost::mutex thread_info_mutex;
+        boost::shared_ptr<detail::thread_data_base> thread_info;
+
+        void start_thread();
+        
+        explicit thread(boost::shared_ptr<detail::thread_data_base> data);
+
+        boost::shared_ptr<detail::thread_data_base> get_thread_info() const;
+        
     public:
         thread();
-        explicit thread(const function0<void>& threadfunc);
         ~thread();
+        
+        template <class F>
+        explicit thread(F f):
+            thread_info(new thread_data<F>(f))
+        {
+            start_thread();
+        }
+        template <class F>
+        explicit thread(boost::move_t<F> f):
+            thread_info(new thread_data<F>(f))
+        {
+            start_thread();
+        }
 
-        bool operator==(const thread& other) const;
-        bool operator!=(const thread& other) const;
+        explicit thread(boost::move_t<thread> x);
+        thread& operator=(boost::move_t<thread> x);
+        operator boost::move_t<thread>();
+        boost::move_t<thread> move();
 
+        void swap(thread& x);
+
+        typedef detail::thread_id id;
+        
+        id get_id() const;
+
+        bool joinable() const;
         void join();
+        void detach();
 
-        static void sleep(const xtime& xt);
+        static unsigned hardware_concurrency();
+
+        // backwards compatibility
+        bool operator==(const thread& other) const;
+        bool operator!=(const thread& other) const;
+
+        static void sleep(const system_time& xt);
         static void yield();
 
-        typedef detail::thread_id id;
-        
-        id get_id() const
-        {
-            return m_id;
-        }
+        // extensions
+        class cancel_handle;
+        cancel_handle get_cancel_handle() const;
+        void cancel();
+        bool cancellation_requested() const;
 
-    private:
-        id m_id;
-        bool m_joinable;
+        static thread self();
     };
 
     namespace this_thread
     {
+        class disable_cancellation
+        {
+            disable_cancellation(const disable_cancellation&);
+            disable_cancellation& operator=(const disable_cancellation&);
+            
+            bool cancel_was_enabled;
+            friend class enable_cancellation;
+        public:
+            disable_cancellation();
+            ~disable_cancellation();
+        };
+
+        class enable_cancellation
+        {
+            enable_cancellation(const enable_cancellation&);
+            enable_cancellation& operator=(const enable_cancellation&);
+        public:
+            explicit enable_cancellation(disable_cancellation& d);
+            ~enable_cancellation();
+        };
+
         inline thread::id get_id()
         {
             return thread::id(pthread_self());
         }
+
+        void BOOST_THREAD_DECL cancellation_point();
+        bool BOOST_THREAD_DECL cancellation_enabled();
+        bool BOOST_THREAD_DECL cancellation_requested();
+
+        void BOOST_THREAD_DECL yield();
+        template<typename TimeDuration>
+        void sleep(TimeDuration const& rel_time)
+        {
+            thread::sleep(get_system_time()+rel_time);
+        }
+    }
+
+    namespace detail
+    {
+        struct thread_exit_function_base
+        {
+            virtual ~thread_exit_function_base()
+            {}
+            virtual void operator()() const=0;
+        };
+        
+        template<typename F>
+        struct thread_exit_function:
+            thread_exit_function_base
+        {
+            F f;
+            
+            thread_exit_function(F f_):
+                f(f_)
+            {}
+            
+            void operator()() const
+            {
+                f();
+            }
+        };
+        
+        void add_thread_exit_function(thread_exit_function_base*);
+    }
+    
+    namespace this_thread
+    {
+        template<typename F>
+        void at_thread_exit(F f)
+        {
+            detail::thread_exit_function_base* const thread_exit_func=new detail::thread_exit_function<F>(f);
+            detail::add_thread_exit_function(thread_exit_func);
+        }
     }
 
     class BOOST_THREAD_DECL thread_group : private noncopyable
@@ -133,4 +294,4 @@
 } // namespace boost
 
 
-#endif // BOOST_THREAD_WEK070601_HPP
+#endif
Modified: trunk/boost/thread/win32/thread.hpp
==============================================================================
--- trunk/boost/thread/win32/thread.hpp	(original)
+++ trunk/boost/thread/win32/thread.hpp	2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
@@ -20,7 +20,7 @@
 
 namespace boost
 {
-    class thread_canceled
+    class thread_cancelled
     {};
 
     namespace detail
@@ -105,19 +105,19 @@
         ~thread();
 
         template <class F>
-        thread(F f):
+        explicit thread(F f):
             thread_info(detail::heap_new<thread_data<F> >(f))
         {
             start_thread();
         }
         template <class F>
-        thread(boost::move_t<F> f):
+        explicit thread(boost::move_t<F> f):
             thread_info(detail::heap_new<thread_data<F> >(f))
         {
             start_thread();
         }
 
-        thread(boost::move_t<thread> x);
+        explicit thread(boost::move_t<thread> x);
         thread& operator=(boost::move_t<thread> x);
         operator boost::move_t<thread>();
         boost::move_t<thread> move();
Modified: trunk/libs/thread/src/pthread/thread.cpp
==============================================================================
--- trunk/libs/thread/src/pthread/thread.cpp	(original)
+++ trunk/libs/thread/src/pthread/thread.cpp	2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
@@ -11,213 +11,339 @@
 #include <boost/thread/xtime.hpp>
 #include <boost/thread/condition.hpp>
 #include <boost/thread/locks.hpp>
-#include <cassert>
+#include <boost/thread/once.hpp>
 
 #include "timeconv.inl"
 
-namespace {
-
-class thread_param
+namespace boost
 {
-public:
-    thread_param(const boost::function0<void>& threadfunc)
-        : m_threadfunc(threadfunc), m_started(false)
-    {
-    }
-    void wait()
+    namespace detail
     {
-        boost::mutex::scoped_lock scoped_lock(m_mutex);
-        while (!m_started)
-            m_condition.wait(scoped_lock);
+        struct thread_exit_callback_node
+        {
+            boost::detail::thread_exit_function_base* func;
+            thread_exit_callback_node* next;
+        };
     }
-    void started()
+    namespace
     {
-        boost::mutex::scoped_lock scoped_lock(m_mutex);
-        m_started = true;
-        m_condition.notify_one();
+        boost::once_flag current_thread_tls_init_flag=BOOST_ONCE_INIT;
+        pthread_key_t current_thread_tls_key;
+
+        extern "C"
+        {
+            void tls_destructor(void* data)
+            {
+                boost::detail::thread_data_base* thread_info=static_cast<boost::detail::thread_data_base*>(data);
+                if(thread_info)
+                {
+                    while(thread_info->thread_exit_callbacks)
+                    {
+                        boost::detail::thread_exit_callback_node* const current_node=thread_info->thread_exit_callbacks;
+                        thread_info->thread_exit_callbacks=current_node->next;
+                        if(current_node->func)
+                        {
+                            (*current_node->func)();
+                            delete current_node->func;
+                        }
+                        delete current_node;
+                    }
+                }
+            }
+        }
+    
+
+        void create_current_thread_tls_key()
+        {
+            int const res=pthread_key_create(¤t_thread_tls_key,NULL);
+            BOOST_ASSERT(!res);
+        }
+
+        boost::detail::thread_data_base* get_current_thread_data()
+        {
+            boost::call_once(current_thread_tls_init_flag,create_current_thread_tls_key);
+            return (boost::detail::thread_data_base*)pthread_getspecific(current_thread_tls_key);
+        }
+
+        void set_current_thread_data(detail::thread_data_base* new_data)
+        {
+            boost::call_once(current_thread_tls_init_flag,create_current_thread_tls_key);
+            int const res=pthread_setspecific(current_thread_tls_key,new_data);
+            BOOST_ASSERT(!res);
+        }
+
+
+        extern "C"
+        {
+            void* thread_proxy(void* param)
+            {
+                boost::shared_ptr<boost::detail::thread_data_base> thread_info = static_cast<boost::detail::thread_data_base*>(param)->self;
+                thread_info->self.reset();
+                set_current_thread_data(thread_info.get());
+                try
+                {
+                    thread_info->run();
+                }
+                catch(thread_cancelled const&)
+                {
+                }
+                catch(...)
+                {
+                    std::terminate();
+                }
+
+                tls_destructor(thread_info.get());
+                set_current_thread_data(0);
+                boost::lock_guard<boost::mutex> lock(thread_info->done_mutex);
+                thread_info->done=true;
+                thread_info->done_condition.notify_all();
+                return 0;
+            }
+
+        }
     }
 
-    boost::mutex m_mutex;
-    boost::condition m_condition;
-    const boost::function0<void>& m_threadfunc;
-    bool m_started;
-};
 
-} // unnamed namespace
+    thread::thread()
+    {}
 
-extern "C" {
-        static void* thread_proxy(void* param)
+    void thread::start_thread()
     {
-        thread_param* p = static_cast<thread_param*>(param);
-        boost::function0<void> threadfunc = p->m_threadfunc;
-        p->started();
-        threadfunc();
-        return 0;
+        thread_info->self=thread_info;
+        int const res = pthread_create(&thread_info->thread_handle, 0, &thread_proxy, thread_info.get());
+        if (res != 0)
+        {
+            thread_info->self.reset();
+            throw thread_resource_error();
+        }
     }
 
-}
+    thread::~thread()
+    {
+        detach();
+    }
 
-namespace boost {
+    bool thread::operator==(const thread& other) const
+    {
+        return get_id()==other.get_id();
+    }
 
-thread::thread():
-    m_joinable(false)
-{}
+    bool thread::operator!=(const thread& other) const
+    {
+        return !operator==(other);
+    }
 
-thread::thread(const function0<void>& threadfunc)
-    : m_joinable(true)
-{
-    thread_param param(threadfunc);
-    int res = 0;
-    pthread_t m_thread;
-    res = pthread_create(&m_thread, 0, &thread_proxy, ¶m);
-    if (res != 0)
-        throw thread_resource_error();
-    m_id=m_thread;
-    param.wait();
-}
+    boost::shared_ptr<detail::thread_data_base> thread::get_thread_info() const
+    {
+        lock_guard<mutex> l(thread_info_mutex);
+        return thread_info;
+    }
 
-thread::~thread()
-{
-    if (m_joinable)
+    void thread::join()
     {
-        pthread_detach(*m_id.id);
+        boost::shared_ptr<detail::thread_data_base> const local_thread_info=get_thread_info();
+        if(local_thread_info)
+        {
+            bool do_join=false;
+            
+            {
+                unique_lock<mutex> lock(local_thread_info->done_mutex);
+                while(!local_thread_info->done)
+                {
+                    local_thread_info->done_condition.wait(lock);
+                }
+                do_join=!local_thread_info->join_started;
+                
+                if(do_join)
+                {
+                    local_thread_info->join_started=true;
+                }
+                else
+                {
+                    while(!local_thread_info->joined)
+                    {
+                        local_thread_info->done_condition.wait(lock);
+                    }
+                }
+            }
+            if(do_join)
+            {
+                void* result=0;
+                int const res=pthread_join(local_thread_info->thread_handle,&result);
+                BOOST_ASSERT(!res);
+                lock_guard<mutex> lock(local_thread_info->done_mutex);
+                local_thread_info->joined=true;
+                local_thread_info->done_condition.notify_all();
+            }
+            
+            lock_guard<mutex> l1(thread_info_mutex);
+            if(thread_info==local_thread_info)
+            {
+                thread_info.reset();
+            }
+        }
     }
-}
 
-bool thread::operator==(const thread& other) const
-{
-    return m_id==other.m_id;
-}
+    bool thread::joinable() const
+    {
+        return get_thread_info();
+    }
 
-bool thread::operator!=(const thread& other) const
-{
-    return !operator==(other);
-}
 
-void thread::join()
-{
-    assert(m_joinable); //See race condition comment below
-    int res = 0;
-    res = pthread_join(*m_id.id, 0);
-    assert(res == 0);
-    // This isn't a race condition since any race that could occur would
-    // have us in undefined behavior territory any way.
-    m_joinable = false;
-}
+    void thread::detach()
+    {
+        boost::shared_ptr<detail::thread_data_base> local_thread_info;
+        {
+            lock_guard<mutex> l1(thread_info_mutex);
+            thread_info.swap(local_thread_info);
+        }
+        
+        if(local_thread_info)
+        {
+            lock_guard<mutex> lock(local_thread_info->done_mutex);
+            if(!local_thread_info->join_started)
+            {
+                int const res=pthread_detach(local_thread_info->thread_handle);
+                BOOST_ASSERT(!res);
+                local_thread_info->join_started=true;
+                local_thread_info->joined=true;
+            }
+        }
+    }
 
-void thread::sleep(const xtime& xt)
-{
-    for (int foo=0; foo < 5; ++foo)
+    void thread::sleep(const system_time& st)
     {
+        xtime const xt=get_xtime(st);
+    
+        for (int foo=0; foo < 5; ++foo)
+        {
 #   if defined(BOOST_HAS_PTHREAD_DELAY_NP)
-        timespec ts;
-        to_timespec_duration(xt, ts);
-        int res = 0;
-        res = pthread_delay_np(&ts);
-        assert(res == 0);
+            timespec ts;
+            to_timespec_duration(xt, ts);
+            int res = 0;
+            res = pthread_delay_np(&ts);
+            BOOST_ASSERT(res == 0);
 #   elif defined(BOOST_HAS_NANOSLEEP)
-        timespec ts;
-        to_timespec_duration(xt, ts);
+            timespec ts;
+            to_timespec_duration(xt, ts);
 
-        //  nanosleep takes a timespec that is an offset, not
-        //  an absolute time.
-        nanosleep(&ts, 0);
+            //  nanosleep takes a timespec that is an offset, not
+            //  an absolute time.
+            nanosleep(&ts, 0);
 #   else
-        mutex mx;
-        mutex::scoped_lock lock(mx);
-        condition cond;
-        cond.timed_wait(lock, xt);
+            mutex mx;
+            mutex::scoped_lock lock(mx);
+            condition cond;
+            cond.timed_wait(lock, xt);
 #   endif
-        xtime cur;
-        xtime_get(&cur, TIME_UTC);
-        if (xtime_cmp(xt, cur) <= 0)
-            return;
+            xtime cur;
+            xtime_get(&cur, TIME_UTC);
+            if (xtime_cmp(xt, cur) <= 0)
+                return;
+        }
     }
-}
 
-void thread::yield()
-{
+    void thread::yield()
+    {
 #   if defined(BOOST_HAS_SCHED_YIELD)
-    int res = 0;
-    res = sched_yield();
-    assert(res == 0);
+        int res = 0;
+        res = sched_yield();
+        BOOST_ASSERT(res == 0);
 #   elif defined(BOOST_HAS_PTHREAD_YIELD)
-    int res = 0;
-    res = pthread_yield();
-    assert(res == 0);
+        int res = 0;
+        res = pthread_yield();
+        BOOST_ASSERT(res == 0);
 #   else
-    xtime xt;
-    xtime_get(&xt, TIME_UTC);
-    sleep(xt);
+        xtime xt;
+        xtime_get(&xt, TIME_UTC);
+        sleep(xt);
 #   endif
-}
+    }
 
-thread_group::thread_group()
-{
-}
+    unsigned thread::hardware_concurrency()
+    {
+        return 1;
+    }
 
-thread_group::~thread_group()
-{
-    // We shouldn't have to scoped_lock here, since referencing this object
-    // from another thread while we're deleting it in the current thread is
-    // going to lead to undefined behavior any way.
-    for (std::list<thread*>::iterator it = m_threads.begin();
-         it != m_threads.end(); ++it)
+    thread::id thread::get_id() const
     {
-        delete (*it);
+        boost::shared_ptr<detail::thread_data_base> local_thread_info=get_thread_info();
+        if(local_thread_info)
+        {
+            return id(local_thread_info->thread_handle);
+        }
+        else
+        {
+            return id();
+        }
     }
-}
 
-thread* thread_group::create_thread(const function0<void>& threadfunc)
-{
-    // No scoped_lock required here since the only "shared data" that's
-    // modified here occurs inside add_thread which does scoped_lock.
-    std::auto_ptr<thread> thrd(new thread(threadfunc));
-    add_thread(thrd.get());
-    return thrd.release();
-}
+    thread_group::thread_group()
+    {
+    }
 
-void thread_group::add_thread(thread* thrd)
-{
-    mutex::scoped_lock scoped_lock(m_mutex);
+    thread_group::~thread_group()
+    {
+        // We shouldn't have to scoped_lock here, since referencing this object
+        // from another thread while we're deleting it in the current thread is
+        // going to lead to undefined behavior any way.
+        for (std::list<thread*>::iterator it = m_threads.begin();
+             it != m_threads.end(); ++it)
+        {
+            delete (*it);
+        }
+    }
 
-    // For now we'll simply ignore requests to add a thread object multiple
-    // times. Should we consider this an error and either throw or return an
-    // error value?
-    std::list<thread*>::iterator it = std::find(m_threads.begin(),
-        m_threads.end(), thrd);
-    assert(it == m_threads.end());
-    if (it == m_threads.end())
-        m_threads.push_back(thrd);
-}
+    thread* thread_group::create_thread(const function0<void>& threadfunc)
+    {
+        // No scoped_lock required here since the only "shared data" that's
+        // modified here occurs inside add_thread which does scoped_lock.
+        std::auto_ptr<thread> thrd(new thread(threadfunc));
+        add_thread(thrd.get());
+        return thrd.release();
+    }
 
-void thread_group::remove_thread(thread* thrd)
-{
-    mutex::scoped_lock scoped_lock(m_mutex);
+    void thread_group::add_thread(thread* thrd)
+    {
+        mutex::scoped_lock scoped_lock(m_mutex);
 
-    // For now we'll simply ignore requests to remove a thread object that's
-    // not in the group. Should we consider this an error and either throw or
-    // return an error value?
-    std::list<thread*>::iterator it = std::find(m_threads.begin(),
-        m_threads.end(), thrd);
-    assert(it != m_threads.end());
-    if (it != m_threads.end())
-        m_threads.erase(it);
-}
+        // For now we'll simply ignore requests to add a thread object multiple
+        // times. Should we consider this an error and either throw or return an
+        // error value?
+        std::list<thread*>::iterator it = std::find(m_threads.begin(),
+                                                    m_threads.end(), thrd);
+        BOOST_ASSERT(it == m_threads.end());
+        if (it == m_threads.end())
+            m_threads.push_back(thrd);
+    }
 
-void thread_group::join_all()
-{
-    mutex::scoped_lock scoped_lock(m_mutex);
-    for (std::list<thread*>::iterator it = m_threads.begin();
-         it != m_threads.end(); ++it)
+    void thread_group::remove_thread(thread* thrd)
     {
-        (*it)->join();
+        mutex::scoped_lock scoped_lock(m_mutex);
+
+        // For now we'll simply ignore requests to remove a thread object that's
+        // not in the group. Should we consider this an error and either throw or
+        // return an error value?
+        std::list<thread*>::iterator it = std::find(m_threads.begin(),
+                                                    m_threads.end(), thrd);
+        BOOST_ASSERT(it != m_threads.end());
+        if (it != m_threads.end())
+            m_threads.erase(it);
     }
-}
 
-int thread_group::size() const
-{
+    void thread_group::join_all()
+    {
+        mutex::scoped_lock scoped_lock(m_mutex);
+        for (std::list<thread*>::iterator it = m_threads.begin();
+             it != m_threads.end(); ++it)
+        {
+            (*it)->join();
+        }
+    }
+
+    int thread_group::size() const
+    {
         return m_threads.size();
-}
+    }
 
-} // namespace boost
+}
Modified: trunk/libs/thread/src/pthread/tss.cpp
==============================================================================
--- trunk/libs/thread/src/pthread/tss.cpp	(original)
+++ trunk/libs/thread/src/pthread/tss.cpp	2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
@@ -30,13 +30,7 @@
 boost::once_flag tss_data_once = BOOST_ONCE_INIT;
 boost::mutex* tss_data_mutex = 0;
 tss_data_cleanup_handlers_type* tss_data_cleanup_handlers = 0;
-#if defined(BOOST_HAS_WINTHREADS)
-    DWORD tss_data_native_key=TLS_OUT_OF_INDEXES;
-#elif defined(BOOST_HAS_PTHREADS)
     pthread_key_t tss_data_native_key;
-#elif defined(BOOST_HAS_MPTASKS)
-    TaskStorageIndex tss_data_native_key;
-#endif
 int tss_data_use = 0;
 
 void tss_data_inc_use(boost::mutex::scoped_lock& lk)
@@ -58,15 +52,7 @@
         lk.unlock();
         delete tss_data_mutex;
         tss_data_mutex = 0;
-#if defined(BOOST_HAS_WINTHREADS)
-        TlsFree(tss_data_native_key);
-        tss_data_native_key=TLS_OUT_OF_INDEXES;
-#elif defined(BOOST_HAS_PTHREADS)
         pthread_key_delete(tss_data_native_key);
-#elif defined(BOOST_HAS_MPTASKS)
-        // Don't know what to put here.
-        // But MPTASKS isn't currently maintained anyways...
-#endif
     }
 }
 
@@ -79,9 +65,6 @@
         (*(*tss_data_cleanup_handlers)[i])((*slots)[i]);
         (*slots)[i] = 0;
     }
-#if defined(BOOST_HAS_WINTHREADS)
-    TlsSetValue(tss_data_native_key,0);
-#endif
     tss_data_dec_use(lock);
     delete slots;
 }
@@ -95,23 +78,9 @@
     if (temp_mutex.get() == 0)
         throw boost::thread_resource_error();
 
-#if defined(BOOST_HAS_WINTHREADS)
-    //Force the cleanup implementation library to be linked in
-    tss_cleanup_implemented();
-
-    //Allocate tls slot
-    tss_data_native_key = TlsAlloc();
-    if (tss_data_native_key == TLS_OUT_OF_INDEXES)
-        return;
-#elif defined(BOOST_HAS_PTHREADS)
     int res = pthread_key_create(&tss_data_native_key, &cleanup_slots);
     if (res != 0)
         return;
-#elif defined(BOOST_HAS_MPTASKS)
-    OSStatus status = MPAllocateTaskStorageIndex(&tss_data_native_key);
-    if (status != noErr)
-        return;
-#endif
 
     // The life time of cleanup handlers and mutex is beeing
     // managed by a reference counting technique.
@@ -123,48 +92,20 @@
     tss_data_mutex = temp_mutex.release();
 }
 
-#if defined(BOOST_HAS_WINTHREADS)
-tss_slots* get_slots(bool alloc);
-
-void __cdecl tss_thread_exit()
-{
-    tss_slots* slots = get_slots(false);
-    if (slots)
-        cleanup_slots(slots);
-}
-#endif
 
 tss_slots* get_slots(bool alloc)
 {
     tss_slots* slots = 0;
 
-#if defined(BOOST_HAS_WINTHREADS)
-    slots = static_cast<tss_slots*>(
-        TlsGetValue(tss_data_native_key));
-#elif defined(BOOST_HAS_PTHREADS)
     slots = static_cast<tss_slots*>(
         pthread_getspecific(tss_data_native_key));
-#elif defined(BOOST_HAS_MPTASKS)
-    slots = static_cast<tss_slots*>(
-        MPGetTaskStorageValue(tss_data_native_key));
-#endif
 
     if (slots == 0 && alloc)
     {
         std::auto_ptr<tss_slots> temp(new tss_slots);
 
-#if defined(BOOST_HAS_WINTHREADS)
-        if (at_thread_exit(&tss_thread_exit) == -1)
-            return 0;
-        if (!TlsSetValue(tss_data_native_key, temp.get()))
-            return 0;
-#elif defined(BOOST_HAS_PTHREADS)
         if (pthread_setspecific(tss_data_native_key, temp.get()) != 0)
             return 0;
-#elif defined(BOOST_HAS_MPTASKS)
-        if (MPSetTaskStorageValue(tss_data_native_key, temp.get()) != noErr)
-            return 0;
-#endif
         {
             boost::mutex::scoped_lock lock(*tss_data_mutex);
             tss_data_inc_use(lock);
Modified: trunk/libs/thread/src/win32/thread.cpp
==============================================================================
--- trunk/libs/thread/src/win32/thread.cpp	(original)
+++ trunk/libs/thread/src/win32/thread.cpp	2007-10-24 11:39:14 EDT (Wed, 24 Oct 2007)
@@ -88,7 +88,7 @@
         {
             thread_info->run();
         }
-        catch(thread_canceled const&)
+        catch(thread_cancelled const&)
         {
         }
         catch(...)
@@ -302,7 +302,7 @@
                 else if(notified_index==cancel_index)
                 {
                     detail::win32::ResetEvent(get_current_thread_data()->cancel_handle);
-                    throw thread_canceled();
+                    throw thread_cancelled();
                 }
             }
             else
@@ -322,7 +322,7 @@
             if(cancellation_enabled() && cancellation_requested())
             {
                 detail::win32::ResetEvent(get_current_thread_data()->cancel_handle);
-                throw thread_canceled();
+                throw thread_cancelled();
             }
         }