This application provides an example of Azure RTOS ThreadX stack usage, it shows how to develop an application using ThreadX low power feature. It demonstrates how to configure the LowPower feature of Azure RTOS ThreadX stack. In addition, it shows how to use ThreadX MACRO related to the LowPower feature. The main entry function tx_application_define() is then called by ThreadX during kernel start, at this stage, the application creates 1 thread and 1 semaphore:
MainThread (Prio : 10; Preemption Threshold : 10)
Semaphore (Initial count = 0 to prevent its acquisition by the MainThread, on the application start)
‘MainThread’:
When the “tx_app_thread” is in suspended state, waiting for the ‘Semaphore’, the system is in idle state and the scheduler decides to enter in low power mode by calling the TX_LOW_POWER_USER_ENTER that makes the system enter the STOP Mode via the HAL_PWR_EnterSTOPMode() API.
As soon as the User button is pressed, the ‘Semaphore’ is released, and the ‘tx_app_thread’ passes in Active state.
The scheduler exits the STOP Mode by calling the TX_LOW_POWER_EXIT.
In System STOP Mode, all I/O pins keep the same state as in Run mode.
When exiting the STOP Mode, the MCU is in Run mode (Range 1 or Range 2 depending on VOS bit in PWR_CR1).
On failure, an error message is printed to the serial port.
None
None
tx_low_power_enter() service enters low power mode. For keeping track of time while in low power mode, there are two possibilities:
1.1. A ThreadX timer is active: Function tx_timer_get_next returns TX_TRUE.
Note that in this situation, a low power clock must be used in order to wake up the CPU for the next ThreadX timer expiration.
Therefore an alternative clock must be programmed. Program the hardware timer source such that the next timer interrupt is equal to: tx_low_power_next_expiration tick_frequency. The tick_frequency is application-specific and typically set up in tx_low_level_initialize.
1.2. There are no ThreadX timers active: Function tx_timer_get_next returns TX_FALSE.
1.2.1. The application may choose not to keep the ThreadX internal
tick count updated (define **TX_LOW_POWER_TICKLESS**), therefore there is no need
to set up a low power clock.
1.2.2. The application still needs to keep the ThreadX tick up-to-date. In this case a low power clock needs to be set up.
Entering Low-power mode through WFI will be executed only if no interrupt is pending.
The Debug Module must be stopped during STOP Mode, otherwise, It will generate interrupts that cause the Wake-up of the system immediately after entering the STOP Mode.
The user push-button interrupt priority must be set to the highest possible value, otherwise, after exiting STOP Mode the processor will not execute the interrupt handler.
To optimize the application footprint, the following ThreadX configuration options should be enabled in the tx_user.h file:
#define TX_DISABLE_PREEMPTION_THRESHOLD
#define TX_DISABLE_NOTIFY_CALLBACKS
#define TX_DISABLE_REDUNDANT_CLEARING
#define TX_DISABLE_STACK_FILLING
#define TX_NOT_INTERRUPTABLE
#define TX_TIMER_PROCESS_IN_ISR
#define TX_DISABLE_ERROR_CHECKING
For EWARM add the following section into the .icf file:
place in RAM_region { last section FREE_MEM };
For MDK-ARM:
either define the RW_IRAM1 region in the ".sct" file or modify the line below in "tx_initialize_low_level.S" to match the memory region being used LDR r1, =|Image$$RW_IRAM1$$ZI$$Limit|
For STM32CubeIDE add the following section into the .ld file:
._threadx_heap : { . = ALIGN(8); __RAM_segment_used_end__ = .; . = . + 64K; . = ALIGN(8); } >RAM_D1 AT> RAM_D1
The simplest way to provide memory for ThreadX is to define a new section, see ._threadx_heap above. In the example above the ThreadX heap size is set to 64KBytes. The ._threadx_heap must be located between the .bss and the ._user_heap_stack sections in the linker script. Caution: Make sure that ThreadX does not need more than the provided heap memory (64KBytes in this example). Read more in STM32CubeIDE User Guide, chapter: “Linker script”.
The “tx_initialize_low_level.S” should be also modified to enable the “USE_DYNAMIC_MEMORY_ALLOCATION” flag.
RTOS, ThreadX, Threading, Semaphore, PWR, STOP Mode, Interrupt, EXTI, Wakeup, LowPower
This application runs on STM32C031C6Tx devices.
This application has been tested with STMicroelectronics NUCLEO-C031C6 boards Revision MB1717 B-01 and can be easily tailored to any other supported device and development board.
This application uses USART2 to display error messages, the hyperterminal configuration is as follows:
In order to make the program work, you must do the following: