Official mbed Real Time Operating System based on the RTX implementation of the CMSIS-RTOS API open standard. Patched to work with NUCLEO L152 board
Fork of mbed-rtos by
RTX_CM_lib.h
00001 /*---------------------------------------------------------------------------- 00002 * RL-ARM - RTX 00003 *---------------------------------------------------------------------------- 00004 * Name: RTX_CM_LIB.H 00005 * Purpose: RTX Kernel System Configuration 00006 * Rev.: V4.60 00007 *---------------------------------------------------------------------------- 00008 * 00009 * Copyright (c) 1999-2009 KEIL, 2009-2012 ARM Germany GmbH 00010 * All rights reserved. 00011 * Redistribution and use in source and binary forms, with or without 00012 * modification, are permitted provided that the following conditions are met: 00013 * - Redistributions of source code must retain the above copyright 00014 * notice, this list of conditions and the following disclaimer. 00015 * - Redistributions in binary form must reproduce the above copyright 00016 * notice, this list of conditions and the following disclaimer in the 00017 * documentation and/or other materials provided with the distribution. 00018 * - Neither the name of ARM nor the names of its contributors may be used 00019 * to endorse or promote products derived from this software without 00020 * specific prior written permission. 00021 * 00022 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 00023 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00024 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 00025 * ARE DISCLAIMED. IN NO EVENT SHALL COPYRIGHT HOLDERS AND CONTRIBUTORS BE 00026 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 00027 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 00028 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 00029 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 00030 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 00031 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 00032 * POSSIBILITY OF SUCH DAMAGE. 00033 *---------------------------------------------------------------------------*/ 00034 #include "mbed_error.h" 00035 00036 #if defined (__CC_ARM) 00037 #pragma O3 00038 #define __USED __attribute__((used)) 00039 #elif defined (__GNUC__) 00040 #pragma GCC optimize ("O3") 00041 #define __USED __attribute__((used)) 00042 #elif defined (__ICCARM__) 00043 #define __USED __root 00044 #endif 00045 00046 00047 /*---------------------------------------------------------------------------- 00048 * Definitions 00049 *---------------------------------------------------------------------------*/ 00050 00051 #define _declare_box(pool,size,cnt) uint32_t pool[(((size)+3)/4)*(cnt) + 3] 00052 #define _declare_box8(pool,size,cnt) uint64_t pool[(((size)+7)/8)*(cnt) + 2] 00053 00054 #define OS_TCB_SIZE 48 00055 #define OS_TMR_SIZE 8 00056 00057 #if defined (__CC_ARM) && !defined (__MICROLIB) 00058 00059 typedef void *OS_ID; 00060 typedef uint32_t OS_TID; 00061 typedef uint32_t OS_MUT[3]; 00062 typedef uint32_t OS_RESULT; 00063 00064 #define runtask_id() rt_tsk_self() 00065 #define mutex_init(m) rt_mut_init(m) 00066 #define mutex_wait(m) os_mut_wait(m,0xFFFF) 00067 #define mutex_rel(m) os_mut_release(m) 00068 00069 extern OS_TID rt_tsk_self (void); 00070 extern void rt_mut_init (OS_ID mutex); 00071 extern OS_RESULT rt_mut_release (OS_ID mutex); 00072 extern OS_RESULT rt_mut_wait (OS_ID mutex, uint16_t timeout); 00073 00074 #define os_mut_wait(mutex,timeout) _os_mut_wait((uint32_t)rt_mut_wait,mutex,timeout) 00075 #define os_mut_release(mutex) _os_mut_release((uint32_t)rt_mut_release,mutex) 00076 00077 OS_RESULT _os_mut_release (uint32_t p, OS_ID mutex) __svc_indirect(0); 00078 OS_RESULT _os_mut_wait (uint32_t p, OS_ID mutex, uint16_t timeout) __svc_indirect(0); 00079 00080 #endif 00081 00082 00083 /*---------------------------------------------------------------------------- 00084 * Global Variables 00085 *---------------------------------------------------------------------------*/ 00086 00087 #if (OS_TIMERS != 0) 00088 #define OS_TASK_CNT (OS_TASKCNT + 1) 00089 #else 00090 #define OS_TASK_CNT OS_TASKCNT 00091 #endif 00092 00093 uint16_t const os_maxtaskrun = OS_TASK_CNT; 00094 uint32_t const os_rrobin = (OS_ROBIN << 16) | OS_ROBINTOUT; 00095 uint32_t const os_trv = OS_TRV; 00096 uint8_t const os_flags = OS_RUNPRIV; 00097 00098 /* Export following defines to uVision debugger. */ 00099 __USED uint32_t const os_clockrate = OS_TICK; 00100 __USED uint32_t const os_timernum = 0; 00101 00102 /* Stack for the os_idle_demon */ 00103 unsigned int idle_task_stack[OS_IDLESTKSIZE]; 00104 unsigned short const idle_task_stack_size = OS_IDLESTKSIZE; 00105 00106 #ifndef OS_FIFOSZ 00107 #define OS_FIFOSZ 16 00108 #endif 00109 00110 /* Fifo Queue buffer for ISR requests.*/ 00111 uint32_t os_fifo[OS_FIFOSZ*2+1]; 00112 uint8_t const os_fifo_size = OS_FIFOSZ; 00113 00114 /* An array of Active task pointers. */ 00115 void *os_active_TCB[OS_TASK_CNT]; 00116 00117 /* User Timers Resources */ 00118 #if (OS_TIMERS != 0) 00119 extern void osTimerThread (void const *argument); 00120 osThreadDef(osTimerThread, (osPriority)(OS_TIMERPRIO-3), 4*OS_TIMERSTKSZ); 00121 osThreadId osThreadId_osTimerThread; 00122 osMessageQDef(osTimerMessageQ, OS_TIMERCBQS, void *); 00123 osMessageQId osMessageQId_osTimerMessageQ; 00124 #else 00125 osThreadDef_t os_thread_def_osTimerThread = { NULL }; 00126 osThreadId osThreadId_osTimerThread; 00127 osMessageQDef(osTimerMessageQ, 0, void *); 00128 osMessageQId osMessageQId_osTimerMessageQ; 00129 #endif 00130 00131 00132 /*---------------------------------------------------------------------------- 00133 * RTX Optimizations (empty functions) 00134 *---------------------------------------------------------------------------*/ 00135 00136 #if OS_ROBIN == 0 00137 void rt_init_robin (void) {;} 00138 void rt_chk_robin (void) {;} 00139 #endif 00140 00141 #if OS_STKCHECK == 0 00142 void rt_stk_check (void) {;} 00143 #endif 00144 00145 00146 /*---------------------------------------------------------------------------- 00147 * Standard Library multithreading interface 00148 *---------------------------------------------------------------------------*/ 00149 00150 #if defined (__CC_ARM) && !defined (__MICROLIB) 00151 static OS_MUT std_libmutex[OS_MUTEXCNT]; 00152 static uint32_t nr_mutex; 00153 00154 /*--------------------------- _mutex_initialize -----------------------------*/ 00155 00156 int _mutex_initialize (OS_ID *mutex) { 00157 /* Allocate and initialize a system mutex. */ 00158 00159 if (nr_mutex >= OS_MUTEXCNT) { 00160 /* If you are here, you need to increase the number OS_MUTEXCNT. */ 00161 error("Not enough stdlib mutexes\n"); 00162 } 00163 *mutex = &std_libmutex[nr_mutex++]; 00164 mutex_init (*mutex); 00165 return (1); 00166 } 00167 00168 00169 /*--------------------------- _mutex_acquire --------------------------------*/ 00170 00171 __attribute__((used)) void _mutex_acquire (OS_ID *mutex) { 00172 /* Acquire a system mutex, lock stdlib resources. */ 00173 if (runtask_id ()) { 00174 /* RTX running, acquire a mutex. */ 00175 mutex_wait (*mutex); 00176 } 00177 } 00178 00179 00180 /*--------------------------- _mutex_release --------------------------------*/ 00181 00182 __attribute__((used)) void _mutex_release (OS_ID *mutex) { 00183 /* Release a system mutex, unlock stdlib resources. */ 00184 if (runtask_id ()) { 00185 /* RTX running, release a mutex. */ 00186 mutex_rel (*mutex); 00187 } 00188 } 00189 00190 #endif 00191 00192 00193 /*---------------------------------------------------------------------------- 00194 * RTX Startup 00195 *---------------------------------------------------------------------------*/ 00196 00197 /* Main Thread definition */ 00198 extern int main (void); 00199 osThreadDef_t os_thread_def_main = {(os_pthread)main, osPriorityNormal, 0, NULL}; 00200 00201 // This define should be probably moved to the CMSIS layer 00202 #if defined(TARGET_LPC1768) 00203 #define INITIAL_SP (0x10008000UL) 00204 00205 #elif defined(TARGET_LPC11U24) 00206 #define INITIAL_SP (0x10002000UL) 00207 00208 #elif defined(TARGET_LPC11U35_401) || defined(TARGET_LPC11U35_501) || defined(TARGET_LPCCAPPUCCINO) 00209 #define INITIAL_SP (0x10002000UL) 00210 00211 #elif defined(TARGET_LPC1114) 00212 #define INITIAL_SP (0x10001000UL) 00213 00214 #elif defined(TARGET_LPC812) 00215 #define INITIAL_SP (0x10001000UL) 00216 00217 #elif defined(TARGET_KL25Z) 00218 #define INITIAL_SP (0x20003000UL) 00219 00220 #elif defined(TARGET_K64F) 00221 #define INITIAL_SP (0x20030000UL) 00222 00223 #elif defined(TARGET_KL46Z) 00224 #define INITIAL_SP (0x20006000UL) 00225 00226 #elif defined(TARGET_KL05Z) 00227 #define INITIAL_SP (0x20000C00UL) 00228 00229 #elif defined(TARGET_LPC4088) 00230 #define INITIAL_SP (0x10010000UL) 00231 00232 #elif defined(TARGET_LPC4337) 00233 #define INITIAL_SP (0x10008000UL) 00234 00235 #elif defined(TARGET_LPC1347) 00236 #define INITIAL_SP (0x10002000UL) 00237 00238 #elif defined(TARGET_STM32F100RB) || defined(TARGET_STM32F051R8) 00239 #define INITIAL_SP (0x20002000UL) 00240 00241 #elif defined(TARGET_DISCO_F303VC) 00242 #define INITIAL_SP (0x2000A000UL) 00243 00244 #elif defined(TARGET_STM32F407) || defined(TARGET_F407VG) 00245 #define INITIAL_SP (0x20020000UL) 00246 00247 #elif defined(TARGET_STM32F401RE) 00248 #define INITIAL_SP (0x20018000UL) 00249 00250 #elif defined(TARGET_LPC1549) 00251 #define INITIAL_SP (0x02009000UL) 00252 00253 #elif defined(TARGET_LPC11U68) 00254 #define INITIAL_SP (0x10004000UL) 00255 00256 #elif defined(TARGET_NRF51822) || defined (TARGET_NUCLEO_L152RE) 00257 #define INITIAL_SP (0x20004000UL) 00258 00259 #elif defined(TARGET_STM32F411RE) 00260 #define INITIAL_SP (0x20020000UL) 00261 00262 #else 00263 #error "no target defined" 00264 00265 #endif 00266 00267 #ifdef __CC_ARM 00268 extern unsigned char Image$$RW_IRAM1$$ZI$$Limit[]; 00269 #define HEAP_START (Image$$RW_IRAM1$$ZI$$Limit) 00270 #elif defined(__GNUC__) 00271 extern unsigned char __end__[]; 00272 #define HEAP_START (__end__) 00273 #endif 00274 00275 void set_main_stack(void) { 00276 // That is the bottom of the main stack block: no collision detection 00277 os_thread_def_main.stack_pointer = HEAP_START; 00278 00279 // Leave OS_SCHEDULERSTKSIZE words for the scheduler and interrupts 00280 os_thread_def_main.stacksize = (INITIAL_SP - (unsigned int)HEAP_START) - (OS_SCHEDULERSTKSIZE * 4); 00281 } 00282 00283 #if defined (__CC_ARM) 00284 #ifdef __MICROLIB 00285 void _main_init (void) __attribute__((section(".ARM.Collect$$$$000000FF"))); 00286 void _main_init (void) { 00287 osKernelInitialize(); 00288 set_main_stack(); 00289 osThreadCreate(&os_thread_def_main, NULL); 00290 osKernelStart(); 00291 for (;;); 00292 } 00293 #else 00294 00295 /* The single memory model is checking for stack collision at run time, verifing 00296 that the heap pointer is underneath the stack pointer. 00297 00298 With the RTOS there is not only one stack above the heap, there are multiple 00299 stacks and some of them are underneath the heap pointer. 00300 */ 00301 #pragma import(__use_two_region_memory) 00302 00303 __asm void __rt_entry (void) { 00304 00305 IMPORT __user_setup_stackheap 00306 IMPORT __rt_lib_init 00307 IMPORT os_thread_def_main 00308 IMPORT osKernelInitialize 00309 IMPORT set_main_stack 00310 IMPORT osKernelStart 00311 IMPORT osThreadCreate 00312 IMPORT exit 00313 00314 BL __user_setup_stackheap 00315 MOV R1,R2 00316 BL __rt_lib_init 00317 BL osKernelInitialize 00318 BL set_main_stack 00319 LDR R0,=os_thread_def_main 00320 MOVS R1,#0 00321 BL osThreadCreate 00322 BL osKernelStart 00323 BL exit 00324 00325 ALIGN 00326 } 00327 #endif 00328 00329 #elif defined (__GNUC__) 00330 00331 #ifdef __CS3__ 00332 00333 /* CS3 start_c routine. 00334 * 00335 * Copyright (c) 2006, 2007 CodeSourcery Inc 00336 * 00337 * The authors hereby grant permission to use, copy, modify, distribute, 00338 * and license this software and its documentation for any purpose, provided 00339 * that existing copyright notices are retained in all copies and that this 00340 * notice is included verbatim in any distributions. No written agreement, 00341 * license, or royalty fee is required for any of the authorized uses. 00342 * Modifications to this software may be copyrighted by their authors 00343 * and need not follow the licensing terms described here, provided that 00344 * the new terms are clearly indicated on the first page of each file where 00345 * they apply. 00346 */ 00347 00348 #include "cs3.h" 00349 00350 extern void __libc_init_array (void); 00351 00352 __attribute ((noreturn)) void __cs3_start_c (void){ 00353 unsigned regions = __cs3_region_num; 00354 const struct __cs3_region *rptr = __cs3_regions; 00355 00356 /* Initialize memory */ 00357 for (regions = __cs3_region_num, rptr = __cs3_regions; regions--; rptr++) { 00358 long long *src = (long long *)rptr->init; 00359 long long *dst = (long long *)rptr->data; 00360 unsigned limit = rptr->init_size; 00361 unsigned count; 00362 00363 if (src != dst) 00364 for (count = 0; count != limit; count += sizeof (long long)) 00365 *dst++ = *src++; 00366 else 00367 dst = (long long *)((char *)dst + limit); 00368 limit = rptr->zero_size; 00369 for (count = 0; count != limit; count += sizeof (long long)) 00370 *dst++ = 0; 00371 } 00372 00373 /* Run initializers. */ 00374 __libc_init_array (); 00375 00376 osKernelInitialize(); 00377 set_main_stack(); 00378 osThreadCreate(&os_thread_def_main, NULL); 00379 osKernelStart(); 00380 for (;;); 00381 } 00382 00383 #else 00384 00385 __attribute__((naked)) void software_init_hook (void) { 00386 __asm ( 00387 ".syntax unified\n" 00388 ".thumb\n" 00389 "movs r0,#0\n" 00390 "movs r1,#0\n" 00391 "mov r4,r0\n" 00392 "mov r5,r1\n" 00393 "ldr r0,= __libc_fini_array\n" 00394 "bl atexit\n" 00395 "bl __libc_init_array\n" 00396 "mov r0,r4\n" 00397 "mov r1,r5\n" 00398 "bl osKernelInitialize\n" 00399 "bl set_main_stack\n" 00400 "ldr r0,=os_thread_def_main\n" 00401 "movs r1,#0\n" 00402 "bl osThreadCreate\n" 00403 "bl osKernelStart\n" 00404 "bl exit\n" 00405 ); 00406 } 00407 00408 #endif 00409 00410 #elif defined (__ICCARM__) 00411 00412 extern int __low_level_init(void); 00413 extern void __iar_data_init3(void); 00414 extern void exit(int arg); 00415 00416 __noreturn __stackless void __cmain(void) { 00417 int a; 00418 00419 if (__low_level_init() != 0) { 00420 __iar_data_init3(); 00421 } 00422 osKernelInitialize(); 00423 osThreadCreate(&os_thread_def_main, NULL); 00424 a = osKernelStart(); 00425 exit(a); 00426 } 00427 00428 #endif 00429 00430 00431 /*---------------------------------------------------------------------------- 00432 * end of file 00433 *---------------------------------------------------------------------------*/ 00434 00435
Generated on Thu Jul 14 2022 02:41:33 by 1.7.2