25 Jun Zephyr in the age of IoT
Zephyr in the age of IoT
Javad Rahimipetroudi
24/06/2024
Not a long time ago, embedded software engineers had a hard life. A sole engineer, a CRT monitor, a parallel port debugger and a huge size microcontroller were shaping our world. The available BSPs were buggy, and no fancy IDEs were available. At that time our knowledge was transferred by floppy disk, or CDs. Porting new sensors was a tearful tragedy for us. A sensor with a low-quality black-and-white copied datasheet, an upcoming deadline, and an angry technical manager behind the doors were all we had in our hands to do our jobs. Developing the firmware was one side of the story, and making it stabilize and fixing the potential bugs was the other side.
To make it worse, semiconductor companies had a monopoly in the market, and we were left with no option but to use all products from a single vendor such as assemblers and compilers, without the right to question or criticize.
As time passed, however, we learned to cooperate. We realized that sharing what we have and helping each other build something better is the only way to survive. It started with the Free Software movement, hobbyists and university students writing software that is shared with the world. It turned out that businesses adopted this concept, because collaboration just yields better results cheaper than if everyone has to reinvent the wheel.
Very slowly, Free Software also entered the commercial embedded systems world. It started with the toolchains that almost completely got replaced with GCC, then Eclipse that became the framework that formed the basis is the chip vendor’s IDEs. However, the software running on the microcontrollers themselves remained largely proprietary. There are quite a few open source operating systems for microcontrollers, but none of them really broke through to total market domination like Linux did for the larger embedded systems.
This changed about two years ago, with the arrival of Zephyr. Although it is based on Virtuoso which is already more than 20 years old, and it has been open source collaborative project under the Linux Foundation for almost 8 years, it is only in the last two years that Zephyr has seen an explosive growth and is quickly becoming the be all and end all of operating systems for microcontrollers.
Why Zephyr?
Let’s consider a scenario. Your company has a new project with a very nice financial margin. You made a contract, and everything is already written and signed with the customer. Everything is fine, life is beautiful, and every day you wake up and start working on the project. You know the customer’s needs, you know your microcontroller device for a long time such that you have ever memorized all of the errata that have been published by the vendor. The demo board is ready and you are working on it.
After a while, the customer requests you for changes in the final product. Okay, “The customer is the king”. You prefer to modify the firmware rather than facing with your boss’s red angry face. After applying the changes, the final product is ready to go. However, the worst thing that you may imagine happens. Your manager informs you that the customer also requests network-based connectivity for this project. They claimed that “another company can design the same project with the same costs by using a new microcontroller that also provides connectivity”. “As it is a vital project, we have to do it. Otherwise, the customer will cancel the project without paying a penny”, your manager said
“What? It is impossible! All ports are used. No DMA, No Mac layer, nothing at all. Even if they were available, the CPU is working at full capacity. It is necessary to use a different microcontroller to meet the customer’s requirements”, you said.
As you may guess, the project fails and you’ll need to start searching for a new job.
The situation described above is a frequent occurrence in the field of embedded systems. Embedded system development is the art of combining software and hardware while taking into account customer needs and budgetary constraints. We work with a diverse range of applications, varying client requirements, and even different types of hardware. On the other hand, developing firmware requires a deep understanding of the underlying microcontroller, its limitations, its tips and tricks, and anything that may affect the final product. Furthermore, interfacing with such a huge number of available sensors and actuators in the market, stabilizing the drivers, fixing bugs, etc… As you can see using a different controlling unit is not just finding a better device.
How can we increase our project’s safety margin and reduce the failure rate while not overburdening our available resources?
We have a good experience with the Linux operating system. With available frameworks such as Buildroot, Yocto, etc., porting it to a new platform, although not necessarily easy, can certainly be done straightforwardly. So, is it possible to have a Linux-like OS for MCUs?
This is where Zephyr comes into play. With Zephyr, application code can be written mostly independently from the hardware, thus making it easy to replace the hardware with something else when the need arises.
What is Zephyr
Based on the official definition:
The Zephyr OS is based on a small-footprint kernel designed for use on resource-constrained and embedded systems: from simple embedded environmental sensors and LED wearables to sophisticated embedded controllers, smart watches, and IoT wireless applications.
It provides full support for a wide range of microcontrollers from major players in the market, as well as a wide range of peripherals.
It is an operating system. Here the first question arises. does it require a lot of memory and space to run? The short answer is no. By disabling multithreading support, its footprint can be reduced to 4-5 KB. If the timer is also disabled, it will only need 2 KB to run [1].
In addition to the core RTOS, Zephyr offers:
- A platform that isolates the developer from the underlying hardware,
- Support for a wide variety of platforms,
- Support for many available sensors/actuators,
- Strong support of the connectivity stack (we are living in the age of [A]IoT, do you agree?),
- POSIX support
- Customizability
- FoF (Fire and Forget) feature (build/flash/run with a single command)
- Strong Community support
- Freedom
Platform isolation
This feature is the most important and life-saving feature of the Zephyr that may save us from a job loss. Switching from one hardware to another hardware is just like slicing a cake. You only need to change the name of the hardware in the build command.
For example, you are working on a Rasberry Pico platform to prototype your project. You can build it with:
west build -f -p -b rpi_pico samples/basic/blinky
Now, after a while, you see that this device is not suitable enough for your project. You can simply switch to another project by changing the board name:
west build -f -p -b stm32h573i_dk samples/basic/blinky
Zephyr comes with over 500 off-the-shelf boards across multiple architectures including ARM, MIPS, RISC-V, SPARC. It is easy to create your own custom board based on one of those by writing or modifying a Device Tree file.
The same applies to support for peripherals. By following a consistent device driver model, adding and reusing a device is far simpler than bare metal application development paradigms. The application code doesn’t access a peripheral directly, but instead it uses one of the many APIs provided by Zephyr to make abstraction of the device, while the Device Tree links it to the concrete model of peripheral that is used on the board.
Just consider we are going to use a i2c light sensor in our project, we can simply add it to our project by adding its node to the project device three overlay file (as we do in Linux-based projects):
&i2c2 {
veml6030:veml6030@10 {
compatible = “vishay,veml6030”;
reg = <0x10>;
label = “Ambient Light Sensor”;
status = “okay”;
};
status = “okay”;
};
Such abstraction typically comes at the cost of a lot of overhead and indirection. The Zephyr build process, however, makes sure that the compiler is able to optimise away almost all of that overhead. In the machine code, the application functions do directly call the functions for the specific device model.
In our earlier example, we lost our job because we were unable to add the necessary connectivity stack to our project. Therefore, it is our top priority to ensure that our next embedded ax will have robust connectivity support. Zephyr OS has a strong support of networking stack. It supports BSD sockets for e.g. TCP/IP, along with the state of art M2M protocols (LwM2M, OpenThread, etc.).
Not all developers are embedded developers, furthermore there are a lot of available code bases that are not originally written for embedded systems. So, being able to utilize such codes in our application can dramatically decrease V&V (Verification and Validation) time. Zephyr has strong support of POSIX standards.
Who may use Zephyr
So far, we have observed that developing bare-metal applications is not a viable option in the era of AIoT. No one wants to waste their time and energy writing everything from scratch. However, we also require a framework that can assist us in reducing the time-to-market while maintaining a high level of performance and reusability. The learning curve for Zephyr is very flat, and the Zephyr documentation is truly excellent.
In addition, if you have existing application code, there is no need to convert everything to Zephyr’s abstractions right away. In many cases, the chip vendor SDK’s header files are still included in Zephyr, so it is possible to run code written against those alongside with more modernized Zephyr code that does make use of the abstractions.
All in all, Zephyr is recommended to anyone who is thinking of their next project. From a small scale to large scale project, it can be a great candidate.
Looking for a Zephyr project expert? Schedule a meeting with our specialist today!
Presentations