xref: /trunk/main/vos/source/thread.cxx (revision e8c8fa4b)
1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 #include <osl/time.h>
25 #include <vos/diagnose.hxx>
26 #include <vos/object.hxx>
27 #include <vos/thread.hxx>
28 
29 using namespace vos;
30 
threadWorkerFunction_impl(void * pthis)31 void vos::threadWorkerFunction_impl(void * pthis)
32 {
33 	vos::OThread* pThis= (vos::OThread*)pthis;
34 
35 	// call Handler-Function of OThread-derived class
36 	pThis->run();
37 
38 	// if not already terminating, by a kill do normal shutdown
39 	if (! pThis->m_bTerminating)
40 	{
41 		pThis->m_bTerminating = sal_True;
42 
43 		pThis->onTerminated();		// could e.g. delete this
44 	}
45 }
46 
47 /////////////////////////////////////////////////////////////////////////////
48 //
49 // Thread class
50 //
51 
52 VOS_IMPLEMENT_CLASSINFO(VOS_CLASSNAME(OThread, vos),
53 						VOS_NAMESPACE(OThread, vos),
54 						VOS_NAMESPACE(OObject, vos), 0);
55 
OThread()56 OThread::OThread()
57 {
58 	m_hThread      = 0;
59 	m_bTerminating = sal_False;
60     m_aCondition   = osl_createCondition();
61 }
62 
~OThread()63 OThread::~OThread()
64 {
65 	if (m_hThread != 0)
66 	{
67 		osl_destroyThread(m_hThread);
68 	}
69 
70     osl_destroyCondition( m_aCondition );
71 }
72 
create()73 sal_Bool OThread::create()
74 {
75 	VOS_ASSERT(m_hThread == 0);	// only one running thread per instance
76 
77     m_hThread = osl_createSuspendedThread(
78         threadWorkerFunction_impl, (void*)this);
79 	if (m_hThread)
80 		osl_resumeThread(m_hThread);
81 
82 	return m_hThread != 0;
83 }
84 
createSuspended()85 sal_Bool OThread::createSuspended()
86 {
87 	VOS_ASSERT(m_hThread == 0);	// only one running thread per instance
88 
89 	m_hThread= osl_createSuspendedThread(threadWorkerFunction_impl, (void*)this);
90 	return m_hThread != 0;
91 }
92 
suspend()93 void OThread::suspend()
94 {
95 	VOS_ASSERT(m_hThread != 0);	// use only on running thread
96 
97 	osl_suspendThread(m_hThread);
98 }
99 
resume()100 void OThread::resume()
101 {
102 	VOS_ASSERT(m_hThread != 0);	// use only on running thread
103 
104 	osl_resumeThread(m_hThread);
105 }
106 
isRunning()107 sal_Bool OThread::isRunning()
108 {
109 	return m_hThread != 0 && osl_isThreadRunning(m_hThread);
110 }
111 
getIdentifier() const112 OThread::TThreadIdentifier OThread::getIdentifier() const
113 {
114 	return (TThreadIdentifier)osl_getThreadIdentifier(m_hThread);
115 }
116 
getCurrentIdentifier()117 OThread::TThreadIdentifier OThread::getCurrentIdentifier()
118 {
119 	return (TThreadIdentifier)osl_getThreadIdentifier(0);
120 }
121 
join()122 void OThread::join()
123 {
124 	if (m_hThread) {
125 		VOS_ASSERT(getCurrentIdentifier() != getIdentifier());
126 		osl_joinWithThread(m_hThread);
127 	}
128 }
129 
sleep(const TimeValue & Delay)130 OThread::TThreadSleep OThread::sleep(const TimeValue& Delay)
131 {
132     TThreadSleep eRet;
133 
134     switch( osl_waitCondition( m_aCondition, &Delay ) )
135     {
136     case osl_cond_result_ok:
137         eRet = TSleep_Normal;
138         break;
139 
140     case osl_cond_result_timeout:
141         eRet = TSleep_Cancel;
142         break;
143 
144     default:
145         eRet = TSleep_Error;
146         break;
147     }
148 
149     return eRet;
150 }
151 
wait(const TimeValue & Delay)152 void OThread::wait(const TimeValue& Delay) {
153 	osl_waitThread(&Delay);
154 }
155 
awake()156 sal_Bool OThread::awake()
157 {
158     osl_setCondition( m_aCondition );
159     return osl_resetCondition( m_aCondition );
160 }
161 
terminate()162 void OThread::terminate()
163 {
164 	osl_terminateThread(m_hThread);
165 }
166 
schedule()167 sal_Bool OThread::schedule() {
168 	return osl_scheduleThread(m_hThread);
169 }
170 
kill()171 void OThread::kill()
172 {
173 	if (osl_isThreadRunning(m_hThread))
174 	{
175 		// flag we are shutting down
176 		m_bTerminating = sal_True;
177 
178 		terminate();
179 		join();
180 	}
181 }
182 
setPriority(OThread::TThreadPriority Priority)183 void OThread::setPriority(OThread::TThreadPriority Priority)
184 {
185 	osl_setThreadPriority(m_hThread, (oslThreadPriority)Priority);
186 }
187 
getPriority()188 OThread::TThreadPriority OThread::getPriority()
189 {
190 	return 	(TThreadPriority)osl_getThreadPriority(m_hThread);
191 }
192 
193 
yield()194 void OThread::yield()
195 {
196 	osl_yieldThread();
197 }
198 
onTerminated()199 void OThread::onTerminated()
200 {
201 }
202 
203 /////////////////////////////////////////////////////////////////////////////
204 //
205 // ThreadData class
206 //
207 
208 VOS_IMPLEMENT_CLASSINFO(VOS_CLASSNAME(OThreadData, vos),
209 						VOS_NAMESPACE(OThreadData, vos),
210 						VOS_NAMESPACE(OObject, vos), 0);
211 
OThreadData(oslThreadKeyCallbackFunction pCallback)212 OThreadData::OThreadData( oslThreadKeyCallbackFunction pCallback )
213 {
214     m_hKey = osl_createThreadKey( pCallback );
215 	VOS_VERIFY(m_hKey);
216 }
217 
~OThreadData()218 OThreadData::~OThreadData()
219 {
220 	osl_destroyThreadKey(m_hKey);
221 }
222 
setData(void * pData)223 sal_Bool OThreadData::setData(void *pData)
224 {
225 	VOS_ASSERT(m_hKey != 0);
226 
227 	return (osl_setThreadKeyData(m_hKey, pData));
228 }
229 
getData()230 void *OThreadData::getData()
231 {
232 	VOS_ASSERT(m_hKey != 0);
233 
234 	return (osl_getThreadKeyData(m_hKey));
235 }
236 
237