1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 #ifndef _THREAD_HXX_ 29 #define _THREAD_HXX_ 30 31 #ifdef __cplusplus 32 33 #include <osl/time.h> 34 35 36 #include <osl/diagnose.h> 37 #include <osl/thread.h> 38 #include <rtl/alloc.h> 39 40 namespace osl 41 { 42 /** threadFunc is the function which is executed by the threads 43 created by the osl::Thread class. The function's signature 44 matches the one of oslWorkerFunction which is declared in 45 osl/thread.h . 46 */ 47 extern "C" inline void SAL_CALL threadFunc( void* param); 48 49 class Thread 50 { 51 Thread( const Thread& ); 52 Thread& operator= ( const Thread& ); 53 public: 54 // these are here to force memory de/allocation to sal lib. 55 inline static void * SAL_CALL operator new( size_t nSize ) SAL_THROW (()) 56 { return ::rtl_allocateMemory( nSize ); } 57 inline static void SAL_CALL operator delete( void * pMem ) SAL_THROW (()) 58 { ::rtl_freeMemory( pMem ); } 59 inline static void * SAL_CALL operator new( size_t, void * pMem ) SAL_THROW (()) 60 { return pMem; } 61 inline static void SAL_CALL operator delete( void *, void * ) SAL_THROW (()) 62 {} 63 64 Thread(): m_hThread(0){} 65 66 virtual ~Thread() 67 { 68 osl_destroyThread( m_hThread); 69 } 70 71 sal_Bool SAL_CALL create() 72 { 73 OSL_ASSERT(m_hThread == 0); // only one running thread per instance 74 if (m_hThread) 75 return sal_False; 76 77 m_hThread = osl_createSuspendedThread( threadFunc, (void*)this); 78 if ( m_hThread ) 79 osl_resumeThread(m_hThread); 80 81 return m_hThread != 0; 82 } 83 84 sal_Bool SAL_CALL createSuspended() 85 { 86 OSL_ASSERT(m_hThread == 0); // only one running thread per instance 87 if( m_hThread) 88 return sal_False; 89 m_hThread= osl_createSuspendedThread( threadFunc, 90 (void*)this); 91 return m_hThread != 0; 92 } 93 94 virtual void SAL_CALL suspend() 95 { 96 if( m_hThread ) 97 osl_suspendThread(m_hThread); 98 } 99 100 virtual void SAL_CALL resume() 101 { 102 if( m_hThread ) 103 osl_resumeThread(m_hThread); 104 } 105 106 virtual void SAL_CALL terminate() 107 { 108 if( m_hThread ) 109 osl_terminateThread(m_hThread); 110 } 111 112 virtual void SAL_CALL join() 113 { 114 osl_joinWithThread(m_hThread); 115 } 116 117 sal_Bool SAL_CALL isRunning() const 118 { 119 return osl_isThreadRunning(m_hThread); 120 } 121 122 void SAL_CALL setPriority( oslThreadPriority Priority) 123 { 124 if( m_hThread ) 125 osl_setThreadPriority(m_hThread, Priority); 126 } 127 128 oslThreadPriority SAL_CALL getPriority() const 129 { 130 return m_hThread ? osl_getThreadPriority(m_hThread) : osl_Thread_PriorityUnknown; 131 } 132 133 oslThreadIdentifier SAL_CALL getIdentifier() const 134 { 135 return osl_getThreadIdentifier(m_hThread); 136 } 137 138 static oslThreadIdentifier SAL_CALL getCurrentIdentifier() 139 { 140 return osl_getThreadIdentifier(0); 141 } 142 143 static void SAL_CALL wait(const TimeValue& Delay) 144 { 145 osl_waitThread(&Delay); 146 } 147 148 static void SAL_CALL yield() 149 { 150 osl_yieldThread(); 151 } 152 153 static inline void setName(char const * name) throw () { 154 osl_setThreadName(name); 155 } 156 157 virtual sal_Bool SAL_CALL schedule() 158 { 159 return m_hThread ? osl_scheduleThread(m_hThread) : sal_False; 160 } 161 162 SAL_CALL operator oslThread() const 163 { 164 return m_hThread; 165 } 166 167 protected: 168 169 /** The thread functions calls the protected functions 170 run and onTerminated. 171 */ 172 friend void SAL_CALL threadFunc( void* param); 173 174 virtual void SAL_CALL run() = 0; 175 176 virtual void SAL_CALL onTerminated() 177 { 178 } 179 180 private: 181 oslThread m_hThread; 182 }; 183 184 extern "C" inline void SAL_CALL threadFunc( void* param) 185 { 186 Thread* pObj= (Thread*)param; 187 pObj->run(); 188 pObj->onTerminated(); 189 } 190 191 class ThreadData 192 { 193 ThreadData( const ThreadData& ); 194 ThreadData& operator= (const ThreadData& ); 195 public: 196 /// Create a thread specific local data key 197 ThreadData( oslThreadKeyCallbackFunction pCallback= 0 ) 198 { 199 m_hKey = osl_createThreadKey( pCallback ); 200 } 201 202 /// Destroy a thread specific local data key 203 ~ThreadData() 204 { 205 osl_destroyThreadKey(m_hKey); 206 } 207 208 /** Set the data associated with the data key. 209 @returns True if operation was successfull 210 */ 211 sal_Bool SAL_CALL setData(void *pData) 212 { 213 return (osl_setThreadKeyData(m_hKey, pData)); 214 } 215 216 /** Get the data associated with the data key. 217 @returns The data asscoitaed with the data key or 218 NULL if no data was set 219 */ 220 void* SAL_CALL getData() 221 { 222 return osl_getThreadKeyData(m_hKey); 223 } 224 225 operator oslThreadKey() const 226 { 227 return m_hKey; 228 } 229 230 private: 231 oslThreadKey m_hKey; 232 }; 233 234 } // end namespace osl 235 #endif 236 #endif 237