This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

RTOS : Task switch during a time tick

Dear all,

I have to work with RL-RTX, and I have first look at the RTX traffic example. There is something I do not understand about task switching. Some years ago, I was working on a home-made RTOS, and the switch from a task to another could only occured at "kernel time" (that means at every time tick). If a task only used 50% of a tick time, the rest of the tick time was for "idle", and next task only starts after the kernel time at the end of the tick.
With the traffic example, it seems that when a task is delayed (by instance with os_dly_wait) during a tick time, another "ready" task can directly start, without waiting for the end of the tick time when the kernel will run.
Is it right? If yes, can you explain me how it works? (maybe the kernel runs to switch the tasks even if the time tick is not finished?)
Thanks !
Best regards

  • An RTOS is designed with the RT very much in mind, i.e. Real Time.

    So it normally allows a switch whenever a reason is found. Which may be that a task says: "I'm done". Or that the task sends a message that a higher-prio task has been waiting for. Or that an interrupt receives some data and makes this data available to some task.

    It is also common that the OS runs an internal clock at a higher speed than the normal time slices. If each slice is 10 clock ticks and one thread doesn't consume the full 10 ticks but gets ended after only 8 ticks, then the next thread can still start a full 10-tick slice instead of getting punished by getting only two ticks, i.e. the remainder of the slice time donated by the previous thread.

    So a good RTOS is not ticking forward like it would be playing sheet music, but is trying to instantly switch when an event makes a more prioritized thread runnable. This gives lower latencies when responding to events - i.e. "real time".

  • When a task is "blocked" for some reason the next task in the ready queue is run. The idle task is considered just another task that can run that is always ready. Task switching is not actually tied to the timer tick. There are cases that the timer tick MAY cause a task switch (a delay terminates, other waiting items timeout, but these timeouts are process, the tasks are placed in the ready queue and when the tick processing is over the highest priority ready task is run. The OS actually does not do a full saving of state of the task unless there is actually a task switch.

  • Thank you for your answer. I knew what you explain about the time slice, but my question was: what appens if the slice is 10 ticks, and one thread only uses for example 7.5 ticks. It seems that the 2nd part (0.5) of the 8th tick is then directly use by the next ready task in the queue.

  • Thank you. In my (old) opinion, the RT kernel had to choose at each end of tick what to do for the next one, i.e. looking for the ready task that has to run, and eventually apply a task switching.
    If "task switching is not actually tied to the timer tick", I understand that kernel job is less complex and is only about delay stuff. The task switching is controled by a "ready queue", but this queue is updated at any time, and not only at the tick time, right? (I am not sure to understand then "who" update this queue: the delay fonction by instance?).

  • If you have an OS that runs the system ticks at a higher frequency than the length of a normal time slice length, then the OS will switch instantly when a switch is possible. If the thread A gives up time (or gets interrupted) after 9.5 out of 10 ticks, then the new thread will get 10 ticks where the first tick is short - so it will end up getting a 9.5 tick slice. And in total 19 system ticks will have passed. If the first gives up just after 9 ticks, then the next gets almost 10 full ticks. If the first hands over after 3 ticks, then the next gets 10 ticks and the total time will be 13 ticks. If the first gives up after 0.5 ticks, then the second gets 10-0.5 = 9.5 ticks for a total of 10 ticks.

    The OS never spends time idling while waiting for the system timer to tick - the only reason for idling is if zero user threads is ready, i.e. all are waiting for some event to happen.

    Some OS runs tickless. I.e. they run the system timer at so high speed that if the first thread ends the slice early at maybe 0.9452 of the slice then the next thread still gets a 1.0000 length slice. If you have a processor that runs the timer at 10MHz speed and have 10ms long slices then the timer runs 100000 ticks for every time slice so it is totally irrelevant what value the timer has when the OS starts the next task - current timer + 100000 will be close enough to a 10ms slice. A 0.1us jitter of the system timer is irrelevant compared to a 10ms time slice. 32-bit processors has much easier to run "tickless" because they can use 32-bit timers that doesn't overflows so quickly. At 10MHz a 32-bit timer still only overflows every 400 seconds which is a huge time for an RTOS.

  • The OS will reevaluate what task to run whenever a thread or ISR generates a signal or posts a mail. Or whenever the system timer ticks the last tick of a time slice. Or when a thread donates time. Or when a sleep timer ends.

    So it isn't just at the end of a time slice that the OS can perform rescheduling. The OS kernel is an event processor. You send it an event when you post a mail. The ISR sends it events by using the signal or mailbox functions. The system timer sends it events. Any event is as good as another for rescheduling what thread to run.

  • As a footnote. If you have a very low-resolution system timer so you time slice on every system timer tick then a thread that donates time after 95% of the system tick can result in the next thread only getting 5% of a time slice before the timer ticks again. If the OS has access to maybe a prescaler counter it may view it could correct this issue by giving the next thread 105% time i.e. by setting a flag that the next system tick shouldn't result in a task switch. If the OS doesn't have access to any prescaler, then it will either have be extremely unfair or busy-loop until the next timer tick and not switch to the next thread until the system tick happens. So old OS with low-resolution system timers had a hard time trying to be fair.

    A normal workaround would be to program the system timer so a task switch happens on overflow. And an early task switch is then handling by clearing the timer to restart a full task switch. But that makes it hard to use the same timer for measuring delays. Especially when the processor registers also quickly overflows.

    But not many people selects 8-bit or even 16-bit processors anymore if they want to run an RTOS.