Search This Blog

Monday, August 22, 2022

The 1980s called, they want their C compiler back

 

(Random Internet Screen Shot)

Plaguing your code with debugging statements

I know how this happens, it is the belief that making a function call, even an empty one will create overhead in a C program. However, that is not the case anymore. Today's C compilers are very aggressive in optimizing, especially at cutting out dead code.

Example: I was looking through a micro-controllers library so that I could figure out how I could use it, and I saw a bunch of code that looked like this,
 

Figure 1 – Nothing wrong with debugging statements, it’s the distraction of all those #ifdef / #endif statements that make the code hard to understand.

Figure1 is really very hard on the eyes, the indent level keeps changing and all those #ifdef / #endif statements really make a visual mess out of the whole code base.

Do yourself a favor and write a simple logging function, then your code can look much cleaner like this,
 
Figure 2 – Refactoring the debug statements into a debug function really cleans up the appearance of the code.

I still don’t like the indention style, but that is a matter of preference, as the indention style that this author used is certainly a common convention.

The logging function can be as simple as this,
 


Figure 3 – Refactoring the serial debug print statements into a function can be as simple as this and can be used everywhere throughout the code if desired in the future.

Logging still works the same way, add a #define DEBUG_TO_SERIAL in the code to enable logging, and then do a #undef DEBUG_TO_SERIAL to stop logging.

Objection

The main objection is usually this: “You will still have a function call with debugging turned off, making your code bloated, slower, and bigger.”

This isn't the 1980's anymore and our modern compilers are very good at optimizing out code that does nothing. In fact, every compiler I have used in the last 10 years, especially the ones derived off of GCC, when doing even minimal optimizing (Level=1) will see that the function call is empty and that the passed variables are not being used and the compiler will simply not generate anything if the flag DEBUG_TO_SERIAL is not defined. It just ignores the entire function call as if it never existed.

This is the same as most compilers today will totally ignore “Quick and dirty delay” statements like this ‘attempt’ to make a delay, not generating any code at all,

     For(int I = 0 ; I < 1000 ; i++)
     {
          int j = I * 1000;
     }


Snippet – A modern compiler, like GCC, will easily see that the code above does nothing and will completely ignore it, not generating any assembly code at all.

Conclusion: 

Remember that the compiler you are probably using is very, very good at getting rid of dead, unused code even at low optimization levels. Therefore you can write code in a very clean way, and help those who come after you in more easily comprehending your code.


Bonus:

You now have the makings of a very nice debug / logging library that you can start to use everywhere, while still keeping your code very readable.

 

Article By: Steve Hageman www.AnalogHome.com    

We design custom: Analog, RF and Embedded systems for a wide variety of industrial and commercial clients. Please feel free to contact us if we can help on your next project. 

This Blog does not use cookies (other than the edible ones).

No comments:

Post a Comment