====== IoT and Embedded Systems Programming Models ====== {{:en:iot-open:czapka_b.png?50| General audience classification icon }}{{:en:iot-open:czapka_m.png?50| General audience classification icon }}{{:en:iot-open:czapka_e.png?50| General audience classification icon }}\\ IoT device programming can be done on a variety of levels. Below are the most popular models and a brief discussion of their pros and cons.\\ ==== Bare Metal Programming ==== The bare metal programming model is where the software developer builds firmware (usually from scratch or based on a stub generated by the SDK) and flashes it to the MCU. The MCU usually does not contain software other than technical ones necessary for starting and updating the device, e.g. a bootloader. The developer must implement all algorithms, communication, interfacing, storage, etc., on a low level. They may use 3rd party libraries to implement it, which speeds up development significantly. There is no operating system running in the background. Eventually, it comes with the firmware as part of it, as included by the developer, e.g. FreeRTOS ((https://www.freertos.org/)). Bare metal programming applies first to the Edge class devices, rarely to the Fog class. Bare metal programming requires a good understanding of the hardware configuration of the IoT device as well as the configuration of the software development toolchain. The MCU manufacturer usually provides SDK and related tools, but there do exist middleware solutions (such as PlatformIO ((https://platformio.org/))) that significantly simplify installation. In most cases, source code is written in C or C++ language or their combination (e.g. in the case of the STM). The development process for bare metal programming is present in the following figure {{ref>prog_img_baremetal}} and its features are discussed in table {{ref>prog_tbl_baremetal}}. In short, it requires developing, compiling and uploading the firmware to the device's flash memory. Programming uses a programmer (physical or Over-the-air - OTA, virtual interface). The bare metal model usually provides hardware development capabilities.
{{ :en:iot-open:programming_models-bare_metal.drawio.png?680 | Bare metal IoT firmware development process}} Bare metal IoT firmware development process
The bare metal programming model is considered the only one that enables developers to have absolute control over the hardware on a very low level. On the one hand, it brings opportunities to implement non-standard solutions and optimal code in terms of compactness and efficiency; on the other, it increases time-to-market delivery. Recent advances in development supporting tools (e.g. AI-based code generation), wide availability of the libraries, standardisation of their presence and automated management, such as, e.g. in PlatformIO Library Management ((https://docs.platformio.org/en/latest/librarymanager/index.html)) significantly lower this time. ^ Pros ^ Cons ^ | Absolute control over hardware | Need to implement all from scratch | | Secure, low vulnerability | Requires good hardware understanding | | No bottlenecks | Requires advanced programming skills | | Efficient and compact code | Requires complex development environment | | Fastest, no overhead of the middleware | Possibility to brick the device during flashing | | Good community support | Time consuming implementation | | Highly flexible, enables the developer to prepare non-standard solutions | | | Provides hardware debugging capabilities | | | Energy efficient, it gives control over low-level, energy-saving mechanisms (waitstates, sleep modes, radio power, etc.) | |
Bare metal programming pros and cons
In the IoT world, it is common to distribute firmware remotely (OTA - Over The Air). For this reason, it is pretty frequent that the flash memory of the IoT device is split in half into two partitions, each containing a different version of the firmware (old and new). OTA mechanism flashes an inactive partition, and then the bootloader swaps them during the reboot of the device once flashing is done. If new firmware fails to boot, the bootloader swaps the partition back to run the old version, reboots the device, and notifies about the update error. ==== Script Programming with Middleware ==== Opposite to bare metal programming, script programming does not involve compilation or firmware burning into the flash memory. This programming model uses interpreted languages such as Python (actually Micropython: an edition of Python for microcontrollers dedicated to constrained devices), NodeJS, Javascript, Java, C#, etc. A virtual machine middleware (programming language interpreter) running bare metal (installed as firmware) or as a part of the operating system (if any), and the developer prepares an algorithm as a script, usually in a textual form, later uploaded and executed on the device. The middleware brings an overhead on execution; thus, this solution is intended for not-so-constrained IoT devices, still acceptable for Edge and quite common for Fog class. It requires much more CPU, RAM and storage than bare metal programming, has limitations from the interpreter implementation and only indirectly accesses hardware. It is not suitable for real-time solutions. Scripting programming is common for more powerful Edge devices and almost the first choice for Fog class devices. The development process for scripting programming is present in the following figure {{ref>prog_img_scripting}} and its features are discussed in table {{ref>prog_tbl_scripting}}. In short, it requires limited SDK (or none), but debugging is complex, if possible.
{{ :en:iot-open:programming_models-scripting.drawio.png?580 | IoT programming process}} Scripting IoT programming process
This programming model is suitable wherever standard solutions are implemented and where code execution efficiency is not critical, and there is no demand for real-time operations; eventually, the IoT device is unconstrained, providing developers with decent CPU (e.g. modern ARM), RAM and storage. Note those solutions are usually less energy efficient than bare metal programming; still, they offer great flexibility in algorithm implementation, far beyond a predefined list of choices or limited configuration as presented in the following section. On the other hand, it speeds up delivery time to the market because of the ease of implementation, the lack of need to install the complex software development environment and the high level of abstraction. ^ Pros ^ Cons ^ | Better suitable for beginners | Not optimal because of the middleware overhead on execution | | Uses higher abstraction level | Not suitable for real-time operations | | Uses high-level programming languages | Limited hardware interfacing and features to those exposed by the middleware | | Usually does not involve complex SDK/development environment | Limited and non-optimal energy efficiency management | | Flexible enough to implement complex algorithms | Low extendibility | | Rapid development | Middleware updates used to cause the need to adapt script with algorithm | | | Hardware debugging is tricky or not possible at all |
Scripting programming pros and cons
==== Configuring Firmware ==== Several configurable firmware (IoT frameworks) are available for various IoT devices. This development model focuses on reconfiguring the ready-to-use firmware delivered "as is" using some configuration interface or script (or both). Eventually, modifying and recompiling it yourself is possible if it is open source. Still, the recompilation process is usually very complex, and understanding all relations and development toolchains is sometimes more complicated than developing a solution from scratch as a bare metal. Some open-source firmware (like Tasmota, ESPhome, and OpenBeken) offer high flexibility and configureability, making their use the simplest and fastest way to develop IoT devices. In contrast, proprietary firmware does not bring this opportunity at all and is delivered "as is" with a predefined set of features. Software modifications are not allowed, and configuration is limited to changing the state of the elements from simply switching them on and off to setting up access and credentials. This usually does not bring capabilities to modify the algorithm, eventually to choose a behaviour from the predefined list proposed by the firmware author. Such a model does not bring debugging capabilities; finally, simple tracking with error codes and log files (if at all). Moreover, in many scenarios, firmware operation is dependent on some external resources (e.g. authorisation via a cloud or firmware updates delivered with this channel). Firmware configuration model is applied to both Edge and Fog class devices, exposed via IoT frameworks. Sometimes, it also involves the cloud part of the solution. The development process for the firmware configuration model is present in the following figure {{ref>prog_img_middleware}} and its features are discussed in table {{ref>prog_img_middleware}}.
{{ :en:iot-open:programming_models-configure.drawio.png?580 | Firmware configuration process}} Firmware configuration process
Configuration range varies among IoT frameworks but commonly requires compatible hardware. Proprietary firmware provides sealed configuration software and encryption; thus, it virtually excludes any non-standard modifications or makes them very complex. Configuration in proprietary firmware scenarios can be provided indirectly via a cloud solution that raises serious questions about privacy (e.g. configuring your private WiFi router credentials via a public or 3rd party cloud, not directly to the device). It is worth mentioning that IoT hardware used to be compatible with more than one firmware, and proprietary ones can be replaced with alternative open-source firmware, e.g. Tasmota ((https://tasmota.github.io/docs/)), ESPHome ((https://esphome.io/index.html)), OpenBeken ((https://github.com/openshwprojects/OpenBK7231T_App)), ESPEasy ((https://github.com/letscontrolit/ESPEasy)), ESPurna ((https://github.com/xoseperez/espurna)). Unfortunately, the replacement process usually requires specialised skills like soldering because, in most cases, first-time reflashing needs a physical connection with the chip. WARNING! The reflashing process usually needs specialised skills and requires high care. Flashing an alternative firmware can lead to unexpected behaviour of the device and can make the device unusable. Never connect anything or touch the device while it is opened and powered by an electric line! ^ Pros ^ Cons ^ | Easy to use even for beginners | Limited number of use scenarios | | Consistent environment (configuration, use) common look and feel | Problems appearing hard to solve in case of failure | | No need for SDK, configuration tools use plain text, browsers or apps | Low flexibility - limited support for hardware (only proprietary or limited compatibility in the case of the open source) | | Manufacturer's support (for proprietary) but usually for a limited time and shorter compared to open source solutions | Doubtful privacy, in particular when a public cloud is in use | | Usually reliable | Lack of help once the Manufacturer's maintenance period is finished | | During the maintenance period, updates are given by the vendor | |
Middleware configuration model pros and cons
In this book, we focus on the bare metal programming model using the C/C++ model, but we also present some aspects of scripting programming and review some IoT frameworks that are exposed with the alternative firmware configuration model.