Reputation: 78498
CMake is being used to compile some C++ files. There are assert
calls in the code. These calls are disabled in Release mode of CMake. It defines NDEBUG
in Release mode, I guess.
If I'm interested in having assert in Release mode of CMake, how do I enable it?
Upvotes: 27
Views: 25104
Reputation: 28811
Here's how LLVM does it. They add a LLVM_ENABLE_ASSERTIONS
option to the project (change LLVM
to your project's prefix), then check for it and filter the compile flags. There is a special case for MSVC.
Overall, this seems more sensible to me than defining a build configuration. Enabling assertions is IMO orthogonal concern to the overall build configuration.
# This is commonly needed so define it before we include anything else.
string(TOUPPER "${CMAKE_BUILD_TYPE}" uppercase_CMAKE_BUILD_TYPE)
[...]
if(uppercase_CMAKE_BUILD_TYPE STREQUAL "DEBUG" )
option(QD_ENABLE_ASSERTIONS "Enable assertions" ON)
else()
option(QD_ENABLE_ASSERTIONS "Enable assertions" OFF)
endif()
[...]
if(QD_ENABLE_ASSERTIONS)
if(NOT MSVC)
add_definitions(-D_DEBUG)
endif()
# On non-Debug builds cmake automatically defines NDEBUG, so we explicitly undefine it:
if(NOT uppercase_CMAKE_BUILD_TYPE STREQUAL "DEBUG")
# NOTE: use `add_compile_options` rather than `add_definitions` since
# `add_definitions` does not support generator expressions.
add_compile_options($<$<OR:$<COMPILE_LANGUAGE:C>,$<COMPILE_LANGUAGE:CXX>>:-UNDEBUG>)
# Also remove /D NDEBUG to avoid MSVC warnings about conflicting defines.
foreach (flags_var_to_scrub
CMAKE_CXX_FLAGS_RELEASE
CMAKE_CXX_FLAGS_RELWITHDEBINFO
CMAKE_CXX_FLAGS_MINSIZEREL
CMAKE_C_FLAGS_RELEASE
CMAKE_C_FLAGS_RELWITHDEBINFO
CMAKE_C_FLAGS_MINSIZEREL)
string (REGEX REPLACE "(^| )[/-]D *NDEBUG($| )" " "
"${flags_var_to_scrub}" "${${flags_var_to_scrub}}")
endforeach()
endif()
endif()
Source: https://opensource.apple.com/source/llvmCore/llvmCore-2358.3/CMakeLists.txt.auto.html
Upvotes: 8
Reputation: 65831
See this answer in the CMake FAQ, i.e.:
Fix it manually by changing the definition of the cache variables CMAKE_C_FLAGS_RELEASE
and CMAKE_CXX_FLAGS_RELEASE
. This has to be done every time you set up a new build directory.
To fix it permanently, create a custom CMake rules file in your source folder with the desired settings for the release flags (omit the option /D NDEBUG
). Then in your outermost CMakeLists.txt point the variable CMAKE_USER_MAKE_RULES_OVERRIDE
to the custom CMake rules file.
Upvotes: 15
Reputation: 3500
This would be a solution for the MSVC compiler:
string( REPLACE "/DNDEBUG" "" CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE}")
A better option may be to enable asserts not in Release mode but in RelWithDebInfo mode instead:
string( REPLACE "/DNDEBUG" "" CMAKE_CXX_FLAGS_RELWITHDEBINFO "${CMAKE_CXX_FLAGS_RELWITHDEBINFO}")
But this depends on your project and preferences of course.
Upvotes: 16
Reputation:
If you interested in assert
functionality only in your own code then the simple one solution
is to provide custom assert. For instance:
#if (MY_DEBUG)
# define MY_ASSERT(A) ... checks here ...
#else
# define MY_ASSERT(A) ... ignore A ...
#endif
Use option
to enable/disable assert:
# CMakeLists.txt
option(ENABLE_MY_ASSERT "Turn on MY_ASSERT checks" OFF)
if(ENABLE_MY_ASSERT)
add_definitions(-DMY_DEBUG=1)
else()
add_definitions(-DMY_DEBUG=0)
endif()
In this case you have full control over your checks, you can verify one component and ignore others:
... FOO_DEBUG=0 BOO_DEBUG=1 BAR_DEBUG=0 ...
Add custom CMAKE_BUILD_TYPE (also see CMAKE_CONFIGURATION_TYPES):
cmake_minimum_required(VERSION 2.8.12)
project(foo)
set(CMAKE_CXX_FLAGS_MYREL "-O3")
add_library(foo foo.cpp)
output:
# Debug
# ... -g ...
# Release
# ... -O3 -DNDEBUG ...
# RelWithDebInfo
# ... -O2 -g -DNDEBUG ...
# MyRel
# ... -O3 ...
Upvotes: 9