Skip to content

Commit 7142787

Browse files
Support static allocation in Freertos example (#651)
* Add static allocation Freertos example * Fix some code review issues
1 parent 996867c commit 7142787

File tree

4 files changed

+83
-26
lines changed

4 files changed

+83
-26
lines changed

README.md

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,7 +120,9 @@ These examples require you to set the `FREERTOS_KERNEL_PATH` to point to the Fre
120120

121121
App|Description
122122
---|---
123-
[hello_freertos](freertos/hello_freertos) | Examples that demonstrate how run FreeRTOS and tasks on 1 or 2 cores.
123+
[hello_freertos_one_core](freertos/hello_freertos) | Demonstrates how run FreeRTOS and tasks on one core
124+
[hello_freertos_two_cores](freertos/hello_freertos) | Demonstrates how run FreeRTOS and tasks on two cores.
125+
[hello_freertos_static_allocation](freertos/hello_freertos) | Demonstrates how run FreeRTOS on two cores with static RAM allocation.
124126

125127
### GPIO
126128

freertos/FreeRTOSConfig_examples_common.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,8 +70,12 @@
7070
#define configMESSAGE_BUFFER_LENGTH_TYPE size_t
7171

7272
/* Memory allocation related definitions. */
73+
#ifndef configSUPPORT_STATIC_ALLOCATION
7374
#define configSUPPORT_STATIC_ALLOCATION 0
75+
#endif
76+
#ifndef configSUPPORT_DYNAMIC_ALLOCATION
7477
#define configSUPPORT_DYNAMIC_ALLOCATION 1
78+
#endif
7579
#define configTOTAL_HEAP_SIZE (128*1024)
7680
#define configAPPLICATION_ALLOCATED_HEAP 0
7781

Lines changed: 48 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,42 +1,74 @@
1-
set(TARGET_NAME hello_freertos1)
2-
add_executable(${TARGET_NAME}
1+
# Example running FreeRTOS on 1 core
2+
add_executable(hello_freertos_one_core
33
hello_freertos.c
44
)
5-
target_include_directories(${TARGET_NAME} PRIVATE
5+
target_include_directories(hello_freertos_one_core PRIVATE
66
${CMAKE_CURRENT_LIST_DIR}/..
77
)
8-
target_link_libraries(${TARGET_NAME} PRIVATE
8+
# Linking to FreeRTOS-Kernel-Heap4 means we use a dynamic heap for allocations
9+
target_link_libraries(hello_freertos_one_core PRIVATE
910
pico_async_context_freertos
1011
FreeRTOS-Kernel-Heap4
1112
pico_stdlib
1213
)
14+
# Set the nunber of cores to 1.
15+
# This defaults to 2 in FreeRTOSConfig_examples_common.h if not defined in here
16+
target_compile_definitions(hello_freertos_one_core PRIVATE
17+
configNUMBER_OF_CORES=1
18+
)
1319
if(PICO_CYW43_SUPPORTED)
1420
# For led support on pico_w
15-
target_link_libraries(${TARGET_NAME} PRIVATE
21+
target_link_libraries(hello_freertos_one_core PRIVATE
1622
pico_cyw43_arch_none
17-
)
23+
)
1824
endif()
19-
target_compile_definitions(${TARGET_NAME} PRIVATE
20-
configNUMBER_OF_CORES=1
21-
)
22-
pico_add_extra_outputs(${TARGET_NAME})
25+
pico_add_extra_outputs(hello_freertos_one_core)
2326

24-
set(TARGET_NAME hello_freertos2)
25-
add_executable(${TARGET_NAME}
27+
# Example running FreeRTOS on 2 cores
28+
add_executable(hello_freertos_two_cores
2629
hello_freertos.c
2730
)
28-
target_include_directories(${TARGET_NAME} PRIVATE
31+
target_include_directories(hello_freertos_two_cores PRIVATE
2932
${CMAKE_CURRENT_LIST_DIR}/..
3033
)
31-
target_link_libraries(${TARGET_NAME} PRIVATE
34+
# Linking to FreeRTOS-Kernel-Heap4 to use a dynamic heap for allocations
35+
target_link_libraries(hello_freertos_two_cores PRIVATE
3236
pico_async_context_freertos
3337
FreeRTOS-Kernel-Heap4
3438
pico_stdlib
3539
)
3640
if(PICO_CYW43_SUPPORTED)
3741
# For led support on pico_w
38-
target_link_libraries(${TARGET_NAME} PRIVATE
42+
target_link_libraries(hello_freertos_two_cores PRIVATE
3943
pico_cyw43_arch_none
44+
)
45+
endif()
46+
pico_add_extra_outputs(hello_freertos_two_cores)
47+
48+
# Example running FreeRTOS on 2 cores with static RAM allocation
49+
add_executable(hello_freertos_static_allocation
50+
hello_freertos.c
4051
)
52+
target_include_directories(hello_freertos_static_allocation PRIVATE
53+
${CMAKE_CURRENT_LIST_DIR}/..
54+
)
55+
# Linking to FreeRTOS-Kernel-Static to use static memory instead of a dynamic heap for allocations
56+
target_link_libraries(hello_freertos_static_allocation PRIVATE
57+
pico_async_context_freertos
58+
FreeRTOS-Kernel-Static
59+
pico_stdlib
60+
)
61+
# Change the configuration to just use static RAM allocation
62+
# If configSUPPORT_DYNAMIC_ALLOCATION is left undefined it will default to 1
63+
# If configSUPPORT_STATIC_ALLOCATION is left undefined it will default to 0
64+
target_compile_definitions(hello_freertos_static_allocation PRIVATE
65+
configSUPPORT_STATIC_ALLOCATION=1
66+
configSUPPORT_DYNAMIC_ALLOCATION=0
67+
)
68+
if(PICO_CYW43_SUPPORTED)
69+
# For led support on pico_w
70+
target_link_libraries(hello_freertos_static_allocation PRIVATE
71+
pico_cyw43_arch_none
72+
)
4173
endif()
42-
pico_add_extra_outputs(${TARGET_NAME})
74+
pico_add_extra_outputs(hello_freertos_static_allocation)

freertos/hello_freertos/hello_freertos.c

Lines changed: 28 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -48,18 +48,22 @@
4848
static async_context_freertos_t async_context_instance;
4949

5050
// Create an async context
51-
static async_context_t *example_async_context(void) {
51+
static async_context_t *create_async_context(void) {
5252
async_context_freertos_config_t config = async_context_freertos_default_config();
5353
config.task_priority = WORKER_TASK_PRIORITY; // defaults to ASYNC_CONTEXT_DEFAULT_FREERTOS_TASK_PRIORITY
5454
config.task_stack_size = WORKER_TASK_STACK_SIZE; // defaults to ASYNC_CONTEXT_DEFAULT_FREERTOS_TASK_STACK_SIZE
55+
#if configSUPPORT_STATIC_ALLOCATION
56+
static StackType_t async_context_freertos_task_stack[WORKER_TASK_STACK_SIZE];
57+
config.task_stack = async_context_freertos_task_stack;
58+
#endif
5559
if (!async_context_freertos_init(&async_context_instance, &config))
5660
return NULL;
5761
return &async_context_instance.core;
5862
}
5963

6064
#if USE_LED
6165
// Turn led on or off
62-
static void pico_set_led(bool led_on) {
66+
static void set_led(bool led_on) {
6367
#if defined PICO_DEFAULT_LED_PIN
6468
gpio_put(PICO_DEFAULT_LED_PIN, led_on);
6569
#elif defined(CYW43_WL_GPIO_LED_PIN)
@@ -68,20 +72,20 @@ static void pico_set_led(bool led_on) {
6872
}
6973

7074
// Initialise led
71-
static void pico_init_led(void) {
75+
static void init_led(void) {
7276
#if defined PICO_DEFAULT_LED_PIN
7377
gpio_init(PICO_DEFAULT_LED_PIN);
7478
gpio_set_dir(PICO_DEFAULT_LED_PIN, GPIO_OUT);
7579
#elif defined(CYW43_WL_GPIO_LED_PIN)
7680
hard_assert(cyw43_arch_init() == PICO_OK);
77-
pico_set_led(false); // make sure cyw43 is started
81+
set_led(false); // make sure cyw43 is started
7882
#endif
7983
}
8084

8185
void blink_task(__unused void *params) {
8286
bool on = false;
8387
printf("blink_task starts\n");
84-
pico_init_led();
88+
init_led();
8589
while (true) {
8690
#if configNUMBER_OF_CORES > 1
8791
static int last_core_id = -1;
@@ -90,7 +94,7 @@ void blink_task(__unused void *params) {
9094
printf("blink task is on core %d\n", last_core_id);
9195
}
9296
#endif
93-
pico_set_led(on);
97+
set_led(on);
9498
on = !on;
9599

96100
#if LED_BUSY_WAIT
@@ -122,13 +126,20 @@ static void do_work(async_context_t *context, async_at_time_worker_t *worker) {
122126
async_at_time_worker_t worker_timeout = { .do_work = do_work };
123127

124128
void main_task(__unused void *params) {
125-
async_context_t *context = example_async_context();
129+
async_context_t *context = create_async_context();
126130
// start the worker running
127131
async_context_add_at_time_worker_in_ms(context, &worker_timeout, 0);
128132
#if USE_LED
129133
// start the led blinking
134+
#if configSUPPORT_STATIC_ALLOCATION
135+
static StackType_t blink_stack[BLINK_TASK_STACK_SIZE];
136+
static StaticTask_t blink_buf;
137+
xTaskCreateStatic(blink_task, "BlinkThread", BLINK_TASK_STACK_SIZE, NULL, BLINK_TASK_PRIORITY, blink_stack, &blink_buf);
138+
#else
139+
static_assert(configSUPPORT_DYNAMIC_ALLOCATION, "");
130140
xTaskCreate(blink_task, "BlinkThread", BLINK_TASK_STACK_SIZE, NULL, BLINK_TASK_PRIORITY, NULL);
131-
#endif
141+
#endif // configSUPPORT_STATIC_ALLOCATION
142+
#endif // USE_LED
132143
int count = 0;
133144
while(true) {
134145
#if configNUMBER_OF_CORES > 1
@@ -146,11 +157,19 @@ void main_task(__unused void *params) {
146157

147158
void vLaunch( void) {
148159
TaskHandle_t task;
160+
#if configSUPPORT_STATIC_ALLOCATION
161+
static StackType_t main_stack[MAIN_TASK_STACK_SIZE];
162+
static StaticTask_t main_buf;
163+
task = xTaskCreateStatic(main_task, "MainThread", MAIN_TASK_STACK_SIZE, NULL, MAIN_TASK_PRIORITY, main_stack, &main_buf);
164+
#else
165+
static_assert(configSUPPORT_DYNAMIC_ALLOCATION, "");
149166
xTaskCreate(main_task, "MainThread", MAIN_TASK_STACK_SIZE, NULL, MAIN_TASK_PRIORITY, &task);
150-
167+
#endif // configSUPPORT_STATIC_ALLOCATION
151168
#if configUSE_CORE_AFFINITY && configNUMBER_OF_CORES > 1
152169
// we must bind the main task to one core (well at least while the init is called)
153170
vTaskCoreAffinitySet(task, 1);
171+
#else
172+
(void)task;
154173
#endif
155174

156175
/* Start the tasks and timer running. */

0 commit comments

Comments
 (0)