1 // LAF Base Library 2 // Copyright (c) 2001-2016 David Capello 3 // 4 // This file is released under the terms of the MIT license. 5 // Read LICENSE.txt for more information. 6 7 #ifndef BASE_THREAD_H_INCLUDED 8 #define BASE_THREAD_H_INCLUDED 9 #pragma once 10 11 namespace base { // Based on C++0x threads lib 12 13 class thread { 14 public: 15 typedef void* native_handle_type; 16 17 // Create an instance to represent the current thread 18 thread(); 19 20 // Create a new thread without arguments 21 template<class Callable> thread(const Callable & f)22 thread(const Callable& f) { 23 launch_thread(new func_wrapper0<Callable>(f)); 24 } 25 26 // Create a new thread with one argument 27 template<class Callable, class A> thread(const Callable & f,A a)28 thread(const Callable& f, A a) { 29 launch_thread(new func_wrapper1<Callable, A>(f, a)); 30 } 31 32 // Create a new thread with two arguments 33 template<class Callable, class A, class B> thread(const Callable & f,A a,B b)34 thread(const Callable& f, A a, B b) { 35 launch_thread(new func_wrapper2<Callable, A, B>(f, a, b)); 36 } 37 38 ~thread(); 39 40 bool joinable() const; 41 void join(); 42 void detach(); 43 44 native_handle_type native_handle(); 45 46 class details { 47 public: 48 static void thread_proxy(void* data); 49 }; 50 51 private: 52 native_handle_type m_native_handle; 53 54 class func_wrapper { 55 public: ~func_wrapper()56 virtual ~func_wrapper() { } 57 virtual void operator()() = 0; 58 }; 59 60 void launch_thread(func_wrapper* f); 61 62 template<class Callable> 63 class func_wrapper0 : public func_wrapper { 64 public: 65 Callable f; func_wrapper0(const Callable & f)66 func_wrapper0(const Callable& f) : f(f) { } operator()67 void operator()() { f(); } 68 }; 69 70 template<class Callable, class A> 71 class func_wrapper1 : public func_wrapper { 72 public: 73 Callable f; 74 A a; func_wrapper1(const Callable & f,A a)75 func_wrapper1(const Callable& f, A a) : f(f), a(a) { } operator()76 void operator()() { f(a); } 77 }; 78 79 template<class Callable, class A, class B> 80 class func_wrapper2 : public func_wrapper { 81 public: 82 Callable f; 83 A a; 84 B b; func_wrapper2(const Callable & f,A a,B b)85 func_wrapper2(const Callable& f, A a, B b) : f(f), a(a), b(b) { } operator()86 void operator()() { f(a, b); } 87 }; 88 89 }; 90 91 namespace this_thread 92 { 93 void yield(); 94 void sleep_for(double seconds); 95 thread::native_handle_type native_handle(); 96 } 97 98 // This class joins the thread in its destructor. 99 class thread_guard { 100 thread& m_thread; 101 public: thread_guard(thread & t)102 explicit thread_guard(thread& t) : m_thread(t) { } ~thread_guard()103 ~thread_guard() 104 { 105 if (m_thread.joinable()) 106 m_thread.join(); 107 } 108 }; 109 110 } 111 112 #endif 113