A simple and clear example of undefined behavior

published at 14.10.2021 21:54 by Jens Weller
Save to Instapaper Pocket

If you work with C++ you'll sooner or later will have to deal with undefined behavior. I stumbled upon an easy example to help folks understand the scope of undefined behavoir.

As its not always easy to understand this for beginners. In many situation it also surprises rather seasoned devs, and there is a reason that the UB sanitizer exists.

Here is the simple example I promised:

int C = 1;
int c_cpp = C/C++;

Whats the value of c_cpp?

Its easy to see why it could be 1: the postincrement operator returns the old value before it increments it by 1. So 1/1 = 1. But the expression "C/C++" is undefined behavior, C++ does not define how this should be baked into code by the compiler. This example on compiler explorer shows that while this expression is 1 on clang and icc, its 2 on gcc. And clang is the only compiler that gives a warning:

warning: unsequenced modification and access to 'C' [-Wunsequenced]
auto c_cpp = C/C++;
             ~  ^

Which hints at the reasons for this being UB: the C++ standard defines an unsequenced access to a memory location  - here C -  as undefined in behavoir. 

And while this example isn't real world code, its simple and shows a different result on different compilers. Which helps to show that even if you think you know what this code prints, its not clear what it prints in C++ it self. As the standard does not define the behavoir, the compiler is allowed to decide what it should do in this situation.

 

Join the Meeting C++ patreon community!
This and other posts on Meeting C++ are enabled by my supporters on patreon!