24

Is there a standardized (e.g. implemented by all major compilers) #define that will allow me to distinguish between debug and release builds?

sivabudh
  • 31,807
  • 63
  • 162
  • 228
  • 1
    Actually the major project I work on, we keep debugging in our release, but have it determine verbosity at run-time. It has proven useful in bug-hunting in the wild, with a minimal (_very_ hard to notice; no user complaints) overhead when not enabled. Outside of embedded environments, I'd consider such an approach. – mctylr Feb 12 '10 at 02:32
  • 1
    What is a "release build"? The C++ standard doesn't define it, so there is no portable way to detect if something is a release build. – jalf Feb 12 '10 at 13:16

4 Answers4

26

if believe

 #ifdef NDEBUG
  // nondebug
 #else
  // debug code
 #endif

is the most portable.

But no compiler knows whether you are compiling debug or release, so this isn't automatic. But this one is used by assert.h in the c-runtime, so it's quite common. Visual Studio will set it, and I'm sure most other IDE's will as well.

John Knoeller
  • 33,512
  • 4
  • 61
  • 92
  • the lack of an _ on the front indicates its probably mentioned in the C or C++ standards somewhere. MS has been very very careful in the last releases to prefix any non standard macro's or functions in their c-runtime header files with '_'s – Chris Becke Feb 12 '10 at 05:08
  • 5
    That is not the same. Defining NDEBUG turns off the assert macros. Nothing else. This does __NOT__ imply debug. – Martin York Feb 12 '10 at 05:15
  • 4
    @Martin: nondebug actually. and if it was intended to _only_ turn off the assert macros, they would have called it NOASSERT. you should actually read what I wrote before you start taking off points. – John Knoeller Feb 12 '10 at 05:20
  • I believe Martin is correct. According to the standard, the only thing that defining NDEBUG does is turn off assert. It could be used for other things as well by the programmer, but that is outside the standard. The C++ standard makes only one reference to NDEBUG, and I don't have a copy of the C standard. – KeithB Feb 12 '10 at 13:42
  • 5
    @KeithB: the question is the most _portable_ way, not the most standards compliant way, so all of this standards nit-picking is missing the point. – John Knoeller Feb 14 '10 at 02:41
4

Since there is no standard definition of debug or release, there isn't a way to do this. I can think of at least four different things that could be meant, and they can all be changed independently. Only two can be tested from within the code.

  1. Compiler optimization level
  2. Debugging symbols included in binary (these can even be removed at a later date)
  3. assert() enabled (NDEBUG not defined)
  4. logging turned off
KeithB
  • 16,577
  • 3
  • 41
  • 45
1

Edit: I misread the question and waffled off on a different tangent!!! Apologies... The macro _NDEBUG is used on Linux as well as on Windows...

If the binary is built and you need to determine if the build was release/debug, you can get a hexadecimal dump, if you see loads of symbols in it that would be debugging information...for example, under Linux, using the strings utility. There is a version available for Windows by SysInternals, available here on technet. Release versions of binary executables would not have the strings representing different symbols...

strings some_binary

Hope this helps, Best regards, Tom.

t0mm13b
  • 34,087
  • 8
  • 78
  • 110
  • Not necessarily true; it's possible to produce binaries with symbols (i.e. for functions and static data) but not debug information (i.e. line numbers). – Derrick Turk Feb 12 '10 at 13:50
  • That said, flags providing that information are generally stored in the header of whatever object file format. Try GNU objdump (there's a version for Windows too, distributed with MinGW): objdump -x – Derrick Turk Feb 12 '10 at 13:51
0

Best I could come with is

#ifndef NDEBUG
// Production builds should set NDEBUG=1
#define NDEBUG false
#else
#define NDEBUG true
#endif

#ifndef DEBUG
#define DEBUG !NDEBUG
#endif

Then you can wrap your debug code in if(DEBUG) { ... }.

mpen
  • 272,448
  • 266
  • 850
  • 1,236