mbed-os for GR-LYCHEE

Dependents:   mbed-os-example-blinky-gr-lychee GR-Boads_Camera_sample GR-Boards_Audio_Recoder GR-Boads_Camera_DisplayApp ... more

Committer:
dkato
Date:
Fri Feb 02 05:42:23 2018 +0000
Revision:
0:f782d9c66c49
mbed-os for GR-LYCHEE

Who changed what in which revision?

UserRevisionLine numberNew contents of line
dkato 0:f782d9c66c49 1 /* mbed Microcontroller Library
dkato 0:f782d9c66c49 2 * Copyright (c) 2006-2012 ARM Limited
dkato 0:f782d9c66c49 3 *
dkato 0:f782d9c66c49 4 * Permission is hereby granted, free of charge, to any person obtaining a copy
dkato 0:f782d9c66c49 5 * of this software and associated documentation files (the "Software"), to deal
dkato 0:f782d9c66c49 6 * in the Software without restriction, including without limitation the rights
dkato 0:f782d9c66c49 7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
dkato 0:f782d9c66c49 8 * copies of the Software, and to permit persons to whom the Software is
dkato 0:f782d9c66c49 9 * furnished to do so, subject to the following conditions:
dkato 0:f782d9c66c49 10 *
dkato 0:f782d9c66c49 11 * The above copyright notice and this permission notice shall be included in
dkato 0:f782d9c66c49 12 * all copies or substantial portions of the Software.
dkato 0:f782d9c66c49 13 *
dkato 0:f782d9c66c49 14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
dkato 0:f782d9c66c49 15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
dkato 0:f782d9c66c49 16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
dkato 0:f782d9c66c49 17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
dkato 0:f782d9c66c49 18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
dkato 0:f782d9c66c49 19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
dkato 0:f782d9c66c49 20 * SOFTWARE.
dkato 0:f782d9c66c49 21 */
dkato 0:f782d9c66c49 22 #include "rtos/Thread.h"
dkato 0:f782d9c66c49 23
dkato 0:f782d9c66c49 24 #include "mbed.h"
dkato 0:f782d9c66c49 25 #include "rtos/rtos_idle.h"
dkato 0:f782d9c66c49 26
dkato 0:f782d9c66c49 27 // rt_tid2ptcb is an internal function which we exposed to get TCB for thread id
dkato 0:f782d9c66c49 28 #undef NULL //Workaround for conflicting macros in rt_TypeDef.h and stdio.h
dkato 0:f782d9c66c49 29 #include "rt_TypeDef.h"
dkato 0:f782d9c66c49 30
dkato 0:f782d9c66c49 31 extern "C" P_TCB rt_tid2ptcb(osThreadId thread_id);
dkato 0:f782d9c66c49 32
dkato 0:f782d9c66c49 33
dkato 0:f782d9c66c49 34 static void (*terminate_hook)(osThreadId id) = 0;
dkato 0:f782d9c66c49 35 extern "C" void thread_terminate_hook(osThreadId id)
dkato 0:f782d9c66c49 36 {
dkato 0:f782d9c66c49 37 if (terminate_hook != (void (*)(osThreadId))NULL) {
dkato 0:f782d9c66c49 38 terminate_hook(id);
dkato 0:f782d9c66c49 39 }
dkato 0:f782d9c66c49 40 }
dkato 0:f782d9c66c49 41
dkato 0:f782d9c66c49 42 namespace rtos {
dkato 0:f782d9c66c49 43
dkato 0:f782d9c66c49 44 void Thread::constructor(osPriority priority,
dkato 0:f782d9c66c49 45 uint32_t stack_size, unsigned char *stack_pointer) {
dkato 0:f782d9c66c49 46 _tid = 0;
dkato 0:f782d9c66c49 47 _finished = false;
dkato 0:f782d9c66c49 48 _dynamic_stack = (stack_pointer == NULL);
dkato 0:f782d9c66c49 49
dkato 0:f782d9c66c49 50 #if defined(__MBED_CMSIS_RTOS_CA9) || defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 51 _thread_def.tpriority = priority;
dkato 0:f782d9c66c49 52 _thread_def.stacksize = stack_size;
dkato 0:f782d9c66c49 53 _thread_def.stack_pointer = (uint32_t*)stack_pointer;
dkato 0:f782d9c66c49 54 #endif
dkato 0:f782d9c66c49 55 }
dkato 0:f782d9c66c49 56
dkato 0:f782d9c66c49 57 void Thread::constructor(Callback<void()> task,
dkato 0:f782d9c66c49 58 osPriority priority, uint32_t stack_size, unsigned char *stack_pointer) {
dkato 0:f782d9c66c49 59 constructor(priority, stack_size, stack_pointer);
dkato 0:f782d9c66c49 60
dkato 0:f782d9c66c49 61 switch (start(task)) {
dkato 0:f782d9c66c49 62 case osErrorResource:
dkato 0:f782d9c66c49 63 error("OS ran out of threads!\n");
dkato 0:f782d9c66c49 64 break;
dkato 0:f782d9c66c49 65 case osErrorParameter:
dkato 0:f782d9c66c49 66 error("Thread already running!\n");
dkato 0:f782d9c66c49 67 break;
dkato 0:f782d9c66c49 68 case osErrorNoMemory:
dkato 0:f782d9c66c49 69 error("Error allocating the stack memory\n");
dkato 0:f782d9c66c49 70 default:
dkato 0:f782d9c66c49 71 break;
dkato 0:f782d9c66c49 72 }
dkato 0:f782d9c66c49 73 }
dkato 0:f782d9c66c49 74
dkato 0:f782d9c66c49 75 osStatus Thread::start(Callback<void()> task) {
dkato 0:f782d9c66c49 76 _mutex.lock();
dkato 0:f782d9c66c49 77
dkato 0:f782d9c66c49 78 if ((_tid != 0) || _finished) {
dkato 0:f782d9c66c49 79 _mutex.unlock();
dkato 0:f782d9c66c49 80 return osErrorParameter;
dkato 0:f782d9c66c49 81 }
dkato 0:f782d9c66c49 82
dkato 0:f782d9c66c49 83 #if defined(__MBED_CMSIS_RTOS_CA9) || defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 84 _thread_def.pthread = Thread::_thunk;
dkato 0:f782d9c66c49 85 if (_thread_def.stack_pointer == NULL) {
dkato 0:f782d9c66c49 86 _thread_def.stack_pointer = new uint32_t[_thread_def.stacksize/sizeof(uint32_t)];
dkato 0:f782d9c66c49 87 MBED_ASSERT(_thread_def.stack_pointer != NULL);
dkato 0:f782d9c66c49 88 }
dkato 0:f782d9c66c49 89
dkato 0:f782d9c66c49 90 //Fill the stack with a magic word for maximum usage checking
dkato 0:f782d9c66c49 91 for (uint32_t i = 0; i < (_thread_def.stacksize / sizeof(uint32_t)); i++) {
dkato 0:f782d9c66c49 92 _thread_def.stack_pointer[i] = 0xE25A2EA5;
dkato 0:f782d9c66c49 93 }
dkato 0:f782d9c66c49 94 #endif
dkato 0:f782d9c66c49 95 _task = task;
dkato 0:f782d9c66c49 96 _tid = osThreadCreate(&_thread_def, this);
dkato 0:f782d9c66c49 97 if (_tid == NULL) {
dkato 0:f782d9c66c49 98 if (_dynamic_stack) {
dkato 0:f782d9c66c49 99 delete[] (_thread_def.stack_pointer);
dkato 0:f782d9c66c49 100 _thread_def.stack_pointer = (uint32_t*)NULL;
dkato 0:f782d9c66c49 101 }
dkato 0:f782d9c66c49 102 _mutex.unlock();
dkato 0:f782d9c66c49 103 _join_sem.release();
dkato 0:f782d9c66c49 104 return osErrorResource;
dkato 0:f782d9c66c49 105 }
dkato 0:f782d9c66c49 106
dkato 0:f782d9c66c49 107 _mutex.unlock();
dkato 0:f782d9c66c49 108 return osOK;
dkato 0:f782d9c66c49 109 }
dkato 0:f782d9c66c49 110
dkato 0:f782d9c66c49 111 osStatus Thread::terminate() {
dkato 0:f782d9c66c49 112 osStatus ret;
dkato 0:f782d9c66c49 113 _mutex.lock();
dkato 0:f782d9c66c49 114
dkato 0:f782d9c66c49 115 // Set the Thread's tid to NULL and
dkato 0:f782d9c66c49 116 // release the semaphore before terminating
dkato 0:f782d9c66c49 117 // since this thread could be terminating itself
dkato 0:f782d9c66c49 118 osThreadId local_id = _tid;
dkato 0:f782d9c66c49 119 _join_sem.release();
dkato 0:f782d9c66c49 120 _tid = (osThreadId)NULL;
dkato 0:f782d9c66c49 121 _finished = true;
dkato 0:f782d9c66c49 122
dkato 0:f782d9c66c49 123 ret = osThreadTerminate(local_id);
dkato 0:f782d9c66c49 124
dkato 0:f782d9c66c49 125 _mutex.unlock();
dkato 0:f782d9c66c49 126 return ret;
dkato 0:f782d9c66c49 127 }
dkato 0:f782d9c66c49 128
dkato 0:f782d9c66c49 129 osStatus Thread::join() {
dkato 0:f782d9c66c49 130 int32_t ret = _join_sem.wait();
dkato 0:f782d9c66c49 131 if (ret < 0) {
dkato 0:f782d9c66c49 132 return osErrorOS;
dkato 0:f782d9c66c49 133 }
dkato 0:f782d9c66c49 134
dkato 0:f782d9c66c49 135 // The semaphore has been released so this thread is being
dkato 0:f782d9c66c49 136 // terminated or has been terminated. Once the mutex has
dkato 0:f782d9c66c49 137 // been locked it is ensured that the thread is deleted.
dkato 0:f782d9c66c49 138 _mutex.lock();
dkato 0:f782d9c66c49 139 MBED_ASSERT(NULL == _tid);
dkato 0:f782d9c66c49 140 _mutex.unlock();
dkato 0:f782d9c66c49 141
dkato 0:f782d9c66c49 142 // Release sem so any other threads joining this thread wake up
dkato 0:f782d9c66c49 143 _join_sem.release();
dkato 0:f782d9c66c49 144 return osOK;
dkato 0:f782d9c66c49 145 }
dkato 0:f782d9c66c49 146
dkato 0:f782d9c66c49 147 osStatus Thread::set_priority(osPriority priority) {
dkato 0:f782d9c66c49 148 osStatus ret;
dkato 0:f782d9c66c49 149 _mutex.lock();
dkato 0:f782d9c66c49 150
dkato 0:f782d9c66c49 151 ret = osThreadSetPriority(_tid, priority);
dkato 0:f782d9c66c49 152
dkato 0:f782d9c66c49 153 _mutex.unlock();
dkato 0:f782d9c66c49 154 return ret;
dkato 0:f782d9c66c49 155 }
dkato 0:f782d9c66c49 156
dkato 0:f782d9c66c49 157 osPriority Thread::get_priority() {
dkato 0:f782d9c66c49 158 osPriority ret;
dkato 0:f782d9c66c49 159 _mutex.lock();
dkato 0:f782d9c66c49 160
dkato 0:f782d9c66c49 161 ret = osThreadGetPriority(_tid);
dkato 0:f782d9c66c49 162
dkato 0:f782d9c66c49 163 _mutex.unlock();
dkato 0:f782d9c66c49 164 return ret;
dkato 0:f782d9c66c49 165 }
dkato 0:f782d9c66c49 166
dkato 0:f782d9c66c49 167 int32_t Thread::signal_set(int32_t signals) {
dkato 0:f782d9c66c49 168 // osSignalSet is thread safe as long as the underlying
dkato 0:f782d9c66c49 169 // thread does not get terminated or return from main
dkato 0:f782d9c66c49 170 return osSignalSet(_tid, signals);
dkato 0:f782d9c66c49 171 }
dkato 0:f782d9c66c49 172
dkato 0:f782d9c66c49 173 int32_t Thread::signal_clr(int32_t signals) {
dkato 0:f782d9c66c49 174 // osSignalClear is thread safe as long as the underlying
dkato 0:f782d9c66c49 175 // thread does not get terminated or return from main
dkato 0:f782d9c66c49 176 return osSignalClear(_tid, signals);
dkato 0:f782d9c66c49 177 }
dkato 0:f782d9c66c49 178
dkato 0:f782d9c66c49 179 Thread::State Thread::get_state() {
dkato 0:f782d9c66c49 180 #if !defined(__MBED_CMSIS_RTOS_CA9) && !defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 181 #ifdef CMSIS_OS_RTX
dkato 0:f782d9c66c49 182 State status;
dkato 0:f782d9c66c49 183 _mutex.lock();
dkato 0:f782d9c66c49 184
dkato 0:f782d9c66c49 185 if (_tid != NULL) {
dkato 0:f782d9c66c49 186 status = (State)_thread_def.tcb.state;
dkato 0:f782d9c66c49 187 } else if (_finished) {
dkato 0:f782d9c66c49 188 status = Deleted;
dkato 0:f782d9c66c49 189 } else {
dkato 0:f782d9c66c49 190 status = Inactive;
dkato 0:f782d9c66c49 191 }
dkato 0:f782d9c66c49 192
dkato 0:f782d9c66c49 193 _mutex.unlock();
dkato 0:f782d9c66c49 194 return status;
dkato 0:f782d9c66c49 195 #endif
dkato 0:f782d9c66c49 196 #else
dkato 0:f782d9c66c49 197 State status = Deleted;
dkato 0:f782d9c66c49 198 _mutex.lock();
dkato 0:f782d9c66c49 199
dkato 0:f782d9c66c49 200 if (_tid != NULL) {
dkato 0:f782d9c66c49 201 status = (State)osThreadGetState(_tid);
dkato 0:f782d9c66c49 202 }
dkato 0:f782d9c66c49 203
dkato 0:f782d9c66c49 204 _mutex.unlock();
dkato 0:f782d9c66c49 205 return status;
dkato 0:f782d9c66c49 206 #endif
dkato 0:f782d9c66c49 207 }
dkato 0:f782d9c66c49 208
dkato 0:f782d9c66c49 209 uint32_t Thread::stack_size() {
dkato 0:f782d9c66c49 210 #ifndef __MBED_CMSIS_RTOS_CA9
dkato 0:f782d9c66c49 211 #if defined(CMSIS_OS_RTX) && !defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 212 uint32_t size = 0;
dkato 0:f782d9c66c49 213 _mutex.lock();
dkato 0:f782d9c66c49 214
dkato 0:f782d9c66c49 215 if (_tid != NULL) {
dkato 0:f782d9c66c49 216 size = _thread_def.tcb.priv_stack;
dkato 0:f782d9c66c49 217 }
dkato 0:f782d9c66c49 218
dkato 0:f782d9c66c49 219 _mutex.unlock();
dkato 0:f782d9c66c49 220 return size;
dkato 0:f782d9c66c49 221 #else
dkato 0:f782d9c66c49 222 uint32_t size = 0;
dkato 0:f782d9c66c49 223 _mutex.lock();
dkato 0:f782d9c66c49 224
dkato 0:f782d9c66c49 225 if (_tid != NULL) {
dkato 0:f782d9c66c49 226 P_TCB tcb = rt_tid2ptcb(_tid);
dkato 0:f782d9c66c49 227 size = tcb->priv_stack;
dkato 0:f782d9c66c49 228 }
dkato 0:f782d9c66c49 229
dkato 0:f782d9c66c49 230 _mutex.unlock();
dkato 0:f782d9c66c49 231 return size;
dkato 0:f782d9c66c49 232 #endif
dkato 0:f782d9c66c49 233 #else
dkato 0:f782d9c66c49 234 return 0;
dkato 0:f782d9c66c49 235 #endif
dkato 0:f782d9c66c49 236 }
dkato 0:f782d9c66c49 237
dkato 0:f782d9c66c49 238 uint32_t Thread::free_stack() {
dkato 0:f782d9c66c49 239 #ifndef __MBED_CMSIS_RTOS_CA9
dkato 0:f782d9c66c49 240 #if defined(CMSIS_OS_RTX) && !defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 241 uint32_t size = 0;
dkato 0:f782d9c66c49 242 _mutex.lock();
dkato 0:f782d9c66c49 243
dkato 0:f782d9c66c49 244 if (_tid != NULL) {
dkato 0:f782d9c66c49 245 uint32_t bottom = (uint32_t)_thread_def.tcb.stack;
dkato 0:f782d9c66c49 246 size = _thread_def.tcb.tsk_stack - bottom;
dkato 0:f782d9c66c49 247 }
dkato 0:f782d9c66c49 248
dkato 0:f782d9c66c49 249 _mutex.unlock();
dkato 0:f782d9c66c49 250 return size;
dkato 0:f782d9c66c49 251 #else
dkato 0:f782d9c66c49 252 uint32_t size = 0;
dkato 0:f782d9c66c49 253 _mutex.lock();
dkato 0:f782d9c66c49 254
dkato 0:f782d9c66c49 255 if (_tid != NULL) {
dkato 0:f782d9c66c49 256 P_TCB tcb = rt_tid2ptcb(_tid);
dkato 0:f782d9c66c49 257 uint32_t bottom = (uint32_t)tcb->stack;
dkato 0:f782d9c66c49 258 size = tcb->tsk_stack - bottom;
dkato 0:f782d9c66c49 259 }
dkato 0:f782d9c66c49 260
dkato 0:f782d9c66c49 261 _mutex.unlock();
dkato 0:f782d9c66c49 262 return size;
dkato 0:f782d9c66c49 263 #endif
dkato 0:f782d9c66c49 264 #else
dkato 0:f782d9c66c49 265 return 0;
dkato 0:f782d9c66c49 266 #endif
dkato 0:f782d9c66c49 267 }
dkato 0:f782d9c66c49 268
dkato 0:f782d9c66c49 269 uint32_t Thread::used_stack() {
dkato 0:f782d9c66c49 270 #ifndef __MBED_CMSIS_RTOS_CA9
dkato 0:f782d9c66c49 271 #if defined(CMSIS_OS_RTX) && !defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 272 uint32_t size = 0;
dkato 0:f782d9c66c49 273 _mutex.lock();
dkato 0:f782d9c66c49 274
dkato 0:f782d9c66c49 275 if (_tid != NULL) {
dkato 0:f782d9c66c49 276 uint32_t top = (uint32_t)_thread_def.tcb.stack + _thread_def.tcb.priv_stack;
dkato 0:f782d9c66c49 277 size = top - _thread_def.tcb.tsk_stack;
dkato 0:f782d9c66c49 278 }
dkato 0:f782d9c66c49 279
dkato 0:f782d9c66c49 280 _mutex.unlock();
dkato 0:f782d9c66c49 281 return size;
dkato 0:f782d9c66c49 282 #else
dkato 0:f782d9c66c49 283 uint32_t size = 0;
dkato 0:f782d9c66c49 284 _mutex.lock();
dkato 0:f782d9c66c49 285
dkato 0:f782d9c66c49 286 if (_tid != NULL) {
dkato 0:f782d9c66c49 287 P_TCB tcb = rt_tid2ptcb(_tid);
dkato 0:f782d9c66c49 288 uint32_t top = (uint32_t)tcb->stack + tcb->priv_stack;
dkato 0:f782d9c66c49 289 size = top - tcb->tsk_stack;
dkato 0:f782d9c66c49 290 }
dkato 0:f782d9c66c49 291
dkato 0:f782d9c66c49 292 _mutex.unlock();
dkato 0:f782d9c66c49 293 return size;
dkato 0:f782d9c66c49 294 #endif
dkato 0:f782d9c66c49 295 #else
dkato 0:f782d9c66c49 296 return 0;
dkato 0:f782d9c66c49 297 #endif
dkato 0:f782d9c66c49 298 }
dkato 0:f782d9c66c49 299
dkato 0:f782d9c66c49 300 uint32_t Thread::max_stack() {
dkato 0:f782d9c66c49 301 #ifndef __MBED_CMSIS_RTOS_CA9
dkato 0:f782d9c66c49 302 #if defined(CMSIS_OS_RTX) && !defined(__MBED_CMSIS_RTOS_CM)
dkato 0:f782d9c66c49 303 uint32_t size = 0;
dkato 0:f782d9c66c49 304 _mutex.lock();
dkato 0:f782d9c66c49 305
dkato 0:f782d9c66c49 306 if (_tid != NULL) {
dkato 0:f782d9c66c49 307 uint32_t high_mark = 0;
dkato 0:f782d9c66c49 308 while (_thread_def.tcb.stack[high_mark] == 0xE25A2EA5)
dkato 0:f782d9c66c49 309 high_mark++;
dkato 0:f782d9c66c49 310 size = _thread_def.tcb.priv_stack - (high_mark * 4);
dkato 0:f782d9c66c49 311 }
dkato 0:f782d9c66c49 312
dkato 0:f782d9c66c49 313 _mutex.unlock();
dkato 0:f782d9c66c49 314 return size;
dkato 0:f782d9c66c49 315 #else
dkato 0:f782d9c66c49 316 uint32_t size = 0;
dkato 0:f782d9c66c49 317 _mutex.lock();
dkato 0:f782d9c66c49 318
dkato 0:f782d9c66c49 319 if (_tid != NULL) {
dkato 0:f782d9c66c49 320 P_TCB tcb = rt_tid2ptcb(_tid);
dkato 0:f782d9c66c49 321 uint32_t high_mark = 0;
dkato 0:f782d9c66c49 322 while (tcb->stack[high_mark] == 0xE25A2EA5)
dkato 0:f782d9c66c49 323 high_mark++;
dkato 0:f782d9c66c49 324 size = tcb->priv_stack - (high_mark * 4);
dkato 0:f782d9c66c49 325 }
dkato 0:f782d9c66c49 326
dkato 0:f782d9c66c49 327 _mutex.unlock();
dkato 0:f782d9c66c49 328 return size;
dkato 0:f782d9c66c49 329 #endif
dkato 0:f782d9c66c49 330 #else
dkato 0:f782d9c66c49 331 return 0;
dkato 0:f782d9c66c49 332 #endif
dkato 0:f782d9c66c49 333 }
dkato 0:f782d9c66c49 334
dkato 0:f782d9c66c49 335 osEvent Thread::signal_wait(int32_t signals, uint32_t millisec) {
dkato 0:f782d9c66c49 336 return osSignalWait(signals, millisec);
dkato 0:f782d9c66c49 337 }
dkato 0:f782d9c66c49 338
dkato 0:f782d9c66c49 339 osStatus Thread::wait(uint32_t millisec) {
dkato 0:f782d9c66c49 340 return osDelay(millisec);
dkato 0:f782d9c66c49 341 }
dkato 0:f782d9c66c49 342
dkato 0:f782d9c66c49 343 osStatus Thread::yield() {
dkato 0:f782d9c66c49 344 return osThreadYield();
dkato 0:f782d9c66c49 345 }
dkato 0:f782d9c66c49 346
dkato 0:f782d9c66c49 347 osThreadId Thread::gettid() {
dkato 0:f782d9c66c49 348 return osThreadGetId();
dkato 0:f782d9c66c49 349 }
dkato 0:f782d9c66c49 350
dkato 0:f782d9c66c49 351 void Thread::attach_idle_hook(void (*fptr)(void)) {
dkato 0:f782d9c66c49 352 rtos_attach_idle_hook(fptr);
dkato 0:f782d9c66c49 353 }
dkato 0:f782d9c66c49 354
dkato 0:f782d9c66c49 355 void Thread::attach_terminate_hook(void (*fptr)(osThreadId id)) {
dkato 0:f782d9c66c49 356 terminate_hook = fptr;
dkato 0:f782d9c66c49 357 }
dkato 0:f782d9c66c49 358
dkato 0:f782d9c66c49 359 Thread::~Thread() {
dkato 0:f782d9c66c49 360 // terminate is thread safe
dkato 0:f782d9c66c49 361 terminate();
dkato 0:f782d9c66c49 362 #ifdef __MBED_CMSIS_RTOS_CM
dkato 0:f782d9c66c49 363 if (_dynamic_stack) {
dkato 0:f782d9c66c49 364 delete[] (_thread_def.stack_pointer);
dkato 0:f782d9c66c49 365 _thread_def.stack_pointer = (uint32_t*)NULL;
dkato 0:f782d9c66c49 366 }
dkato 0:f782d9c66c49 367 #endif
dkato 0:f782d9c66c49 368 }
dkato 0:f782d9c66c49 369
dkato 0:f782d9c66c49 370 void Thread::_thunk(const void * thread_ptr)
dkato 0:f782d9c66c49 371 {
dkato 0:f782d9c66c49 372 Thread *t = (Thread*)thread_ptr;
dkato 0:f782d9c66c49 373 t->_task();
dkato 0:f782d9c66c49 374 t->_mutex.lock();
dkato 0:f782d9c66c49 375 t->_tid = (osThreadId)NULL;
dkato 0:f782d9c66c49 376 t->_finished = true;
dkato 0:f782d9c66c49 377 t->_join_sem.release();
dkato 0:f782d9c66c49 378 // rtos will release the mutex automatically
dkato 0:f782d9c66c49 379 }
dkato 0:f782d9c66c49 380
dkato 0:f782d9c66c49 381 }