CMake: Checking Variables with if() Instead of variable_requires()


  • Behavior
    • If any variable wasn't set to TRUE or wasn't set at all (meaning its value was NOTFOUND), it would report an error.
    • If all variables were set to TRUE or not set, it did nothing.
  • Arguments
    It took a list of variables as arguments.
  • Purpose
    It checked if certain variables were set to specific values.

Replacement

if(NOT MY_VARIABLE OR NOT ANOTHER_VARIABLE)
  message(ERROR "Variables MY_VARIABLE and ANOTHER_VARIABLE are required")
endif()

This code checks if both MY_VARIABLE and ANOTHER_VARIABLE are set to TRUE. If either is not set, it displays an error message.



Example 1: Checking a single variable

Imagine you have a variable USE_GUI that determines if your project uses a graphical user interface. You can check if it's set to ON before including a GUI library:

# Old way (deprecated)
# variable_requires(USE_GUI)

# New way (using if())
if(NOT USE_GUI)
  message(WARNING "Building without GUI support")
endif()

find_package(FLTK QUIET)  # Only try to find FLTK if USE_GUI is ON
if(FLTK_FOUND)
  include_directories(${FLTK_INCLUDE_DIRS})
  target_link_libraries(your_target FLTK)
endif()

Example 2: Checking multiple variables

Suppose you need a specific compiler and a specific library for your project. You can check for both:

# Old way (deprecated)
# variable_requires(CMAKE_CXX_COMPILER CMAKE_REQUIRED_LIBRARIES)

# New way (using if())
if(NOT CMAKE_CXX_COMPILER OR NOT CMAKE_REQUIRED_LIBRARIES)
  message(FATAL_ERROR "Requires a C++ compiler and libraries")
endif()

Example 3: Checking variable values

You can also check if a variable has a specific value:

# Old way (not directly possible with variable_requires())

# New way (using if())
if(NOT MY_OPTION EQUAL "VALUE")
  message(STATUS "Option MY_OPTION is not set to 'VALUE'")
endif()


Using if() for Variable Checks

  • Basic check for existence
if(NOT MY_VARIABLE)
  message(ERROR "Variable MY_VARIABLE is required")
endif()

This checks if MY_VARIABLE is defined (not NOTFOUND).

  • Checking for specific value
if(NOT MY_OPTION EQUAL "VALUE")
  message(STATUS "Option MY_OPTION is not set to 'VALUE'")
endif()

This verifies if MY_OPTION has the value "VALUE".

  • Checking multiple variables
if(NOT CMAKE_CXX_COMPILER OR NOT CMAKE_REQUIRED_LIBRARIES)
  message(FATAL_ERROR "Requires a C++ compiler and libraries")
endif()

This ensures both CMAKE_CXX_COMPILER and CMAKE_REQUIRED_LIBRARIES are defined.

Additional Control Flow options with if()

  • elseif()
    This allows for checking additional conditions within the if() block.
  • else() and endif()
    These define alternative code blocks if the condition isn't met and the end of the conditional block, respectively.
  • Integration
    if() can be easily combined with other control flow statements like else() and while() for more intricate logic.
  • Readability
    The syntax of if() is generally considered more readable and easier to understand.
  • Flexibility
    if() allows for more complex conditional logic compared to the limited functionality of variable_requires().