Know your Tool – Optimize C Code for microcontrollers

1488
0

One of the talks in the “Embedded Linux Conference 2016” was about best practices to optimize C for microcontrollers. This talk deserves to be mentioned to Electronics-lab readers.

The presenter Khem Raj worked on Comcast’s (broadcasting and cable television company) reference design kit for STB, Gateway and IoT platforms.

We will cover some important points that have been suggested by the presenter:

Optimization Levels

Optimization in compilers in general (GCC is the one in Khem’s case) has different levels (5 Levels: Os, O1, O2, O3 and Og). Os is for size optimization while O1, O2 and O3 are for performance.

Optimization Levels - From Khem’s slides
Optimization Levels – From Khem’s slides

Linker

Linker which is an important tool in microcontrollers’ software toolchain, is mentioned in Khem’s talk.

Linker script is written in the linker command language and controls the memory layout of the output file (what goes where). Moreover, Linker can output a map file which is very useful when you want to track down references to symbols in the MCU memory.

Linker Script File - From Khem’s slides
Linker Script File – From Khem’s slides

Objdump

GNU GCC has a collection of binary tools; they are called (binutils); and objdump is one of them. It interleaves your assembly code with source code so you can do disassembling using it.

Variables

Talking about best practices with variables. If the concept of local, global, volatile, const and static are blurred for you, then watching this presentation will clarify them besides other important terms.

Khem also mentioned special integer types in C99; they are “fast” and “least” types. So you can allocate your variable like that:

  • Fixed width unsigned 8 bit integer uint8_t
  • Minimum width unsigned 8 bit integer uint_least8_t
  • Fastest minimum width unsigned 8 bit integer uint_fast8_t

To ensure portability of your code, Khem advised to use portable datatypes using uint{8,16,32,64}_t type declaration. This avoids effects of changing size of int type across different processors (compilers).

Using global and local variables is another concern. Khem advised to use local variable as much as possible. Global variable needs to be loaded from memory and stored back every time it is used. So if you use a global variable in a loop you will have multiple loading and storing operations.

Khem’s presentation has other tips about: array subscript Vs. pointer access, loop increments Vs. loop decrements and other stuff. Make sure to watch the presentation, all of it!
Slides

Leave a Reply