Multitasking is something we take for granted these days. Just about every computer we use, from our desktops to our phones, is capable of multitasking. It might sound silly to implement multitasking on lower-spec machines from many decades ago, given their limited resources, but it can be done, as [bchiha] demonstrates on a Z80-based machine.
[bchiha] has achieved pre-emptive multitasking on the TEC-1G Z80 computer, a modern reimagining of the classic Talking Electronics TEC-1 from the 1980s. The proof of concept code allows running up to eight separate tasks at once. Task switching runs on interrupts, triggered at approximately 50 Hz. When an interrupt fires, the CPU registers are transferred onto that task’s stack, and the next task’s stack is swapped to the stack pointer to allow execution of the new task to proceed. There is an overhead, of course, with [bchiha] noting that the task swapping routine itself takes about 430 clock cycles to run in between tasks.
Multitasking took some time to appear on home computers for good reason—it’s not very useful unless you have a machine with enough power to practically run multiple tasks at once. While a Z80 machine like this can do multitasking, you’d better hope each task is pretty tiny to avoid each individual task taking forever to run.
[bchiha] has made the simple multitasking code available on Github for the curious. We’ve featured multitasking work on other unconventional platforms before, too, like the Arduino Uno. Video after the break.
[Thanks to Stephen Walters for the tip!]

there is another significant reason for multitasking – many tasks have to wait for things, and it is often easier to do that in a full task than an interrupt – particularly if your processor is connected to a lot of different things (ie I often have every pin of my esp32 doing something…). So many tasks might be sleeping much of the time..
Even for the z80 this would be true..
Z80 is plenty capable of doing some task switching. Older machines (such as the PDP series) first did batch processing, but multi tasking kernels were quickly developed so many users could use the single (and expensive) computer at the same time. I guess that’s also much more efficient then having the hardware idling while a single person is feeding in stacks of punch cards from different users. The history of how these things evolved is quite interesting.
And tasks for the Z80 do not have to be that tiny. In the example here, all tasks probably use software loop delays to set a certain speed, and that is very bad (arduino like) practice. One of the main parts to make multi tasking efficient, is to use an event driven system. Then the CPU is mostly idling in an empty loop (somewhere in the OS) and a user program only gets cpu cycles if it has something to do (such as refreshing a display, or scanning a keyboard). It is also common for an RTOS to deliver timing services to the applications.
Spending 40s to use the solver of an HP27S to calculate an RC constant is also quite silly. (And so is entering a whole lot of zero’s instead of using an exponent) Maybe a video such as this can help with getting people interested in task switching, but overall there are much better tutorials “out there”. I quite liked the introduction of using an RTOS that was (is?) part of FreeRTOS, but it’s been years since I read it. Apparently ChibiOS is a very small and well written RTOS, but I never used it.
I mostly did my programming for AVR’s, and they are a bit annoying for the task switching part, as they have many registers that have to be saved. Applications are usually also so small that there is not much advantage for using an RTOS. When using an uC such as the ARM Cortex-M series, there is more incentive for using an RTOS. It has much more resources, including more memory and a multi level ISR controller that can be put to good use in an RTOS.
An RTOS can also be used to make code better readable, and re-usable. But there is also the trap of writing more complex “generic” code for the sake of being able to reuse it in another project, while simpler & faster code that just does what is needed for an application is often a better compromise.
There’s also SymbOS, an operating system including a full desktop environment and multitasking for Z80 machines like MSX2 and Amstrad CPC.