Quality RTOS & Embedded Software

 Real time embedded FreeRTOS RSS feed 
Real time embedded FreeRTOS mailing list 
Quick Start Supported MCUs PDF Books Trace Tools Ecosystem TCP & FAT Training




Loading

Preventing entry to sleep when using tickless idle

Posted by bryce78 on November 15, 2016

Hello Community,

I have a question about preventing ("turning off") entry to sleep during specific idle periods. For example, suppose I am performing a network provisioning task which involves a lot of waiting during which the MCU could go to sleep. But, for simplicity and to prevent continuous sleep-wake cycles, I wish to have the idle task run (skipping entry to sleep mode) until the network provisioning completes or timesout. Essentially I would like to control (select) either entry to low-power sleep, or simply remain idling.

Here is a little background on my project: I am using Keil uVision v5.20 for development with FreeRTOS v9.0.0 on STM32L471 ARM Cortex M4 MCU. My RTOS project defines 5 tasks, 4 of which use a Queue and wait for events to process, and the fifth uses Task Notifications to block until something happens. Some relevant configuration:

~~~

define configOVERRIDEDEFAULTTICK_CONFIGURTION 1
define configUSETICKLESSIDLE 2
define configUSEIDLEHOOK 0

~~~

I use 32.768kHz oscillator to drive low-power timer and generate the RTOS tick. I have the RTOS tick independent of the MCU SYSCLK so I can achieve longer sleep periods, and also I need to keep SYSCLK running at a low frequency while in SLEEP. To do all this I had to implemented my own portSUPPRESSTICKSAND_SLEEP() for tickless idle.

Back to the question of selecting either idle or sleep: I am thinking of introducing a simple global variable into the idle task which will determine whether the tickless idle code is skipped or run.

I think it's pretty simple but wouldn't mind a little feedback about this approach or more generally how to control entry to sleep mode. (For example, if portSUPPRESSTICKSAND_SLEEP() is to be skipped, perhaps I should call vApplicationIdleHook() to increment an idle time counter that could be cleared when any task wakes. It could be used to ensure a "minimum idle time" before allowing entry to sleep in general circumstances.)

Thanks for any suggestions! Bryce


Preventing entry to sleep when using tickless idle

Posted by edwards3 on November 15, 2016

The expected way would be to define a portPRESLEEPPROCESSING( x ) macro in FreeRTOSConfig.h. If sleep should not be entered set x to 0 in the macro.

What does setting configUSETICKLESSIDLE to 2 do?


Preventing entry to sleep when using tickless idle

Posted by bryce78 on November 16, 2016

Thanks for the reply!

Ah, yes, now I see that option to set x = 0 and cause the sleep to be skipped. I think that could work -- though the code will run right "up to" the sleep instruction and skip at the last possible chance. I think I'm looking for something a bit more "coarse" -- i.e. not stop the scheduler at all. I will keep this in mind and trying some other options. Thanks for reminding me of this possibility.

The #define configUSETICKLESSIDLE 2 setting doesn't add anything -- from what I saw looking at the code it just ensures the default vPortSetupTimerInterrupt() and portSUPPRESSTICKSANDSLEEP() and anything related to the default configUSETICKLESSIDLE == 1 setting (which assumes that SysTick is the source for RTOS tick) isn't compiled. According to website notes it appropriate when defining your own clock other than SysTick to generate the RTOS tick interrupt. There's some notes about it here and here.


Preventing entry to sleep when using tickless idle

Posted by bryce78 on November 16, 2016

To be more clear, I'm thinking more of an higher "application level" approach to preventing the idle task from entering into sleep, rather than lower "RTOS level". For example, during configuration of peripherals or devices there might be periods of idle (e.g. waiting for sensor to initialize), during which the application can be considered "busy waiting".

Is it possible (safe?) to suspend the idle task using vTaskSuspend()? Any special considerations for doing that?


Preventing entry to sleep when using tickless idle

Posted by edwards3 on November 16, 2016

You must always have a task to run, so if you suspend the idle task you must have an application task that can run. If all the tasks are blocked or suspended it will crash.

This will help http://www.freertos.org/a00021.html#xTaskGetCurrentTaskHandle


Preventing entry to sleep when using tickless idle

Posted by edwards3 on November 16, 2016

Correct link is http://www.freertos.org/a00021.html#xTaskGetIdleTaskHandle


Preventing entry to sleep when using tickless idle

Posted by mrazoun on November 16, 2016

Hi, I asked few weeks ago maybe the same question. You can look : https://sourceforge.net/p/freertos/discussion/382005/thread/063d54e8/ The conclusion was that you can move the responsibily to sleep_sleep which is EnergyMicro library function in our case. The usage of macros in FreeRTOS give you very strong possibilities. Thank's to FreeRTOS developers. Zdenek


Preventing entry to sleep when using tickless idle

Posted by bryce78 on November 17, 2016

Thanks for the info on what can happen if Idle task is suspended and there's nothing to run! I'll keep this information in mind!


Preventing entry to sleep when using tickless idle

Posted by bryce78 on November 18, 2016

Hello and thanks for the pointer to your thread! Definitely it's a question on the same topic. I've had a read from your thread and got further ideas! Plenty to work with now :)


Preventing entry to sleep when using tickless idle

Posted by xz8987f on November 18, 2016

Hi Bryce, I had the problem that I need to prevent entering low power or tickless idle mode in case there is some communication pending (e.g. UART). For this I have extended FreeRTOS with two defines:

~~~

define configUSETICKLESSIDLEDECISIONHOOK 1 /* set to 1 to enable application hook, zero otherwise */
define configUSETICKLESSIDLEDECISIONHOOK_NAME xEnterTicklessIdle /* function name of decision hook */

~~~ The first one turns on an extra hook, and the second one provides the name.

You can find an implementation on GitHub here: https://github.com/ErichStyger/Hexiwearv2/tree/master/KDS/HexiwearSDKv2/freertos/Source

The extension is in task.c https://github.com/ErichStyger/Hexiwearv2/blob/master/KDS/HexiwearSDKv2/freertos/Source/tasks.c around line 3336: ~~~ /* This conditional compilation should use inequality to 0, not equality to 1. This is to ensure portSUPPRESSTICKSANDSLEEP() is called when user defined low power mode implementations require configUSETICKLESSIDLE to be set to a value other than 1. */ #if ( configUSETICKLESSIDLE != 0 ) #if configUSETICKLESSIDLEDECISIONHOOK /* << EST */ if (configUSETICKLESSIDLEDECISIONHOOKNAME()) /* ask application if it shall enter tickless idle mode */ #endif { TickType_t xExpectedIdleTime;

		/* It is not desirable to suspend then resume the scheduler on
		each iteration of the idle task.  Therefore, a preliminary
		test of the expected idle time is performed without the
		scheduler suspended.  The result here is not necessarily
		valid. */

xExpectedIdleTime = prvGetExpectedIdleTime(); ~~~

Basically this extra hook allows the application to decide if the idle (and low power) mode really shall be entered. That approach worked really well for me. See as well https://mcuoneclipse.com/2014/02/09/iot-freertos-down-to-the-micro-amps/ and https://mcuoneclipse.com/2013/07/06/low-power-with-freertos-tickless-idle-mode/

I hope this helps, Erich


Preventing entry to sleep when using tickless idle

Posted by rtel on November 18, 2016

I think there might be an easier way because portSUPPRESSTICKSAND_SLEEP() is declared in a way that allows the user to override its default implementation by providing their own.

The default definition is as follows:

#ifndef portSUPPRESS_TICKS_AND_SLEEP
     extern void vPortSuppressTicksAndSleep( TickType_t xExpectedIdleTime );
     #define portSUPPRESS_TICKS_AND_SLEEP( xExpectedIdleTime ) 
vPortSuppressTicksAndSleep( xExpectedIdleTime )
#endif

To override the definition you can add your own implementation of portSUPPRESSTICKSAND_SLEEP into FreeRTOSConfig.h, and can use that definition to decide if you want to go into sleep mode or not. Something like the following to be added to FreeRTOSConfig.h:

extern void vPortSuppressTicksAndSleep( TickType_t xExpectedIdleTime );
#define portSUPPRESS_TICKS_AND_SLEEP( xExpectedIdleTime ) \
     if( AppWantsToEnterSleepMode() == pdTRUE )            \
     {                                                     \
         vPortSuppressTicksAndSleep( xExpectedIdleTime );  \
     }


[ Back to the top ]    [ About FreeRTOS ]    [ Sitemap ]    [ ]




Copyright (C) 2004-2010 Richard Barry. Copyright (C) 2010-2016 Real Time Engineers Ltd.
Any and all data, files, source code, html content and documentation included in the FreeRTOSTM distribution or available on this site are the exclusive property of Real Time Engineers Ltd.. See the files license.txt (included in the distribution) and this copyright notice for more information. FreeRTOSTM and FreeRTOS.orgTM are trade marks of Real Time Engineers Ltd.

Latest News:

FreeRTOS V9.0.0 is now available for download.


Free TCP/IP and file system demos for the RTOS


Sponsored Links

⇓ Now With No Code Size Limit! ⇓
⇑ Free Download Without Registering ⇑


FreeRTOS Partners

ARM Connected RTOS partner for all ARM microcontroller cores

Renesas Electronics Gold Alliance RTOS Partner.jpg

Microchip Premier RTOS Partner

RTOS partner of NXP for all NXP ARM microcontrollers

Atmel RTOS partner supporting ARM Cortex-M3 and AVR32 microcontrollers

STMicro RTOS partner supporting ARM7, ARM Cortex-M3, ARM Cortex-M4 and ARM Cortex-M0

Xilinx Microblaze and Zynq partner

Silicon Labs low power RTOS partner

Altera RTOS partner for Nios II and Cortex-A9 SoC

Freescale Alliance RTOS Member supporting ARM and ColdFire microcontrollers

Infineon ARM Cortex-M microcontrollers

Texas Instruments MCU Developer Network RTOS partner for ARM and MSP430 microcontrollers

Cypress RTOS partner supporting ARM Cortex-M3

Fujitsu RTOS partner supporting ARM Cortex-M3 and FM3

Microsemi (previously Actel) RTOS partner supporting ARM Cortex-M3

Atollic Partner

IAR Partner

Keil ARM Partner

Embedded Artists