0

Many of the times that I used to code C and some C++ under the RELEASE configuration in visual studio, I had slippery bugs that escaped my notice, and the code, though invoking undefined behavior, seemed to work fine. After several runs however, it becomes apparent that the program is bugged due to different unusual results and/or crashes.

So I decided to save my self the trouble and be on the safe side by selecting the DEBUG configuration while the code is still under development.

But does that guarantee that the program will come to a stop if the code is invoking undefined behavior of any sort?

machine_1
  • 4,266
  • 2
  • 21
  • 42
  • 1
    Nope. A simple demo is to declare two arrays, and write past the end of one to modify the other. – user3386109 Feb 27 '19 at 09:20
  • Use the STL (many implementations of the STL have debugging support), don't use arrays or pointers, generally adopt a safety first approach. – john Feb 27 '19 at 09:25

2 Answers2

2

No. It's the programmer's responsibility to handle poorly-defined behavior.

The summary list of documented cases of UB in C alone is 15 pages long. The undocumented cases are even more numerous - that is, doing things beyond what's even mentioned in the standard. And lets not even mention C++, where the list of poorly-defined behavior could probably be distributed as a separate, thick publication.

And then each single case of UB is wildly different, many of them only appearing in run-time, and the outcome could be anything. The compiler can only do so much to help, it's not it's job to point out potential run-time errors. And then the VS C compiler barely follows the standard in the first place.

Debug builds could actually be worse for detecting UB than release builds. Tools like VS has a tendency to zero-out all memory in debug build - even local memory, making bugs pass unnoticed. And with no/low optimizations in debug mode, some bugs will never manifest themselves.

To weed out undefined behavior, you could use external static/dynamic analysis tools and coding standards such as MISRA or CERT. But in the end it always comes down to language knowledge. Code reviews where some hardened C or C++ veteran get to have a say are very valuable, in order to catch bugs early on.

Lundin
  • 195,001
  • 40
  • 254
  • 396
  • Sorry, but _Tools like VS has a tendency to zero-out all memory in debug build - even local memory, making bugs pass unnoticed_ is generally wrong. Since at least VS.2005 it has had bit patterns of various fills to explicitely find issues like these in debug builds. See https://stackoverflow.com/a/127404/2331956 Sure, those values themselves can also hide bugs but they're generally chosen to expose more bugs than they hide. – Mike Vine Feb 27 '19 at 13:49
  • @MikeVine Okay. Luckily I haven't used VS since early 2000s, when it definitely did crap like that. There's no version mentioned in the question though :) And VS isn't/wasn't the only compiler which liked to sugar-coat debug builds with zero-out of the stack. Still, the remark about optimization holds true for any compiler, so there's plenty of UB which won't surface during debug, but only in release build. – Lundin Feb 27 '19 at 13:59
  • @MikeVine Btw the magic numbers in the linked post have nothing to do with stack zero-out in debug build. That would be a "stack canary". – Lundin Feb 27 '19 at 14:01
  • The stacks are all set to `0xCC` in debug builds afair. – Mike Vine Feb 27 '19 at 14:02
  • @MikeVine Ok, I fail to get anything but gibberish out of VS online C compilers when I try to dump the stack but maybe I failed to compile in debug build. – Lundin Feb 27 '19 at 14:13
1

No. There is no way to guarantee that code with undefined behaviour will crash.

Certainly selecting the DEBUG configuration will increase the chance that some undefined behaviours will be detected at run time (although it can cause others to not be detected). In particular if you don't use raw arrays and pointers, but instead use the STL, then the DEBUG version has many more checks for valid use. (I assume you are using the Microsoft library, because gcc/clang don't tend to use the terms DEBUG and RELEASE.)

It is also much harder (although not impossible) to compile code with UB or memory leaks if you use the STL.