Writing Hardened Firmware and Software for EMC

How to write EMC resistant firmware and software

It is often enough in order to pass EMC testing to have a product that returns to normal use after EMC noise sources have been removed, and this is most commonly facilitated by writing code that resets if the program counter gets lost. There are some very simple and neat techniques that can be used to achieve this, as follows. 

What is hardened code all about?

The risk of coincident EMC events coupling with a susceptible point of electronic hardware at a time at which critical data communications are taking place can never be eliminated. No matter the lengths taken in hardware design, there is always a probability of failure that is essentially a statistical event – susceptible data transmission at just the wrong time.

It is important that software and firmware have error traps such that events of this type are handled, ideally in a manner opaque to the user of the equipment. This Hardened Code (HC) is the subject of this report.

The guidelines in this article enable the writing of HC.

How to use watchdog timers to improve EMC performance?

Operation (Firmware and Hardware)

Watchdog timers are timers that are designed to force a system re-set if they overflow. The timer, once enabled, is cleared in the system software repeatedly thus never overflowing and having no effect under normal conditions. In abnormal conditions the program counter can lose its way and stop running the code, running operations in some random section of memory. A common cause of this is electromagnetic interference (EMI/EMC). Watchdogs allow the system to reset in such a case because the WDT stops getting reset and causes a system reset as a result.

Watchdog timers are best implemented separately from the device (hardware) being monitored despite many such devices having embedded software/firmware watchdogs themselves. Embedded timers are easily implemented and reliable providing a few basic rules are followed:

  • Don’t clear software WDTs in interrupts. WDTs can fail calling themselves and therefore endlessly re-setting the WDT and blocking a needed reset.
  • Use the rules in the Timeout Period section to determine the Timeout of the software WDT.
  • Always use software WDTs if they are available.
  • Include re-initialisation of WDT in boot up re-initialisation functions.

Hardware WDTs are best configured by an independently clocked (XTAL) WDT external to the device being monitored. The device being monitored sends trigger pulses to the WDT, the absence of which will cause an output that is tied to the reset/MCLR line of the controller – hardware reset occurs. These are the most effective WDTs provided basic rules are followed in the hardware design and software/firmware design of the re-triggering pulses, as follows:

  • Timeout period is governed by the rules in the Timeout Period section.
  • The hardware is configured such that the reset requests are continuous until a stable re-triggering pulse train is re-established.
  • The software/firmware uses two independent sources to set high and low levels of re-triggering pulse, e.g., interrupt to set low and firmware functions to set high.
  • Always use controller reset line for hardware WDT: never an interrupt input.

General implementation guidelines are as follows:

  • Never disable a WDT – even when a long operation is needed.
  • Always configure a WDT to cause a reset – all other states can’t be guaranteed.
  • For an extremely sensitive design, consider multiple hardware WDTs.

Timeout Period

The timeout period of the WDT is determined by the needs to the device. WDTs that clear too often introduce overhead and can cause race conditions, and, obviously, those that are too slow may not cause a reset in time for the device to remain effective.

To improve the rigour of WDTs it is efficacious to create a WDT register with bits for all regularly called functions. Only when all of these have been called is the WDT reset. Obviously, some functions may necessarily have to sit outside this model. Consider implementation of WDT register

What is meant by defensive programming?

Input Verification and Validation

The following safeguards should be applied to data inputs that are part of hardened code:

  • Check type and validate all inputs
  • Sample and average input data if practical
  • CRC, parity and checksum all data where applicable
  • Use level triggered interrupts rather than edge ones wherever possible
  • Re-initialise all programmable chips on start up. This includes WDT setting for software WDTs.
  • Average analogue inputs. Also check consecutive inputs – if too many the same initiate reset.
  • Ensure all unused memory locations have data in them such that hardware reset is forced – illegal code or/with explicit command to reset.

Interrupts

The following are suggestions for effective management of interrupts in hardened code:

  • Don’t permit interrupts to clear software watchdog timers.
  • Monitor for stack overflow.

Token Passing

Entry into functions from illegal program jumps can be avoided by passing tokens to functions. A legal call from a function passes a token to the function being called. The function being called checks for the validity of the token, and if it fails, a reset of the system should be initiated.

If this article sparks interest or it is wished to discuss it at all, please don’t hesitate to Contact us.