Morse Micro IoT SDK  2.10.4
mmosal.h
1/*
2 * Copyright 2021-2023 Morse Micro
3 *
4 * SPDX-License-Identifier: Apache-2.0
5 */
6
16#pragma once
17
18#include <stdbool.h>
19#include <stdint.h>
20#include <stdio.h>
21#include <stdlib.h>
22#include <string.h>
23
24#include "mmport.h"
25
26#ifdef __cplusplus
27extern "C"
28{
29#endif
30
40typedef void (*mmosal_app_init_cb_t)(void);
41
55int mmosal_main(mmosal_app_init_cb_t app_init_cb);
56
61/*
62 * ---------------------------------------------------------------------------------------------
63 */
64
84void *mmosal_malloc_(size_t size);
85
99void *mmosal_malloc_dbg(size_t size, const char *name, unsigned line_number);
100
106void mmosal_free(void *p);
107
116void *mmosal_realloc(void *ptr, size_t size);
117
126void *mmosal_calloc(size_t nitems, size_t size);
127
128#ifndef MMOSAL_TRACK_ALLOCATIONS
138#define mmosal_malloc(size) mmosal_malloc_(size)
139#else
140/* Note: we use function name because it should be shorter than the full filename path. */
150#define mmosal_malloc(size) mmosal_malloc_dbg(size, __func__, __LINE__)
151#endif
152
157/*
158 * ---------------------------------------------------------------------------------------------
159 */
160
174typedef void (*mmosal_task_fn_t)(void *arg);
175
178{
189};
190
202struct mmosal_task *mmosal_task_create(mmosal_task_fn_t task_fn,
203 void *argument,
204 enum mmosal_task_priority priority,
205 unsigned stack_size_u32,
206 const char *name);
207
215void mmosal_task_delete(struct mmosal_task *task);
216
222struct mmosal_task *mmosal_task_get_active(void);
223
228
234void mmosal_task_sleep(uint32_t duration_ms);
235
243#define MMOSAL_TASK_ENTER_CRITICAL() \
244 do { \
245 MMPORT_MEM_SYNC(); \
246 mmosal_task_enter_critical(); \
247 } while (0)
248
254#define MMOSAL_TASK_EXIT_CRITICAL() \
255 do { \
256 MMPORT_MEM_SYNC(); \
257 mmosal_task_exit_critical(); \
258 } while (0)
259
270
279
287
295
301const char *mmosal_task_name(void);
302
307/*
308 * ---------------------------------------------------------------------------------------------
309 */
310
326struct mmosal_mutex *mmosal_mutex_create(const char *name);
327
333void mmosal_mutex_delete(struct mmosal_mutex *mutex);
334
343bool mmosal_mutex_get(struct mmosal_mutex *mutex, uint32_t timeout_ms);
344
352bool mmosal_mutex_release(struct mmosal_mutex *mutex);
353
357#define MMOSAL_MUTEX_GET_INF(_mutex) \
358 do { \
359 bool ok__ = mmosal_mutex_get((_mutex), UINT32_MAX); \
360 MMOSAL_ASSERT(ok__); \
361 } while (0)
362
366#define MMOSAL_MUTEX_RELEASE(_mutex) \
367 do { \
368 bool ok__ = mmosal_mutex_release(_mutex); \
369 MMOSAL_ASSERT(ok__); \
370 } while (0)
371
379bool mmosal_mutex_is_held_by_active_task(struct mmosal_mutex *mutex);
380
385/*
386 * ---------------------------------------------------------------------------------------------
387 */
388
407struct mmosal_sem *mmosal_sem_create(unsigned max_count, unsigned initial_count, const char *name);
408
414void mmosal_sem_delete(struct mmosal_sem *sem);
415
425bool mmosal_sem_give(struct mmosal_sem *sem);
426
436bool mmosal_sem_give_from_isr(struct mmosal_sem *sem);
437
446bool mmosal_sem_wait(struct mmosal_sem *sem, uint32_t timeout_ms);
447
455uint32_t mmosal_sem_get_count(struct mmosal_sem *sem);
456
461/*
462 * ---------------------------------------------------------------------------------------------
463 */
464
480struct mmosal_semb *mmosal_semb_create(const char *name);
481
487void mmosal_semb_delete(struct mmosal_semb *semb);
488
498bool mmosal_semb_give(struct mmosal_semb *semb);
499
509bool mmosal_semb_give_from_isr(struct mmosal_semb *semb);
510
519bool mmosal_semb_wait(struct mmosal_semb *semb, uint32_t timeout_ms);
520
525/*
526 * ---------------------------------------------------------------------------------------------
527 */
528
546struct mmosal_queue *mmosal_queue_create(size_t num_items, size_t item_size, const char *name);
547
553void mmosal_queue_delete(struct mmosal_queue *queue);
554
568bool mmosal_queue_pop(struct mmosal_queue *queue, void *item, uint32_t timeout_ms);
569
583bool mmosal_queue_push(struct mmosal_queue *queue, const void *item, uint32_t timeout_ms);
584
596bool mmosal_queue_pop_from_isr(struct mmosal_queue *queue, void *item);
597
609bool mmosal_queue_push_from_isr(struct mmosal_queue *queue, const void *item);
610
615/*
616 * ---------------------------------------------------------------------------------------------
617 */
618
632uint32_t mmosal_get_time_ms(void);
633
639uint32_t mmosal_get_time_ticks(void);
640
647
665static inline bool mmosal_time_lt(uint32_t a, uint32_t b)
666{
667 return ((int32_t)(a - b)) < 0;
668}
669
687static inline bool mmosal_time_le(uint32_t a, uint32_t b)
688{
689 return ((int32_t)(a - b)) <= 0;
690}
691
708static inline uint32_t mmosal_time_max(uint32_t a, uint32_t b)
709{
710 if (mmosal_time_lt(a, b))
711 {
712 return b;
713 }
714 else
715 {
716 return a;
717 }
718}
719
727static inline bool mmosal_time_has_passed(uint32_t t)
728{
730}
731
736/*
737 * ---------------------------------------------------------------------------------------------
738 */
739
755struct mmosal_timer;
756
762typedef void (*timer_callback_t)(struct mmosal_timer *timer);
763
780struct mmosal_timer *mmosal_timer_create(const char *name,
781 uint32_t timer_period_ms,
782 bool auto_reload,
783 void *arg,
784 timer_callback_t callback);
785
791void mmosal_timer_delete(struct mmosal_timer *timer);
792
803bool mmosal_timer_start(struct mmosal_timer *timer);
804
812bool mmosal_timer_stop(struct mmosal_timer *timer);
813
824bool mmosal_timer_change_period(struct mmosal_timer *timer, uint32_t new_period);
825
833void *mmosal_timer_get_arg(struct mmosal_timer *timer);
834
842bool mmosal_is_timer_active(struct mmosal_timer *timer);
843
848/*
849 * ---------------------------------------------------------------------------------------------
850 */
851
860#ifndef MMOSAL_FILEID
862#define MMOSAL_FILEID 0
863#endif
864
869#ifndef MMOSAL_MAX_FAILURE_RECORDS
870#define MMOSAL_MAX_FAILURE_RECORDS 4
871#endif
872
875{
877 uint32_t pc;
879 uint32_t lr;
881 uint32_t fileid;
883 uint32_t line;
886 uint32_t platform_info[4];
887};
888
895void mmosal_log_failure_info(const struct mmosal_failure_info *info);
896
897#ifdef MMOSAL_NO_DEBUGLOG
899#define MMOSAL_LOG_FAILURE_INFO(...)
900#else
903#define MMOSAL_LOG_FAILURE_INFO(...) \
904 do { \
905 void *pc; \
906 struct mmosal_failure_info info = { \
907 .lr = (uint32_t)MMPORT_GET_LR(), \
908 .fileid = MMOSAL_FILEID, \
909 .line = __LINE__, \
910 .platform_info = { __VA_ARGS__ }, \
911 }; \
912 MMPORT_GET_PC(pc); \
913 info.pc = (uint32_t)pc; \
914 mmosal_log_failure_info(&info); \
915 } while (0)
916#endif
917
923void mmosal_impl_assert(void);
924
925/* Note that running with no assertions is untested and not recommended. */
926#ifndef MMOSAL_NOASSERT
933#ifndef MMOSAL_ASSERT
934#define MMOSAL_ASSERT(expr) \
935 do { \
936 if (!(expr)) \
937 { \
938 MMOSAL_LOG_FAILURE_INFO(0); \
939 mmosal_impl_assert(); \
940 while (1) \
941 { \
942 } \
943 } \
944 } while (0)
945#endif
946
954#ifndef MMOSAL_ASSERT_LOG_DATA
955#define MMOSAL_ASSERT_LOG_DATA(expr, ...) \
956 do { \
957 if (!(expr)) \
958 { \
959 MMOSAL_LOG_FAILURE_INFO(__VA_ARGS__); \
960 mmosal_impl_assert(); \
961 while (1) \
962 { \
963 } \
964 } \
965 } while (0)
966#endif
967#else
969#define MMOSAL_ASSERT(expr) (void)(expr)
971#define MMOSAL_ASSERT_LOG_DATA(expr, ...) (void)(expr)
972#endif
973
974#ifdef ENABLE_MMOSAL_DEV_ASSERT
976#define MMOSAL_DEV_ASSERT(x) MMOSAL_ASSERT(x)
979#define MMOSAL_DEV_ASSERT_LOG_DATA(x, ...) MMOSAL_ASSERT_LOG_DATA(x, __VA_ARGS__)
980#else
982#define MMOSAL_DEV_ASSERT(x) ((void)(x))
985#define MMOSAL_DEV_ASSERT_LOG_DATA(x, ...) ((void)(x))
986#endif
987
988#if defined(ENABLE_MANUAL_FAILURE_LOG_PROCESSING) && ENABLE_MANUAL_FAILURE_LOG_PROCESSING
1007bool mmosal_extract_failure_info(struct mmosal_failure_info *buf, uint32_t *failure_count);
1008#endif
1024int mmosal_printf(const char *format, ...);
1025
1039static inline bool mmosal_safer_strcpy(char *dst, const char *src, size_t size)
1040{
1041 bool ret;
1042
1043 if (size == 0)
1044 {
1045 return true;
1046 }
1047
1048 strncpy(dst, src, size);
1049
1050 ret = dst[size - 1] != '\0';
1051 dst[size - 1] = '\0';
1052 return ret;
1053}
1054
1066#ifndef MMOSAL_DEPRECATED_API_ENABLED
1069#define MMOSAL_DEPRECATED_API_ENABLED (1)
1070#endif
1071
1072#if MMOSAL_DEPRECATED_API_ENABLED
1073
1082void mmosal_task_join(struct mmosal_task *task);
1083
1099bool mmosal_task_wait_for_notification(uint32_t timeout_ms);
1100
1113void mmosal_task_notify(struct mmosal_task *task);
1114
1127void mmosal_task_notify_from_isr(struct mmosal_task *task);
1128
1129#endif
1130
1133#ifdef __cplusplus
1134}
1135#endif
1136
void mmosal_log_failure_info(const struct mmosal_failure_info *info)
Log failure information in a way that it is preserved across reboots so that it can be available for ...
void mmosal_impl_assert(void)
Assertion handler implementation.
void mmosal_task_join(struct mmosal_task *task)
Block until the given task has terminated.
void mmosal_task_notify_from_isr(struct mmosal_task *task)
Notifies a waiting task (mmosal_task_wait_for_notification()) that it can continue.
void mmosal_task_notify(struct mmosal_task *task)
Notifies a waiting task (mmosal_task_wait_for_notification()) that it can continue.
bool mmosal_task_wait_for_notification(uint32_t timeout_ms)
Blocks the current task until a notification is received.
int mmosal_main(mmosal_app_init_cb_t app_init_cb)
OS main function.
void(* mmosal_app_init_cb_t)(void)
Application initialization callback (see mmosal_main for details).
Definition: mmosal.h:40
void * mmosal_calloc(size_t nitems, size_t size)
Equivalent of standard library calloc().
void * mmosal_malloc_dbg(size_t size, const char *name, unsigned line_number)
Allocate memory of the given size and return a pointer to it (malloc) – debug version.
void mmosal_free(void *p)
Free the given memory allocation.
void * mmosal_malloc_(size_t size)
Allocate memory of the given size and return a pointer to it (malloc).
void * mmosal_realloc(void *ptr, size_t size)
Equivalent of standard library realloc().
int mmosal_printf(const char *format,...)
OS abstracted version of printf used by morselib.
static bool mmosal_safer_strcpy(char *dst, const char *src, size_t size)
A safer version of strncpy.
Definition: mmosal.h:1039
struct mmosal_mutex * mmosal_mutex_create(const char *name)
Create a new mutex.
bool mmosal_mutex_is_held_by_active_task(struct mmosal_mutex *mutex)
Check whether the given mutex is held by the active thread.
bool mmosal_mutex_release(struct mmosal_mutex *mutex)
Release a mutex.
void mmosal_mutex_delete(struct mmosal_mutex *mutex)
Delete a mutex.
bool mmosal_mutex_get(struct mmosal_mutex *mutex, uint32_t timeout_ms)
Acquire a mutex.
bool mmosal_queue_pop_from_isr(struct mmosal_queue *queue, void *item)
Pop an item from the queue (from ISR context).
struct mmosal_queue * mmosal_queue_create(size_t num_items, size_t item_size, const char *name)
Create a new queue.
bool mmosal_queue_push(struct mmosal_queue *queue, const void *item, uint32_t timeout_ms)
Push an item into the queue.
void mmosal_queue_delete(struct mmosal_queue *queue)
Delete a queue.
bool mmosal_queue_push_from_isr(struct mmosal_queue *queue, const void *item)
Push an item into the queue (from ISR context).
bool mmosal_queue_pop(struct mmosal_queue *queue, void *item, uint32_t timeout_ms)
Pop an item from the queue.
bool mmosal_semb_give_from_isr(struct mmosal_semb *semb)
Give a binary semaphore (from ISR context).
bool mmosal_semb_wait(struct mmosal_semb *semb, uint32_t timeout_ms)
Wait for a counting semaphore.
struct mmosal_semb * mmosal_semb_create(const char *name)
Create a new binary semaphore.
bool mmosal_semb_give(struct mmosal_semb *semb)
Give a binary semaphore.
void mmosal_semb_delete(struct mmosal_semb *semb)
Delete the given binary semaphore.
bool mmosal_sem_give(struct mmosal_sem *sem)
Give a counting semaphore.
void mmosal_sem_delete(struct mmosal_sem *sem)
Delete the given counting semaphore.
bool mmosal_sem_give_from_isr(struct mmosal_sem *sem)
Give a counting semaphore (from ISR context).
struct mmosal_sem * mmosal_sem_create(unsigned max_count, unsigned initial_count, const char *name)
Create a new counting semaphore.
uint32_t mmosal_sem_get_count(struct mmosal_sem *sem)
Returns the current count of the semaphore.
bool mmosal_sem_wait(struct mmosal_sem *sem, uint32_t timeout_ms)
Wait for a counting semaphore.
struct mmosal_task * mmosal_task_create(mmosal_task_fn_t task_fn, void *argument, enum mmosal_task_priority priority, unsigned stack_size_u32, const char *name)
Create a new task.
void mmosal_task_yield(void)
Yield the active task.
struct mmosal_task * mmosal_task_get_active(void)
Get the handle of the active task.
void mmosal_task_exit_critical(void)
Exit critical section.
void mmosal_enable_interrupts(void)
Enable interrupts.
const char * mmosal_task_name(void)
Get the name of the running task.
void mmosal_task_sleep(uint32_t duration_ms)
Sleep for a period of time, yielding during that time.
void(* mmosal_task_fn_t)(void *arg)
Type definition for task main functions.
Definition: mmosal.h:174
void mmosal_disable_interrupts(void)
Disable interrupts.
void mmosal_task_delete(struct mmosal_task *task)
Delete the given task.
void mmosal_task_enter_critical(void)
Enter critical section.
mmosal_task_priority
Enumeration of task priorities (ordered lowest to highest).
Definition: mmosal.h:178
@ MMOSAL_TASK_PRI_LOW
Low priority.
Definition: mmosal.h:184
@ MMOSAL_TASK_PRI_MIN
Minimum priority.
Definition: mmosal.h:182
@ MMOSAL_TASK_PRI_HIGH
High priority.
Definition: mmosal.h:188
@ MMOSAL_TASK_PRI_NORM
Normal priority.
Definition: mmosal.h:186
@ MMOSAL_TASK_PRI_IDLE
Idle task priority.
Definition: mmosal.h:180
bool mmosal_timer_start(struct mmosal_timer *timer)
Start a timer.
void mmosal_timer_delete(struct mmosal_timer *timer)
Delete a timer.
bool mmosal_timer_change_period(struct mmosal_timer *timer, uint32_t new_period)
Change timer period.
bool mmosal_is_timer_active(struct mmosal_timer *timer)
Queries the timer to determine if it running.
void * mmosal_timer_get_arg(struct mmosal_timer *timer)
Get the opaque argument associated with a given timer.
void(* timer_callback_t)(struct mmosal_timer *timer)
Function type definition for timer callbacks.
Definition: mmosal.h:762
bool mmosal_timer_stop(struct mmosal_timer *timer)
Stop a timer.
struct mmosal_timer * mmosal_timer_create(const char *name, uint32_t timer_period_ms, bool auto_reload, void *arg, timer_callback_t callback)
Create a new timer.
uint32_t mmosal_get_time_ms(void)
Get the system time in milliseconds.
static uint32_t mmosal_time_max(uint32_t a, uint32_t b)
Given two times, return the one that is greatest (taking into account wrapping).
Definition: mmosal.h:708
uint32_t mmosal_ticks_per_second(void)
Get the number of ticks in a second.
static bool mmosal_time_le(uint32_t a, uint32_t b)
Check if time a is less than or equal to time b, taking into account wrapping.
Definition: mmosal.h:687
uint32_t mmosal_get_time_ticks(void)
Get the system time in ticks.
static bool mmosal_time_has_passed(uint32_t t)
Check if the given time has already passed.
Definition: mmosal.h:727
static bool mmosal_time_lt(uint32_t a, uint32_t b)
Check if time a is less than time b, taking into account wrapping.
Definition: mmosal.h:665
char buf[1408]
Statically allocated buffer for HTTP GET request, just under 1 packet size.
Definition: sslclient.c:176
Data structure used to store information about a failure that can be preserved across reset.
Definition: mmosal.h:875
uint32_t fileid
File identifier.
Definition: mmosal.h:881
uint32_t pc
Content of the PC register at assertion.
Definition: mmosal.h:877
uint32_t lr
Content of the LR register at assertion.
Definition: mmosal.h:879
uint32_t line
Source code line at which the assertion was triggered.
Definition: mmosal.h:883
uint32_t platform_info[4]
Arbitrary platform-specific failure info.
Definition: mmosal.h:886