Code and compilers: small, fast or what?
All modern compilers generate optimized code. For embedded developers, good optimization is critical, as resources are always at a premium, but control of optimization is also essential, as every embedded system is different. In this article, the balance between fast and small code and why this choice is necessary are considered. Additionally, examples are given where this rule can be broken, and fast, small code results, which lead to a reconsideration of the true function of a compiler.
What is a compiler?
Ask an average engineer and you will get an answer something like: “A software tool that translates high level language code into assembly language or machine code.” Although this definition is not incorrect, it is rather incomplete and out of date – somewhat 1970s. A better way to think of a compiler is: “A software tool that translates an algorithm described in a high level language code into a functionally identical algorithm expressed in assembly language or machine code.” More words, yes, but a more precise definition.
The implications of this definition go beyond placating a pedant like me. It leads to a greater understanding of code generation and hints at just how good a job a modern compiler can do, along with the effect on debugging the compiled code.
Life is often about compromise, but embedded developers are not good at that. Code generation is a context in which compromise is somewhat inevitable - we call it “optimization”. All modern compilers perform optimization, of course. Some do a better job than others. A lot of the time, the compiler simply guesses which optimization will produce the best result without knowing what the designer really wants. For desktop applications, this is OK. Speed is the only important criterion, as memory is effectively free. But embedded is different.
Desktop versus embedded
To the first approximation, all desktop computers are the same. It is quite straightforward to write acceptable applications that will run on anyone’s machine. Also, the broad expectations of their users are identical. But embedded systems are all different – the hardware and software environment varies widely and the expectations of users are just as diverse. In many ways, this is what is particularly interesting about embedded software development.