views:

296

answers:

2

I suspect some ASSERTION code is having side effects. I'd like to switch off ASSERT without making any other changes to how my code is compiled. I'm using MSVS2008. Switching from debug to release won't do as that will alter how memory is initialised.

+2  A: 

If you mean assert, then that should be controlled with the NDEBUG macro.

UncleBens
NDEBUG alters memory initialisation too though
j coe
+4  A: 

Put this at the top of your header files after the inclusions of cassert (or a include that includes cassert)

#undef assert
#define assert(x) ((void)0)

Which redefines the assert marco so that it expands to nothing.

Yacoby
If I'm not mistaken, that turns off the assertion (program termination), but doesn't remove and stop the expression from being evaluated. Perhaps: `#define assert(x) (void)0`?
UncleBens
@UncleBens Ak, you are right, however the `(void)0` is not required. The `(x)` is though.
Yacoby
@Yacoby: In general, you want it because having `assert` expand to a statement helps with warnings and such. For instance, if `assert` expands to nothing in release mode then `if (foo) assert(bar); else assert(baz);` might warn for empty if and/or else clauses. The latest draft of the C standard, at least, *requires* that the built-in assert is implemented that way.
Steve Jessop
Turning off asserts using the `#define` above will *only* cause the statement inside the assert to be evaluated *by the pre-processor*. All `#define` statements will be evaluated and replaced by their appropriate values before the compiler runs, so this method should not cause the expression to be evaluated at run-time.
bta
Not only will it avoid warnings, but will avoid errors. Consider: `assert(baz()), assert(bar());` will fail in release mode if it simply expands to nothing. In C++ i would make it expand to `(void())` or `((void)0)` (the second has the advantage of working in C too).
Johannes Schaub - litb
@litb: Is `(void())` even allowed in C++? I don't have a copy of C89 (or a nearby draft to hand), so I don't know whether it contains the same requirement as the C draft I did refer to. If so, then C++ inherits it, and the macro must be exactly as given when NDEBUG is defined: `#define assert(ignore) ((void)0)`. Of course knowing the code that uses it, you could judge for yourself what you can get away with as against what the standard requires, but what I'd actually do is find the definition in my compiler's header files and use that :-)
Steve Jessop
@Steve, i see. Good point. You can redefine a macro given that it is exactly the same tokenwise afaik (not sure tho whether a program is allowed to redefine an implementation defined macro), and you can of course stringize its result. So a program could depend on the stringized form of it having a sizeof of `10`, i suspect.
Johannes Schaub - litb