Find module variables naming conventions

Hello,

Apologies for asking so many questions lately. This community has been of enormous help so I have another question about find modules.

In CMake there is trend to use find modules like this:

find_package(Foobar)
target_link_libraries(project_library PRIVATE Foobar::Foobar)

And result variables are named as <PackageName>_SOME_VARIABLE. For example, Foobar_INCLUDE_DIRS, Foobar_LIBRARIES, Foobar_VERSION, etc.

# FindFoobar.cmake

find_path(Foobar_INCLUDE_DIR foobar.h)
find_library(Foobar_LIBRARY NAMES foobar)

# Find the Foobar version in some way, for example, from header:
set(Foobar_VERSION "...")

set(Foobar_LIBRARIES ${Foobar_LIBRARY})
set(Foobar_INCLUDE_DIRS ${Foobar_INCLUDE_DIR})

include(FindPackageHandleStandardArgs)
find_package_handle_standard_args(
  Foobar
  REQUIRED_VARS Foobar_LIBRARY Foobar_INCLUDE_DIR
  VERSION_VAR Foobar_VERSION
)

if(Foobar_FOUND AND NOT TARGET Foobar::Foobar)
  add_library(Foobar::Foobar UNKNOWN IMPORTED)
  set_target_properties(
    Foobar::Foobar
    PROPERTIES
    IMPORTED_LOCATION "${Foobar_LIBRARY}"
    INTERFACE_INCLUDE_DIRECTORIES "${Foobar_INCLUDE_DIRS}"
  )
endif()

If I understand correctly, the FindPackageHandleStandardArgs sets both the Foobar_FOUND result variable and the upper-cased FOOBAR_FOUND. Also in recent CMake versions both hint variables Foobar_ROOT and FOOBAR_ROOT can be used.

Now, one of the main issues I’m currently having difficulty to get used to is this mixed case of the result and cache variables <PackageName>_UPPER_CASE defined by the FindFoobar.cmake module.

Because, in case there is a lot of find modules in project and looking at them from the big picture, they look really difficult to read and understand from the beginner point of view. On one hand there is kind of a guideline to name all cache variables in upper case, but these are mixed case.

And also, there is a probability that some package might export its CMake configuration and can be found on the system with find_package(Foobar). So there the project consuming the package must write the find module in sync with upstream and also take into consideration its cache options option(FOOBAR_OPTION ...) for the configuration phase when using FetchContent, etc.

Question: Is it fine, for the find module to be named in CamelCase but to use all variables as upper case?

find_package(Foobar)

# FOOBAR_INCLUDE_DIR
# FOOBAR_INCLUDE_DIRS
# FOOBAR_LIBRARIES
# FOOBAR_LIBRARY
# FOOBAR_VERSION
# ...

Or is it better to be consistent by naming the find module in upper case from the beginning and name all variables in uppercase and not deal with this issue: FindFOOBAR.cmakeFOOBAR_LIBRARY, FOOBAR_VERSION, …?

First, FindPackageHandleStandardArgs do not set the <PackageName>_FOUND variable. It is the responsibility of the module developer.
It only set, for legacy purpose, the <PACAKGE_UPPER_CASE>_FOUND variable. For new developments, it is strongly recommended to not use this variable.

Second, all variables must be prefixed by exactly the same name as the package name. Take a look at Standard Variables Names for more information about variables defined by a module.

Thank you for the reply. Now I’m confused about the <PackageName>_FOUND variables. Really? I wasn’t aware of this. Documentation says that it sets both these variables, the <PackageName>_FOUND and the upper-cased <PACKAGENAME>_FOUND:
https://cmake.org/cmake/help/latest/module/FindPackageHandleStandardArgs.html

And also this document then should mention this https://cmake.org/cmake/help/latest/manual/cmake-developer.7.html#standard-variable-names

Should the docs be updated? Because this is really not clear. And how should then user of the find module know if some package has been found?

Thanks for your help.

My mistake. I confused with other _FOUND variables used for COMPONENTS (i.e. <PackageName>_<ComponentName>_FOUND).

Indeed, find_package_handle_standard_args() set the<PackageName>_FOUND variable.

1 Like