Emutex designed and developed a bespoke firmware solution for an advanced analog and digital sensor measurement system.
THE EMUTEX APPROACH
The task of designing a new battery-powered advanced measurement system can be simplified if an MCU+ADC system complete with firmware is available; requiring only the selection of sensors and configuration of the firmware. That is why one of our customers hired us to develop a comprehensive firmware solution which could make the most from their electronics while being easily configurable when connected to a simple host.
The system allows the connection of digital sensors through different kinds of buses, and analog sensors, via a programmable signal conditioning circuit (see https://www.ncbi.nlm.nih.gov/pmc/articles/PMC3297160/) A set of Analog-to-Digital (ADC) converters transform the analog signals into digital values to be processed by the firmware. The firmware sends the processed data to the Host processor or to the Data logger. Two internal banks of memory are available to store persistent information - one read-only and another to store configurations and other data that comes from the Host. A controllable power supply allows the MCU to save power by selectively turning off part of the electronics and devices when not in use (red arrows show power lines).
THE SPECIFICATIONS, THE CHALLENGE
Emutex was requested to develop the firmware for a complete measurement system with the following main specifications:
- Small memory footprint and able to work at high speed even with no hardware floating point unit.
- Very low power consumption.
- Very flexible and capable of collecting data in many different arrangements and flows.
- Large embedded configuration library.
- User interface able to simplify the configuration process.
- Advanced signal processing.
- Able to detect error conditions even in the devices connected.
- Protected against tampering and human error.
- Production-friendly and easy to calibrate.
- Reliable, and compliant with several industry standards (aerospace, automotive).
- Include additional portable C/C++ High level API on the host side.
- Short time-to-market.
This included working within some challenging constraints, such as:
- Implementing high-rate math calculations and a fast communication interface with a very low-processing-power MCU.
- Storing large sensor databases and measurement result batches within a very small (kBs) memory budget.
- Creating a very flexible and configurable system, while ensuring reliability.
- Implementing a comprehensive set of features, while achieving a short time-to-market.
To meet the deadlines and all the specifications, Emutex quickly assembled a team able to work with efficiency and to collaborate closely with the customer, to deliver a high-quality product in the timeframe: three senior developers, two senior testers and a project manager; all of them with mixed knowledge of embedded software, hardware and analog electronics.
In projects like these, with so many degrees of freedom (due mainly to its extended connectivity and large quantity of configuration options), continuous collaboration with the customer plays a crucial role. That way it is possible to define the detailed specifications about the functionalities of the system and the API with consideration of key constraints such as the hardware or the power consumption and possible trade-offs that must be made as a result.
During the two initial months several meetings per week were held with customer’s engineers from the different departments involved in the project, resulting in a detailed set of specifications and a high-level design to make the most of the hardware while offering a set of functionalities and an API that was consistent, robust but very flexible.
As a side effect of this work, several improvements to the hardware design were fed back to the customer, which they implemented in the final version of the system.
At the same time, the two Emutex’s testers engineered a very special automated test station that was key during the initial firmware development work and subsequent maintenance. Continued close collaboration with the customer throughout the project allowed us to refine the specifications and design to adapt to new requirements that arose following evaluation of the preliminary firmware releases supplied to the customer every month.
Agile and Test-Driven Development
To achieve the above flexibility level, the project was managed under agile methodology (Scrum) and Test-Driven Development (TDD) using a Continuous Integration System where our fully automated test station was included.
Working under TDD rules means that for every new function to be included in the firmware under development, the set of tests needed to verify that function is first defined. Later, while the firmware developers code the functionality, the testers add the required electronics to the test stations and program the new tests cases.
The work of both groups, testers and developers, are synchronised through a central code repository where the continuous integration system automatically performs the static code analysis, builds the code, performs unit tests and, assuming previous steps are successful, deploys the binaries on the test stations.
Controlled by the continuous integration system, the test stations execute the complete battery of tests and the results are presented back to the testers and developers. That way the whole team receives prompt feedback on any issues that need to be fixed or improved.
This cycle is repeated until all functions, both new and existing, are verified as fully working and ready to release to the customer.
The firmware was programmed in portable C, while the API for the host was programmed in a mix of C and C++.
Care was taken to allow it to work with low-end MCUs requiring small memory footprint and making the most from its hardware, allowing timely processing even when no floating-point hardware was present (ARM Cortex-M3, for example). The reduced memory usage was achieved by compressing most of the sensor databases and by aliasing buffers.
The firmware was also conceived to be production-friendly, facilitating calibration and access protection.
An active diagnostic and error reporting mechanism in the firmware provided error identification codes to help quickly trace the origin of any issue occurring during initial configuration or subsequently during use in the field.
The firmware was developed following a modular and layer-based structure illustrated in the diagram below:
Main state machine. It controls the main modes of the firmware which are User interface, Run mode and Configuration. Some of them are triggered by interrupts while others work under the control of a state machine.
User interface. It manages the communications with the Host. It can work with different transport layers like UART and others. The user can configure a large quantity of parameters and save them in the internal flash of the MCU and can also read the measurements performed. The interface deals with security issues, and error reporting. The internal persistent read/write database is also accessed by this interface.
Configuration. It reads and validates the user configuration received through the Host Interface and sets up several processing engines to perform the requested operations.
Run mode engine. It is a very sophisticated engine able to control several interleaved loops with distinct round times oriented to gather information from different kinds of sensors. It allows alert sensors to trigger immediate responses, configuration changes on the fly, one shot mode, pipelined operations and many more. It also intersperses the power control, allowing selective power-down of subsystems when not in active use.
High Speed FP Custom Math library. It is a set of equations developed specifically for this system and this firmware to optimize the hardware speed (even with processor without hardware floating point unit) and memory footprint. It allows the whole firmware work in small MCUs while retaining all the necessary capabilities.
Host API. It provides a high-level C/C++ Application Program Interface to simplify the integration of the system firmware with end user application stack that run in a separate processor known as the Host.
The project produced high quality firmware, a set of host libraries and a fully automated test station (both software and hardware) absolutely tailored to the customer specifications and hardware options. Additionally, a thorough consultancy work was done, helping to shape and upgrade the specifications to obtain the most from the hardware. The usability of the system was also greatly improved, getting a product which can reach a wide range of applications. The firmware was constructed to be fully functional with minimal requirements like 48 KB RAM and 192 KB Flash on an ARM Cortex-M3 (and also ARM Cortex-M4/M4F). The automated test stations, capable of running many thousands of different test cases, have been handed over with all the required information to assembly more of them if needed. They have been the key to ensuring the high quality of the software produced and will help with detection of regressions caused by any future maintenance. As well as validating the firmware functionality, the station can also be used as a test bench for hardware validation during production and is flexible enough to help with replicating and characterising specific configurations in the context of customer support. Documentation and hands-on seminars were provided to the customer to enable their engineers to continue the subsequent maintenance and development of the software. A maintenance contract was also established provide follow-up assistance where needed following the final software release. The customer owns now a product which is innovative, reliable and at the cutting edge of the technology, ready for mass-production as it offers the tools for performance tailoring, unique ID and precise calibration. The well-conceived API and communication interfaces allow end-users to integrate the system in their own design with minimal effort. It transforms the cumbersome tasks of integrating a separate MCU, analog circuits and ADCs, and on top of that creating their own firmware, into a simple task of integrating and configuring a single modular API.