A Closer Look at the MISRA C Firmware Coding Standard
B is for … Bug
Have you ever been working on your computer and suddenly your mouse stops moving? Maybe you’ve been on your phone and suddenly your app crashes for no apparent reason. I’m sure like most people you’ve had the experience of something not working only to find that turning it off and on again miraculously solves the issue. If this sounds familiar there’s a high chance you’ve encountered a “bug“, which is just another way to say “a defect in the firmware”.
As firmware contains varying degrees of complexity, writing completely bug-free code is usually not a straightforward exercise. In any case, these intangible bugs can be problematic.
Most firmware bugs probably cost you no more than a couple of minutes of time and a slight loss in productivity. However, bugs aren't just limited to your everyday PCs, TV remotes or smartphones. Complex Embedded Systems are becoming increasingly more and more prevalent in safety-critical industries such as Healthcare, Automotive, and Aerospace - and in these applications firmware bugs can result in injury or loss of lives. For example, the Patriots missile bug resulted in the terrible death of 28 people and injuring 96 (more on that later).
Needless to say firmware quality is important and there are many ways firmware engineers can mitigate bugs in the code they write. One way is to use test-driven development which I encourage you to read about in one of Beta Solutions' previous blog posts here. Another way, and the topic of this blog, is to follow a coding standard.
The particular coding standard which is the topic of this blog is called is MISRA C.
MISRA stands for Motor Industry Software Reliability Association which is an organisation founded by a number of vehicle manufacturers, including Ford and Jaguar. As the name suggests, the organisation was formed to help make the software (or firmware) developed in the motor industry more reliable. MISRA C is the coding standard MISRA came up with. Although this was intended to be used in the motor industry many other fields have adopted it because of just how reliable it made their firmware. Companies like Boeing, NVIDIA, and Apple all utilise MISRA C in some way. Continue reading to learn how MISRA was started, what MISRA C is, and why and where it is used.
MISRA was founded off the back of a government-funded program in the UK when it became concerned with safety-critical electronics. MISRA was the working group responsible for the motor vehicle industry, and consisted of vehicle manufacturers, component suppliers and engineering consultancies. Their mission statement was:
“We provide world-leading, best practice guidelines for the safe and secure application of both embedded control systems and standalone software.“ - MISRA
This all started in the early 90s and by 1994 they would release “Development Guidelines for Vehicle Based Software“ - a document which outlined a set of guidelines for the creation of embedded firmware in the motor vehicle industry. Government funding stopped the following year but MISRA continues to operate on a self-funding basis with a number of organisations contributing. MISRA was, and still is, a collaboration of the following companies who are or have contributed to MISRA:
- Ford Motor Company
- Rolls Royce and Associates
The original documents they published have since morphed into what's now known as MISRA C, which has three revisions. MISRA 1998, MISRA C 2004 and MISRA C 2012 - all released in their respective years.
MISRA representatives at the MISRA C 2004 release.
What is MISRA C?
In short, MISRA C is a set of firmware coding rules and guidelines which, if followed, are intended to help mitigate firmware bugs.
The C in MISRA C simply represents the programming language it's intended for ie: 'C'. The C language is generally great for embedded systems. It has low overhead, it's very efficient, and it's portable to other micro-controllers with little modifications. That said, there are some downsides to C.
For example, if you’ve had C programming experience you may know of the functions Malloc and Calloc, which are used for allocating memory on the heap (dynamic memory allocation). However, the use of such functions has the potential to lead to memory leaks which, in turn, can lead to undefined firmware behaviour (aka: "bugs").
MISRA C fixes this problem with directive 4.12. which simply states: “Dynamic memory allocation shall not be used“. This is a simple yet very effective rule which can dramatically improve code reliability.
Let's take a quick step back to define what a directive is and the different classifications/categories each guideline can have. Firstly a directive, in this context, is simply something that the code must adhere to if it is to be called MISRA C compliant. So directive 4.12 mentioned above states that for code to be MISRA C compliant it must not contain the use of any dynamic memory allocation. However, MISRA recognised that on the rare occasion it might be impractical to follow some guidelines. This is why each guideline is categorised into three different categories:
- Mandatory: A guideline in the mandatory category must be followed for the code to be MISRA C compliant. Deviation from said guideline is not permitted.
- Required: Code should conform to these guidelines. If it must deviate then formal documentation is required.
- Advisory: Code should conform to these guidelines however formal documentation is not required if a deviation from this is required. MISRA state that these should not be ignored, but rather should be followed as is reasonably practical.
The example directive 4.12 has the category “required”. This means if a firmware engineer has carefully considered the use of dynamic memory allocation then he/she can still call the code compliant if it is well documented. Documentation is very important and serves two purposes:
- It is very helpful for when other engineers are reviewing the code or performing code maintenance.
- It makes the engineer fully consider the decision to deviate from MISRA C.
Why use MISRA C?
As stated above MISRA helps to eliminate firmware bugs and thus improves the reliability of the system.
Code reliability is especially important in systems that are considered ‘critical’ - whereby a failure of that system could lead to: (i) Injury/death of a person(s) (“Safety Critical”), (ii) Breach of sensitive information (“Security Critical”), (iii) Prevention of accomplishing an important Goal (“Mission Critical”).
Needless to say, in a critical system the code reliability should be the highest priority.
How dangerous can firmware bugs be? As an example, we refer back to the aforementioned Patriots missile bug. The Patriot air and missile defence system was used by the US and its allies during the gulf war. The Patriots job was to detect incoming Scud missiles from the enemy and send its own missile to intercept them mid-air before it landed on any allied targets. These were set up around the allies' bases and outposts. The system was designed as a mobile/portable system that would never have a long continuous runtime. (This happens to be quite relevant to the firmware bug.)
The patriot uses radar to scan for incoming threats from up to 80 km away, track that threat, and guide a missile to intercept it. Essentially, a firmware bug caused a miscalculation and the enemy missile was never intercepted. It hit its intended target, a U.S. Army barracks in Dhahran, Saudi Arabia consequently killing 28 people and injuring 96 others.
The miscalculation was caused by a rounding error. Namely, the clock would gradually get more and more out of time the longer the patriot had been running (This is known as clock drift). After about 8 hours running continuously, it would be ineffective. This particular patriot missle was operational for 100 hours when the incident occurred.
Please note: The point overall I am making here with this example is not to discredit the firmware engineers who wrote the patriot missile code, but simply to illustrate to the reader how important firmware quality can be and the consequences of unreliable firmware.
Incidentally, MISRA does address such clock drift issues by stating in directive 4.1 that “Run time errors shall be minimized”, which essentially forces the firmware designer to consider such effects during the code's development.
The Patriot missile sytem and Patriot surface-to-air missile system. © REUTERS/Osman Orsal
MISRA C Recommendations
If a program is to be considered to comply with MISRA C, it is shown using a compliance matrix consisting of all the guidelines and how each is checked. MISRA C recommends the use of a static analysis tool to verify most of these. A static analysis tool is simply a program that automatically checks the code for violations of rules. A firmware developer would typically use it right after they have written a block of code and certainly before the code is released out into the field.
There are many different static analysis tools for embedded systems that contain their own unique features but most support checking for MISRA C.
Where and When is MISRA C used?
Though it was intended to be used in the automotive industry MISRA C has been adopted by a wide array of other safety-critical industries including medical, aerospace, and military to name a few. This is a credit to how well MISRA C achieves its intention of reducing firmware bugs and improving the overall quality of firmware.
While the advantages of following MISRA-C are clear, perhaps the main disadvantage of MISRA C is the increased development cost - due to:
- Using a restricted set of the C programming language, meaning that firmware engineers have less tools to write the code.; and
- Documentation of every deviation.
Therefore prior to the firmware development, one must always consider the question: “What are consequences of a system/product failure due to a potential firmware bug”?
Perhaps one can live with those consequences - perhaps one can’t. The key thing is to be aware of the implications of firmware bugs, and to develop your firmware accordingly. Nevertheless, more often than not, in the long run, it is cheaper and more time effective, to invest in writing quality code from the outset - rather than patching bugs more months (or years) down the track.
For non-critical systems, one could consider using the “Barr Group C” standard which is compatible with MISRA but not as strict. Beta Solutions Ltd, will often use the Barr Group C” standard for non-safety critical projects.
At Beta Solutions, our experienced embedded electronics engineers have the skill and proven track record to use the best suited firmware design methodology for our clients' products. You can get in touch with us to discuss any idea you have in mind via our contact page or give us a call.
- MISRA. Who we are. Retrieved from https://www.misra.org.uk/MISRAHome/Whoarewe/tabid/67/Default.aspx
- Image of MISRA C Working Group, at the official launch of MISRA-C:2004. Retrieved from http://www.misra.or.kr/misra_c_team.html
- Development Guidelines for Vehicle Based Software. Retrieved from https://ia800108.us.archive.org/26/items/misradevelopmentguidelines/misra_dev_guidelines.pdf
- MISRA-C:2004 Guidelines for the use of the C language in critical systems. Retrieved from http://caxapa.ru/thumbs/468328/misra-c-2004.pdf
- The Patriot missile system. Retrieved from https://www.ainonline.com/aviation-news/defense/2019-06-12/big-claims-big-cost-surface-air-missile-systems
- Patriot surface-to-air missile system. © REUTERS/Osman Orsal. Retrieved from https://tass.com/world/1123009
- Banner Image retrieved from https://www.pikrepo.com/fjfjq/black-porsche-911-on-road-during-night-time