| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575 |
- /*
- * Copyright (c) 2006-2021, RT-Thread Development Team
- *
- * SPDX-License-Identifier: Apache-2.0
- *
- * Change Logs:
- * Date Author Notes
- * 2022-04-27 tyustli The first version
- */
- #include <rtthread.h>
- #include <rtdbg.h>
- #include "cmsis_os.h"
- #define DEFAULT_TICK (5)
- #define DEFAULT_THREAD_STACK_SIZE (512)
- #define SIGNAL_ERROR_CODE (0x80000000)
- #define CMSIS_MEM_ALLOC(_size) rt_malloc(_size)
- #define CMSIS_MEM_FREE(_ptr) rt_free(_ptr)
- #define DBG_TAG "cmsis_rtos1"
- #ifdef PKG_USING_CMSIS_RTOS1_DBG
- #define DBG_LVL DBG_LOG
- #else
- #define DBG_LVL DBG_INFO
- #endif
- /* cmsis to rt-thread priority map */
- static const rt_uint8_t priorityArrayMap[7] =
- {
- RT_THREAD_PRIORITY_MAX - 1,
- RT_THREAD_PRIORITY_MAX - 1 - (RT_THREAD_PRIORITY_MAX / 6),
- RT_THREAD_PRIORITY_MAX - 1 - (RT_THREAD_PRIORITY_MAX / 3),
- RT_THREAD_PRIORITY_MAX / 2,
- RT_THREAD_PRIORITY_MAX / 3,
- RT_THREAD_PRIORITY_MAX / 6,
- 0,
- };
- /* Convert from CMSIS type osPriority to RT-Thread priority number */
- static rt_uint8_t makeRttPriority(osPriority priority)
- {
- rt_uint8_t rttPriority = RT_THREAD_PRIORITY_MAX;
- switch (priority)
- {
- case osPriorityIdle:
- rttPriority = priorityArrayMap[0];
- break;
- case osPriorityLow:
- rttPriority = priorityArrayMap[1];
- break;
- case osPriorityBelowNormal:
- rttPriority = priorityArrayMap[2];
- break;
- case osPriorityNormal:
- rttPriority = priorityArrayMap[3];
- break;
- case osPriorityAboveNormal:
- rttPriority = priorityArrayMap[4];
- break;
- case osPriorityHigh:
- rttPriority = priorityArrayMap[5];
- break;
- case osPriorityRealtime:
- rttPriority = priorityArrayMap[6];
- break;
- default:
- break;
- }
- return rttPriority;
- }
- /* Convert from RT-Thread priority number to CMSIS type osPriority */
- static osPriority makeCmsisPriority(rt_uint8_t rttPriority)
- {
- osPriority priority = osPriorityError;
- if (rttPriority == priorityArrayMap[0])
- priority = osPriorityIdle;
- else if (rttPriority == priorityArrayMap[1])
- priority = osPriorityLow;
- else if (rttPriority == priorityArrayMap[2])
- priority = osPriorityBelowNormal;
- else if (rttPriority == priorityArrayMap[3])
- priority = osPriorityNormal;
- else if (rttPriority == priorityArrayMap[4])
- priority = osPriorityAboveNormal;
- else if (rttPriority == priorityArrayMap[5])
- priority = osPriorityHigh;
- else if (rttPriority == priorityArrayMap[6])
- rttPriority = osPriorityRealtime;
- return priority;
- }
- /* Determine whether we are in thread mode or handler mode. */
- static int inHandlerMode(void)
- {
- return rt_interrupt_get_nest() != 0;
- }
- /*********************** Kernel Control Functions *****************************/
- /**
- * @brief Initialize the RTOS Kernel for creating objects.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osKernelInitialize shall be consistent in every CMSIS-RTOS.
- */
- osStatus osKernelInitialize(void)
- {
- return osOK;
- }
- /**
- * @brief Start the RTOS Kernel with executing the specified thread.
- * @param thread_def thread definition referenced with \ref osThread.
- * @param argument pointer that is passed to the thread function as start argument.
- * @retval status code that indicates the execution status of the function
- * @note MUST REMAIN UNCHANGED: \b osKernelStart shall be consistent in every CMSIS-RTOS.
- */
- osStatus osKernelStart(void)
- {
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- return osErrorISR;
- return osOK;
- }
- /**
- * @brief Check if the RTOS kernel is already started
- * @param None
- * @retval (0) RTOS is not started
- * (1) RTOS is started
- * @note MUST REMAIN UNCHANGED: \b osKernelRunning shall be consistent in every CMSIS-RTOS.
- */
- int32_t osKernelRunning(void)
- {
- if (rt_thread_self())
- return 1;
- else
- return 0;
- }
- /**
- * @brief Get the value of the Kernel SysTick timer
- * @param None
- * @retval None
- * @note MUST REMAIN UNCHANGED: \b osKernelSysTick shall be consistent in every CMSIS-RTOS.
- */
- uint32_t osKernelSysTick(void)
- {
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- return 0;
- return rt_tick_get();
- }
- /*********************** Thread Management *****************************/
- typedef struct os_thread_cb
- {
- rt_thread_t thread_id;
- rt_event_t event_id;
- } os_thread_cb_t;
- static void thread_cleanup(struct rt_thread *tid)
- {
- if (tid->user_data)
- {
- /* delete event */
- rt_event_delete(((struct os_thread_cb *)(tid->user_data))->event_id);
- /* free mem */
- CMSIS_MEM_FREE((void *)(tid->user_data));
- tid->user_data = RT_NULL;
- }
- }
- /**
- * @brief Create a thread and add it to Active Threads and set it to state READY.
- * @param thread_def thread definition referenced with \ref osThread.
- * @param argument pointer that is passed to the thread function as start argument.
- * @retval thread ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osThreadCreate shall be consistent in every CMSIS-RTOS.
- */
- osThreadId osThreadCreate(const osThreadDef_t *thread_def, void *argument)
- {
- static rt_uint8_t thread_number = 0;
- char name[RT_NAME_MAX];
- rt_uint8_t rttPriority = 0;
- rt_uint32_t stack_size = 0;
- void (*entry)(void *parameter);
- os_thread_cb_t *thread_cb = RT_NULL;
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- goto thread_create_failed;
- if (RT_NULL == thread_def || RT_NULL == thread_def->pthread)
- goto thread_create_failed;
- rt_snprintf(name, sizeof(name), "thread%02d", thread_number++); /* thread name */
- rttPriority = makeRttPriority(thread_def->tpriority); /* thread priority */
- entry = (void (*)(void *parameter))(thread_def->pthread); /* thread entry */
- stack_size = thread_def->stacksize; /* thread stack size */
- if (0 == thread_def->stacksize)
- stack_size = DEFAULT_THREAD_STACK_SIZE;
- thread_cb = (void *)CMSIS_MEM_ALLOC(sizeof(struct os_thread_cb));
- if (RT_NULL == thread_cb)
- goto thread_create_failed;
- thread_cb->thread_id = rt_thread_create(name,
- entry,
- argument,
- stack_size,
- rttPriority,
- DEFAULT_TICK);
- thread_cb->event_id = rt_event_create(name, RT_IPC_FLAG_PRIO);
- if (RT_NULL == thread_cb->thread_id || RT_NULL == thread_cb->event_id)
- goto thread_create_failed;
- thread_cb->thread_id->user_data = (rt_ubase_t)thread_cb;
- thread_cb->thread_id->cleanup = thread_cleanup; /* when thread done. event and mem must be free */
- /* start thread */
- rt_thread_startup(thread_cb->thread_id);
- return thread_cb;
- thread_create_failed:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- if (thread_cb)
- {
- if (thread_cb->thread_id)
- rt_thread_delete(thread_cb->thread_id);
- if (thread_cb->event_id)
- rt_event_delete(thread_cb->event_id);
- CMSIS_MEM_FREE(thread_cb);
- }
- return RT_NULL;
- }
- osStatus osThreadTerminate(osThreadId thread_id)
- {
- rt_err_t result;
- osStatus status;
- rt_thread_t thread;
- /* thread_id is incorrect */
- if (RT_NULL == thread_id)
- {
- status = osErrorParameter;
- goto thread_terminate_error;
- }
- thread = thread_id->thread_id;
- /* thread_id refers to a thread that is not an active thread. thread maybe done or has terminated*/
- if (rt_object_get_type((rt_object_t)thread) != RT_Object_Class_Thread)
- {
- status = osErrorResource;
- goto thread_terminate_error;
- }
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto thread_terminate_error;
- }
- result = rt_thread_control(thread, RT_THREAD_CTRL_CLOSE, RT_NULL);
- if (result != RT_EOK)
- {
- status = osErrorOS;
- goto thread_terminate_error;
- }
- return osOK;
- thread_terminate_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Pass control to next thread that is in state \b READY.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osThreadYield shall be consistent in every CMSIS-RTOS.
- */
- osStatus osThreadYield(void)
- {
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- return osErrorISR;
- rt_thread_yield();
- return osOK;
- }
- /**
- * @brief Return the thread ID of the current running thread.
- * @retval thread ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osThreadGetId shall be consistent in every CMSIS-RTOS.
- */
- osThreadId osThreadGetId(void)
- {
- rt_thread_t thread;
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- return RT_NULL;
- thread = rt_thread_self();
- return (osThreadId)(thread->user_data);
- }
- /**
- * @brief Change priority of an active thread.
- * @param thread_id thread ID obtained by \ref osThreadCreate or \ref osThreadGetId.
- * @param priority new priority value for the thread function.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osThreadSetPriority shall be consistent in every CMSIS-RTOS.
- */
- osStatus osThreadSetPriority(osThreadId thread_id, osPriority priority)
- {
- osStatus status;
- rt_err_t result;
- rt_uint8_t rttPriority = 0;
- rt_thread_t thread;
- /* thread_id is incorrect */
- if (RT_NULL == thread_id)
- {
- status = osErrorParameter;
- goto set_pri_error;
- }
- /* incorrect priority value */
- if (osPriorityError == priority)
- {
- status = osErrorValue;
- goto set_pri_error;
- }
- thread = thread_id->thread_id;
- /* thread_id refers to a thread that is not an active thread. thread maybe done or has terminated*/
- if (rt_object_get_type((rt_object_t)thread) != RT_Object_Class_Thread)
- {
- status = osErrorResource;
- goto set_pri_error;
- }
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto set_pri_error;
- }
- rttPriority = makeRttPriority(priority);
- result = rt_thread_control(thread, RT_THREAD_CTRL_CHANGE_PRIORITY, &rttPriority);
- if (result != RT_EOK)
- {
- status = osErrorOS;
- goto set_pri_error;
- }
- return osOK;
- set_pri_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Get current priority of an active thread.
- * @param thread_id thread ID obtained by \ref osThreadCreate or \ref osThreadGetId.
- * @retval current priority value of the thread function.
- * @note MUST REMAIN UNCHANGED: \b osThreadGetPriority shall be consistent in every CMSIS-RTOS.
- */
- osPriority osThreadGetPriority(osThreadId thread_id)
- {
- rt_thread_t thread;
- if (RT_NULL == thread_id)
- goto get_pri_error;
- thread = thread_id->thread_id;
- /* thread_id refers to a thread that is not an active thread. thread maybe done or has terminated*/
- if (rt_object_get_type((rt_object_t)thread) != RT_Object_Class_Thread)
- goto get_pri_error;
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- goto get_pri_error;
- return makeCmsisPriority(thread->current_priority);
- get_pri_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__);
- return osPriorityError;
- }
- /*********************** Generic Wait Functions *******************************/
- /**
- * @brief Wait for Timeout (Time Delay)
- * @param millisec time delay value
- * @retval status code that indicates the execution status of the function.
- */
- osStatus osDelay(uint32_t millisec)
- {
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- return osErrorISR;
- rt_thread_mdelay(millisec);
- return osOK;
- }
- #if (defined(osFeature_Wait) && (osFeature_Wait != 0)) /* Generic Wait available */
- /**
- * @brief Wait for Signal, Message, Mail, or Timeout
- * @param millisec timeout value or 0 in case of no time-out
- * @retval event that contains signal, message, or mail information or error code.
- * @note MUST REMAIN UNCHANGED: \b osWait shall be consistent in every CMSIS-RTOS.
- */
- osEvent osWait(uint32_t millisec)
- {
- osEvent event;
- event.status = osErrorOS;
- LOG_E("CMSIS RTOS1 %s failed. this function not implement", __func__);
- return event;
- }
- #endif /* Generic Wait available */
- /*********************** Timer Management Functions ***************************/
- /**
- * @brief Create a timer.
- * @param timer_def timer object referenced with \ref osTimer.
- * @param type osTimerOnce for one-shot or osTimerPeriodic for periodic behavior.
- * @param argument argument to the timer call back function.
- * @retval timer ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osTimerCreate shall be consistent in every CMSIS-RTOS.
- */
- osTimerId osTimerCreate(const osTimerDef_t *timer_def, os_timer_type type, void *argument)
- {
- rt_timer_t timer;
- static rt_uint16_t timer_number = 0U;
- rt_uint8_t flag = RT_TIMER_FLAG_SOFT_TIMER;
- char name[RT_NAME_MAX];
- void (*timeout_callback)(void *parameter);
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- goto timer_create_error;
- if (RT_NULL == timer_def || RT_NULL == timer_def->ptimer)
- goto timer_create_error;
- if (osTimerPeriodic == type)
- flag |= RT_TIMER_FLAG_PERIODIC;
- else if (osTimerOnce == type)
- flag |= RT_TIMER_FLAG_ONE_SHOT;
- else
- goto timer_create_error;
- rt_snprintf(name, sizeof(name), "timer%02d", timer_number++); /* timer name */
- timeout_callback = (void (*)(void *parameter))(timer_def->ptimer); /* timeout callback */
- timer = rt_timer_create(name,
- timeout_callback,
- argument,
- 0,
- flag);
- if (RT_NULL == timer)
- goto timer_create_error;
- return (osTimerId)timer;
- timer_create_error:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return RT_NULL;
- }
- /**
- * @brief Start or restart a timer.
- * @param timer_id timer ID obtained by \ref osTimerCreate.
- * @param millisec time delay value of the timer.
- * @retval status code that indicates the execution status of the function
- * @note MUST REMAIN UNCHANGED: \b osTimerStart shall be consistent in every CMSIS-RTOS.
- */
- osStatus osTimerStart(osTimerId timer_id, uint32_t millisec)
- {
- rt_err_t result;
- rt_tick_t ticks;
- osStatus status;
- /* timer_id is incorrect */
- if ((RT_NULL == timer_id))
- {
- status = osErrorParameter;
- goto timer_start_error;
- }
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto timer_start_error;
- }
- ticks = rt_tick_from_millisecond(millisec);
- result = rt_timer_control((rt_timer_t)timer_id, RT_TIMER_CTRL_SET_TIME, &ticks);
- if (result != RT_EOK)
- {
- status = osErrorOS;
- goto timer_start_error;
- }
- result = rt_timer_start((rt_timer_t)timer_id);
- if (result != RT_EOK)
- {
- status = osErrorOS;
- goto timer_start_error;
- }
- return osOK;
- timer_start_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Stop a timer.
- * @param timer_id timer ID obtained by \ref osTimerCreate
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osTimerStop shall be consistent in every CMSIS-RTOS.
- */
- osStatus osTimerStop(osTimerId timer_id)
- {
- rt_err_t result;
- rt_uint32_t timer_status;
- osStatus status;
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto timer_stop_error;
- }
- /* timer_id is incorrect */
- if (RT_NULL == timer_id)
- {
- status = osErrorParameter;
- goto timer_stop_error;
- }
- /* the timer is not started */
- rt_timer_control((rt_timer_t)timer_id, RT_TIMER_CTRL_GET_STATE, &timer_status);
- if (RT_TIMER_FLAG_ACTIVATED != timer_status)
- {
- status = osErrorResource;
- goto timer_stop_error;
- }
- result = rt_timer_stop((rt_timer_t)timer_id);
- if (result != RT_EOK)
- {
- status = osErrorOS;
- goto timer_stop_error;
- }
- return osOK;
- timer_stop_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Delete a timer.
- * @param timer_id timer ID obtained by \ref osTimerCreate
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osTimerDelete shall be consistent in every CMSIS-RTOS.
- */
- osStatus osTimerDelete(osTimerId timer_id)
- {
- rt_err_t result;
- osStatus status;
- /* timer_id is incorrect. */
- if (RT_NULL == timer_id)
- {
- status = osErrorParameter;
- goto timer_delete_error;
- }
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto timer_delete_error;
- }
- result = rt_timer_delete((rt_timer_t)timer_id);
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto timer_delete_error;
- }
- return osOK;
- timer_delete_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /*************************** Signal Management ********************************/
- /**
- * @brief Set the specified Signal Flags of an active thread.
- * @param thread_id thread ID obtained by \ref osThreadCreate or \ref osThreadGetId.
- * @param signals specifies the signal flags of the thread that should be set.
- * @retval previous signal flags of the specified thread or 0x80000000 in case of incorrect parameters.
- * @note MUST REMAIN UNCHANGED: \b osSignalSet shall be consistent in every CMSIS-RTOS.
- */
- int32_t osSignalSet(osThreadId thread_id, int32_t signal)
- {
- rt_event_t event;
- int32_t ret = SIGNAL_ERROR_CODE;
- rt_err_t result;
- if (RT_NULL == thread_id)
- goto signal_set_error;
- event = thread_id->event_id;
- /* previous signal flags of the specified thread */
- rt_enter_critical();
- ret = event->set;
- rt_exit_critical();
- result = rt_event_send(event, signal);
- if (RT_EOK != result)
- {
- ret = SIGNAL_ERROR_CODE;
- goto signal_set_error;
- }
- return ret;
- signal_set_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, ret);
- return SIGNAL_ERROR_CODE;
- }
- /**
- * @brief Clear the specified Signal Flags of an active thread.
- * @param thread_id thread ID obtained by \ref osThreadCreate or \ref osThreadGetId.
- * @param signals specifies the signal flags of the thread that shall be cleared.
- * @retval previous signal flags of the specified thread or 0x80000000 in case of incorrect parameters.
- * @note MUST REMAIN UNCHANGED: \b osSignalClear shall be consistent in every CMSIS-RTOS.
- */
- int32_t osSignalClear(osThreadId thread_id, int32_t signal)
- {
- rt_event_t event;
- int32_t ret = SIGNAL_ERROR_CODE;
- if (RT_NULL == thread_id)
- goto signal_clear_error;
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- goto signal_clear_error;
- event = thread_id->event_id;
- /* previous signal flags of the specified thread */
- rt_enter_critical();
- ret = event->set;
- rt_exit_critical();
- rt_event_control(event, RT_IPC_CMD_RESET, RT_NULL);
- return ret;
- signal_clear_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, ret);
- return SIGNAL_ERROR_CODE;
- }
- /**
- * @brief Wait for one or more Signal Flags to become signaled for the current \b RUNNING thread.
- * @param signals wait until all specified signal flags set or 0 for any single signal flag.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval event flag information or error code.
- * @note MUST REMAIN UNCHANGED: \b osSignalWait shall be consistent in every CMSIS-RTOS.
- */
- osEvent osSignalWait(int32_t signals, uint32_t millisec)
- {
- osEvent event;
- rt_event_t recv_event;
- osThreadId thread_cb;
- rt_uint32_t recved;
- rt_uint32_t ticks = 0;
- rt_err_t result;
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- {
- event.status = osErrorISR;
- goto signal_wait_error;
- }
- /* get receive event */
- thread_cb = osThreadGetId();
- recv_event = thread_cb->event_id;
- /* get timeout */
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- if (signals != 0)
- result = rt_event_recv(recv_event, signals, RT_EVENT_FLAG_AND | RT_EVENT_FLAG_CLEAR, ticks, &recved);
- else
- result = rt_event_recv(recv_event, signals, RT_EVENT_FLAG_OR | RT_EVENT_FLAG_CLEAR, ticks, &recved);
- if (-RT_ETIMEOUT == result)
- {
- event.status = osEventTimeout;
- goto signal_wait_error;
- }
- else if (RT_EOK != result)
- {
- event.status = osErrorOS;
- goto signal_wait_error;
- }
- event.status = osEventSignal;
- return event;
- signal_wait_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, event.status);
- return event;
- }
- /**************************** Mutex Management ********************************/
- /**
- * @brief Create and Initialize a Mutex object
- * @param mutex_def mutex definition referenced with \ref osMutex.
- * @retval mutex ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osMutexCreate shall be consistent in every CMSIS-RTOS.
- */
- osMutexId osMutexCreate(const osMutexDef_t *mutex_def)
- {
- #ifdef RT_USING_MUTEX
- static rt_uint16_t mutex_cnt = 0U;
- char name[RT_NAME_MAX];
- rt_mutex_t mutex;
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- goto mutex_create_failed;
- rt_snprintf(name, sizeof(name), "mutex%02d", mutex_cnt++); /* mutex name */
- mutex = rt_mutex_create(name, RT_IPC_FLAG_PRIO);
- if (RT_NULL == mutex)
- goto mutex_create_failed;
- return (osMutexId)mutex;
- mutex_create_failed:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return RT_NULL;
- #else /* not define RT_USING_MUTEX */
- return RT_NULL;
- #endif /* RT_USING_MUTEX */
- }
- /**
- * @brief Wait until a Mutex becomes available
- * @param mutex_id mutex ID obtained by \ref osMutexCreate.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osMutexWait shall be consistent in every CMSIS-RTOS.
- */
- osStatus osMutexWait(osMutexId mutex_id, uint32_t millisec)
- {
- rt_err_t result;
- osStatus status;
- rt_uint32_t ticks = 0;
- /* the parameter mutex_id is incorrect */
- if (RT_NULL == mutex_id)
- {
- status = osErrorParameter;
- goto mutex_wait_error;
- }
- /* the mutex could not be obtained when no timeout was specified */
- if (0 == millisec)
- {
- status = osErrorResource;
- goto mutex_wait_error;
- }
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto mutex_wait_error;
- }
- rt_enter_critical();
- if (((rt_mutex_t)mutex_id)->owner == rt_thread_self())
- {
- rt_exit_critical();
- status = osErrorOS;
- goto mutex_wait_error;
- }
- rt_exit_critical();
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- result = rt_mutex_take((rt_mutex_t)mutex_id, ticks);
- if (-RT_ETIMEOUT == result)
- {
- status = osErrorTimeoutResource;
- goto mutex_wait_error;
- }
- else if (RT_EOK != result)
- {
- status = osErrorOS;
- goto mutex_wait_error;
- }
- return osOK;
- mutex_wait_error:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return status;
- }
- /**
- * @brief Release a Mutex that was obtained by \ref osMutexWait
- * @param mutex_id mutex ID obtained by \ref osMutexCreate.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osMutexRelease shall be consistent in every CMSIS-RTOS.
- */
- osStatus osMutexRelease(osMutexId mutex_id)
- {
- rt_err_t result;
- osStatus status;
- /* the parameter mutex_id is incorrect */
- if (RT_NULL == mutex_id)
- {
- status = osErrorParameter;
- goto mutex_release_error;
- }
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto mutex_release_error;
- }
- /* the mutex was not obtained before */
- if (rt_object_get_type(&((rt_mutex_t)mutex_id)->parent.parent) != RT_Object_Class_Mutex)
- {
- status = osErrorResource;
- goto mutex_release_error;
- }
- result = rt_mutex_release((rt_mutex_t)mutex_id);
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto mutex_release_error;
- }
- return osOK;
- mutex_release_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Delete a Mutex
- * @param mutex_id mutex ID obtained by \ref osMutexCreate.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osMutexDelete shall be consistent in every CMSIS-RTOS.
- */
- osStatus osMutexDelete(osMutexId mutex_id)
- {
- osStatus status;
- rt_err_t result;
- /* Check parameters */
- if (RT_NULL == mutex_id)
- {
- status = osErrorParameter;
- goto mutex_delete_error;
- }
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto mutex_delete_error;
- }
- /* all tokens have already been released */
- if (rt_object_get_type(&((rt_mutex_t)mutex_id)->parent.parent) != RT_Object_Class_Mutex)
- {
- status = osErrorResource;
- goto mutex_delete_error;
- }
- result = rt_mutex_delete((rt_mutex_t)mutex_id);
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto mutex_delete_error;
- }
- return osOK;
- mutex_delete_error:
- LOG_E("CMSIS RTOS1 %s failed error code is :%d", __func__, status);
- return status;
- }
- /******************** Semaphore Management Functions **************************/
- #if (defined(osFeature_Semaphore) && (osFeature_Semaphore != 0))
- /**
- * @brief Create and Initialize a Semaphore object used for managing resources
- * @param semaphore_def semaphore definition referenced with \ref osSemaphore.
- * @param count number of available resources.
- * @retval semaphore ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osSemaphoreCreate shall be consistent in every CMSIS-RTOS.
- */
- osSemaphoreId osSemaphoreCreate(const osSemaphoreDef_t *semaphore_def, int32_t count)
- {
- #ifdef RT_USING_SEMAPHORE
- static rt_uint16_t sem_cnt = 0U;
- char name[RT_NAME_MAX];
- rt_sem_t sem;
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- goto sem_create_error;
- if (count < 0 || count > osFeature_Semaphore)
- goto sem_create_error;
- rt_snprintf(name, sizeof(name), "sem%02d", sem_cnt++);
- sem = rt_sem_create(name, count, RT_IPC_FLAG_PRIO);
- if (RT_NULL == sem)
- goto sem_create_error;
- return (osSemaphoreId)sem;
- sem_create_error:
- LOG_E("CMSIS RTOS1 %s failed error", __func__);
- return RT_NULL;
- #else /* not defined RT_USING_SEMAPHORE */
- return RT_NULL;
- #endif /* RT_USING_SEMAPHORE */
- }
- /* get semaphore cnt */
- static int32_t _osSemaphoreGetCount(osSemaphoreId semaphore_id)
- {
- rt_sem_t sem_cb = (rt_sem_t)semaphore_id;
- /* Check parameters */
- if ((RT_NULL == sem_cb) || (rt_object_get_type(&sem_cb->parent.parent) != RT_Object_Class_Semaphore))
- return 0U;
- return sem_cb->value;
- }
- /**
- * @brief Wait until a Semaphore token becomes available
- * @param semaphore_id semaphore object referenced with \ref osSemaphore.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval number of available tokens, or -1 in case of incorrect parameters.
- * @note MUST REMAIN UNCHANGED: \b osSemaphoreWait shall be consistent in every CMSIS-RTOS.
- */
- int32_t osSemaphoreWait(osSemaphoreId semaphore_id, uint32_t millisec)
- {
- rt_err_t result;
- rt_int32_t ticks = 0;
- if (RT_NULL == semaphore_id)
- goto sem_take_error;
- /* when millisec is set to osWaitForever the function will wait for an infinite time until the Semaphore token becomes available. */
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- /* when millisec is 0, the function returns instantly */
- if (0 == millisec)
- result = rt_sem_trytake((rt_sem_t)semaphore_id);
- else
- result = rt_sem_take((rt_sem_t)semaphore_id, ticks);
- if (RT_EOK != result)
- goto sem_take_error;
- return _osSemaphoreGetCount(semaphore_id);
- sem_take_error:
- LOG_E("CMSIS RTOS1 %s failed ", __func__);
- return 0; /* If 0 is returned, then no semaphore was available. */
- }
- /**
- * @brief Release a Semaphore token
- * @param semaphore_id semaphore object referenced with \ref osSemaphore.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osSemaphoreRelease shall be consistent in every CMSIS-RTOS.
- */
- osStatus osSemaphoreRelease(osSemaphoreId semaphore_id)
- {
- rt_err_t result;
- osStatus status;
- /* the parameter semaphore_id is incorrect. */
- if (RT_NULL == semaphore_id)
- {
- status = osErrorParameter;
- goto sem_release_error;
- }
- /* all tokens have already been released. */
- if (0 == _osSemaphoreGetCount(semaphore_id))
- {
- status = osErrorResource;
- goto sem_release_error;
- }
- result = rt_sem_release((rt_sem_t)semaphore_id);
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto sem_release_error;
- }
- return osOK;
- sem_release_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Delete a Semaphore
- * @param semaphore_id semaphore object referenced with \ref osSemaphore.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osSemaphoreDelete shall be consistent in every CMSIS-RTOS.
- */
- osStatus osSemaphoreDelete(osSemaphoreId semaphore_id)
- {
- rt_err_t result;
- osStatus status;
- /* the parameter semaphore_id is incorrect. */
- if (RT_NULL == semaphore_id)
- {
- status = osErrorParameter;
- goto sem_delete_error;
- }
- /* Cannot be called from Interrupt Service Routines */
- if (inHandlerMode())
- {
- status = osErrorISR;
- goto sem_delete_error;
- }
- /* the semaphore object could not be deleted. */
- if (rt_object_get_type((rt_object_t) & (((rt_sem_t)semaphore_id)->parent)) != RT_Object_Class_Semaphore)
- {
- status = osErrorResource;
- goto sem_delete_error;
- }
- result = rt_sem_delete((rt_sem_t)semaphore_id);
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto sem_delete_error;
- }
- return osOK;
- sem_delete_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- #endif /* Use Semaphores */
- /******************* Memory Pool Management Functions ***********************/
- #if (defined(osFeature_Pool) && (osFeature_Pool != 0))
- /**
- * @brief Create and Initialize a memory pool
- * @param pool_def memory pool definition referenced with \ref osPool.
- * @retval memory pool ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osPoolCreate shall be consistent in every CMSIS-RTOS.
- */
- osPoolId osPoolCreate(const osPoolDef_t *pool_def)
- {
- static rt_uint16_t mp_cnt = 0U;
- char name[RT_NAME_MAX];
- rt_mp_t mempool;
- rt_size_t block_size;
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- goto mp_create_error;
- if (RT_NULL == pool_def || 0 == pool_def->pool_sz || 0 == pool_def->item_sz)
- goto mp_create_error;
- rt_snprintf(name, sizeof(name), "mp%02d", mp_cnt++); /* name */
- block_size = RT_ALIGN(pool_def->item_sz, RT_ALIGN_SIZE); /* pool size */
- mempool = rt_mp_create(name, pool_def->pool_sz, block_size);
- if (RT_NULL == mempool)
- goto mp_create_error;
- return (osPoolId)mempool;
- mp_create_error:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return RT_NULL;
- }
- /**
- * @brief Allocate a memory block from a memory pool
- * @param pool_id memory pool ID obtain referenced with \ref osPoolCreate.
- * @retval address of the allocated memory block or NULL in case of no memory available.
- * @note MUST REMAIN UNCHANGED: \b osPoolAlloc shall be consistent in every CMSIS-RTOS.
- */
- void *osPoolAlloc(osPoolId pool_id)
- {
- /* Check parameters */
- if (RT_NULL == pool_id)
- return RT_NULL;
- return rt_mp_alloc((rt_mp_t)pool_id, RT_WAITING_FOREVER);
- }
- /**
- * @brief Allocate a memory block from a memory pool and set memory block to zero
- * @param pool_id memory pool ID obtain referenced with \ref osPoolCreate.
- * @retval address of the allocated memory block or NULL in case of no memory available.
- * @note MUST REMAIN UNCHANGED: \b osPoolCAlloc shall be consistent in every CMSIS-RTOS.
- */
- void *osPoolCAlloc(osPoolId pool_id)
- {
- void *p = osPoolAlloc(pool_id);
- if (p != NULL)
- rt_memset(p, 0, ((rt_mp_t)pool_id)->block_size);
- return p;
- }
- /**
- * @brief Return an allocated memory block back to a specific memory pool
- * @param pool_id memory pool ID obtain referenced with \ref osPoolCreate.
- * @param block address of the allocated memory block that is returned to the memory pool.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osPoolFree shall be consistent in every CMSIS-RTOS.
- */
- osStatus osPoolFree(osPoolId pool_id, void *block)
- {
- osStatus status;
- /* Check parameters */
- if (NULL == pool_id)
- {
- status = osErrorParameter;
- goto pool_free_error;
- }
- if (NULL == block)
- {
- status = osErrorParameter;
- goto pool_free_error;
- }
- rt_mp_free(block);
- block = RT_NULL;
- return osOK;
- pool_free_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- #endif /* Use Memory Pool Management */
- /******************* Message Queue Management Functions *********************/
- #if (defined(osFeature_MessageQ) && (osFeature_MessageQ != 0)) /* Use Message Queues */
- /**
- * @brief Create and Initialize a Message Queue
- * @param queue_def queue definition referenced with \ref osMessageQ.
- * @param thread_id thread ID (obtained by \ref osThreadCreate or \ref osThreadGetId) or NULL.
- * @retval message queue ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osMessageCreate shall be consistent in every CMSIS-RTOS.
- */
- osMessageQId osMessageCreate(const osMessageQDef_t *queue_def, osThreadId thread_id)
- {
- #ifdef RT_USING_MAILBOX
- (void)thread_id;
- static rt_uint16_t mailbox_cnt = 0U;
- char name[RT_NAME_MAX];
- rt_mailbox_t mailbox;
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- goto message_create_error;
- /* param error */
- if (RT_NULL == queue_def || 0 == queue_def->queue_sz || sizeof(void *) != queue_def->item_sz)
- goto message_create_error;
- rt_snprintf(name, sizeof(name), "mailbox%02d", mailbox_cnt++);
- mailbox = rt_mb_create(name, queue_def->queue_sz, RT_IPC_FLAG_PRIO);
- if (mailbox == RT_NULL)
- goto message_create_error;
- return (osMessageQId)mailbox;
- message_create_error:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return RT_NULL;
- #else /* RT_USING_MAILBOX */
- return RT_NULL;
- #endif /* not define RT_USING_MAILBOX */
- }
- /**
- * @brief Put a Message to a Queue.
- * @param queue_id message queue ID obtained with \ref osMessageCreate.
- * @param info message information.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osMessagePut shall be consistent in every CMSIS-RTOS.
- */
- osStatus osMessagePut(osMessageQId queue_id, uint32_t info, uint32_t millisec)
- {
- rt_err_t result;
- osStatus status;
- rt_mailbox_t mb_cb = (rt_mailbox_t)queue_id;
- rt_tick_t ticks = 0;
- if (RT_NULL == queue_id)
- {
- /* a parameter is invalid or outside of a permitted range */
- status = osErrorParameter;
- goto message_put_error;
- }
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- /* when millisec is 0, the function returns instantly */
- if (0 == millisec)
- result = rt_mb_send(mb_cb, info);
- else
- result = rt_mb_send_wait(mb_cb, info, ticks);
- if (-RT_EFULL == result)
- {
- /* no memory in the queue was available */
- status = osErrorResource;
- goto message_put_error;
- }
- else if (-RT_ETIMEOUT == result)
- {
- /* no memory in the queue was available during the given time limit. */
- status = osErrorTimeoutResource;
- goto message_put_error;
- }
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto message_put_error;
- }
- return osOK;
- message_put_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Get a Message or Wait for a Message from a Queue.
- * @param queue_id message queue ID obtained with \ref osMessageCreate.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval event information that includes status code.
- * @note MUST REMAIN UNCHANGED: \b osMessageGet shall be consistent in every CMSIS-RTOS.
- */
- osEvent osMessageGet(osMessageQId queue_id, uint32_t millisec)
- {
- osEvent event;
- rt_err_t result;
- rt_tick_t ticks = 0;
- if (RT_NULL == queue_id)
- {
- /* a parameter is invalid or outside of a permitted range */
- event.status = osErrorParameter;
- goto message_get_error;
- }
- event.def.message_id = queue_id;
- event.value.v = 0;
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- result = rt_mb_recv((rt_mailbox_t)queue_id, &(event.value.v), ticks);
- if (-RT_ETIMEOUT == result)
- {
- /* no message has arrived during the given timeout period */
- event.status = osEventTimeout;
- goto message_get_error;
- }
- else if (RT_EOK != result)
- {
- event.status = osErrorOS;
- goto message_get_error;
- }
- /* message received, value.p contains the pointer to message */
- event.status = osEventMessage;
- return event;
- message_get_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, event.status);
- return event;
- }
- #endif /* Use Message Queues */
- /******************** Mail Queue Management Functions ***********************/
- #if (defined(osFeature_MailQ) && (osFeature_MailQ != 0)) /* Use Mail Queues */
- typedef struct os_mailQ_cb
- {
- rt_mp_t mp_id;
- rt_mailbox_t mb_id;
- } os_mailQ_cb_t;
- /**
- * @brief Create and Initialize mail queue
- * @param queue_def reference to the mail queue definition obtain with \ref osMailQ
- * @param thread_id thread ID (obtained by \ref osThreadCreate or \ref osThreadGetId) or NULL.
- * @retval mail queue ID for reference by other functions or NULL in case of error.
- * @note MUST REMAIN UNCHANGED: \b osMailCreate shall be consistent in every CMSIS-RTOS.
- */
- osMailQId osMailCreate(const osMailQDef_t *queue_def, osThreadId thread_id)
- {
- #if defined(RT_USING_MEMPOOL) && defined(RT_USING_MAILBOX)
- (void)thread_id;
- os_mailQ_cb_t *ptr = RT_NULL;
- char name[RT_NAME_MAX];
- static rt_uint16_t mail_cnt = 0U;
- rt_size_t block_size;
- /* Cannot be called from Interrupt Service Routines. */
- if (inHandlerMode())
- goto mail_create_failed;
- if (RT_NULL == queue_def || 0 == queue_def->queue_sz || 0 == queue_def->item_sz)
- goto mail_create_failed;
- rt_snprintf(name, sizeof(name), "mb%02d", mail_cnt++);
- block_size = RT_ALIGN(queue_def->item_sz, RT_ALIGN_SIZE);
- ptr = (void *)CMSIS_MEM_ALLOC(sizeof(struct os_mailQ_cb));
- if (RT_NULL == ptr)
- goto mail_create_failed;
- ptr->mp_id = rt_mp_create(name, queue_def->queue_sz, block_size);
- ptr->mb_id = rt_mb_create(name, queue_def->queue_sz, RT_IPC_FLAG_PRIO);
- if ((RT_NULL == ptr->mp_id) || (RT_NULL == ptr->mb_id))
- goto mail_create_failed;
- return ptr;
- mail_create_failed:
- if (ptr)
- CMSIS_MEM_FREE(ptr);
- if (RT_NULL != ptr->mp_id)
- rt_mp_delete(ptr->mp_id);
- if (RT_NULL != ptr->mb_id)
- rt_mb_delete(ptr->mb_id);
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return RT_NULL;
- #else /* RT_USING_MEMPOOL && RT_USING_MAILBOX */
- return RT_NULL;
- #endif /* not define RT_USING_MEMPOOL && RT_USING_MAILBOX */
- }
- /**
- * @brief Allocate a memory block from a mail
- * @param queue_id mail queue ID obtained with \ref osMailCreate.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval pointer to memory block that can be filled with mail or NULL in case error.
- * @note MUST REMAIN UNCHANGED: \b osMailAlloc shall be consistent in every CMSIS-RTOS.
- */
- void *osMailAlloc(osMailQId queue_id, uint32_t millisec)
- {
- os_mailQ_cb_t *ptr = (os_mailQ_cb_t *)queue_id;
- void *ret = NULL;
- rt_tick_t ticks = 0;
- if (RT_NULL == ptr)
- goto mail_alloc_error;
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- ret = rt_mp_alloc(ptr->mp_id, ticks);
- if (RT_NULL == ret)
- goto mail_alloc_error;
- return ret;
- mail_alloc_error:
- LOG_E("CMSIS RTOS1 %s failed", __func__);
- return RT_NULL;
- }
- /**
- * @brief Allocate a memory block from a mail and set memory block to zero
- * @param queue_id mail queue ID obtained with \ref osMailCreate.
- * @param millisec timeout value or 0 in case of no time-out.
- * @retval pointer to memory block that can be filled with mail or NULL in case error.
- * @note MUST REMAIN UNCHANGED: \b osMailCAlloc shall be consistent in every CMSIS-RTOS.
- */
- void *osMailCAlloc(osMailQId queue_id, uint32_t millisec)
- {
- void *p = osMailAlloc(queue_id, millisec);
- if (p)
- rt_memset(p, 0, ((os_mailQ_cb_t *)queue_id)->mp_id->block_size);
- return p;
- }
- /**
- * @brief Put a mail to a queue
- * @param queue_id mail queue ID obtained with \ref osMailCreate.
- * @param mail memory block previously allocated with \ref osMailAlloc or \ref osMailCAlloc.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osMailPut shall be consistent in every CMSIS-RTOS.
- */
- osStatus osMailPut(osMailQId queue_id, void *mail)
- {
- osStatus status;
- os_mailQ_cb_t *ptr = (os_mailQ_cb_t *)queue_id;
- rt_err_t result;
- if (RT_NULL == ptr)
- {
- status = osErrorParameter;
- goto mail_put_error;
- }
- if (RT_NULL == mail)
- {
- status = osErrorValue;
- goto mail_put_error;
- }
- result = rt_mb_send((ptr->mb_id), (rt_ubase_t)mail);
- if (RT_EOK != result)
- {
- status = osErrorOS;
- goto mail_put_error;
- }
- return osOK;
- mail_put_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- /**
- * @brief Get a mail from a queue
- * @param queue_id mail queue ID obtained with \ref osMailCreate.
- * @param millisec timeout value or 0 in case of no time-out
- * @retval event that contains mail information or error code.
- * @note MUST REMAIN UNCHANGED: \b osMailGet shall be consistent in every CMSIS-RTOS.
- */
- osEvent osMailGet(osMailQId queue_id, uint32_t millisec)
- {
- osEvent event;
- os_mailQ_cb_t *ptr = (os_mailQ_cb_t *)queue_id;
- rt_err_t result;
- rt_ubase_t value;
- rt_tick_t ticks = 0;
- if (RT_NULL == ptr)
- {
- event.status = osErrorParameter;
- goto mail_get_error;
- }
- if (osWaitForever == millisec)
- ticks = RT_WAITING_FOREVER;
- else if (0U != millisec)
- ticks = rt_tick_from_millisecond(millisec);
- result = rt_mb_recv((ptr->mb_id), &value, ticks);
- if (-RT_ETIMEOUT == result)
- {
- event.status = osEventTimeout;
- goto mail_get_error;
- }
- else if (RT_EOK != result)
- {
- event.status = osErrorOS;
- goto mail_get_error;
- }
- event.value.p = (void *)value;
- event.status = osEventMail;
- return event;
- mail_get_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, event.status);
- return event;
- }
- /**
- * @brief Free a memory block from a mail
- * @param queue_id mail queue ID obtained with \ref osMailCreate.
- * @param mail pointer to the memory block that was obtained with \ref osMailGet.
- * @retval status code that indicates the execution status of the function.
- * @note MUST REMAIN UNCHANGED: \b osMailFree shall be consistent in every CMSIS-RTOS.
- */
- osStatus osMailFree(osMailQId queue_id, void *mail)
- {
- osStatus status;
- os_mailQ_cb_t *ptr = (os_mailQ_cb_t *)queue_id;
- if (RT_NULL == ptr)
- {
- status = osErrorParameter;
- goto mail_free_error;
- }
- if (RT_NULL == mail)
- {
- status = osErrorValue;
- goto mail_free_error;
- }
- rt_mp_free(mail);
- mail = RT_NULL;
- return osOK;
- mail_free_error:
- LOG_E("CMSIS RTOS1 %s failed error code is : 0x%x", __func__, status);
- return status;
- }
- #endif /* Use Mail Queues */
- /****************************** end of file ******************************/
|