diff options
author | Brad King <brad.king@kitware.com> | 2021-03-26 14:52:30 (GMT) |
---|---|---|
committer | Brad King <brad.king@kitware.com> | 2021-03-26 15:01:34 (GMT) |
commit | e34d64c04d5715710a811325ce68a1481a514d3c (patch) | |
tree | f85c22e046193eb2f4f18c20c29d63923243b8f2 /Modules | |
parent | cb0d1a49e67456612b6b211a52042e23a6bc9452 (diff) | |
download | CMake-e34d64c04d5715710a811325ce68a1481a514d3c.zip CMake-e34d64c04d5715710a811325ce68a1481a514d3c.tar.gz CMake-e34d64c04d5715710a811325ce68a1481a514d3c.tar.bz2 |
FindIntl: Fix detection of intl built in to C library
Since commit c30d06b7e6 (FindIntl: Add imported target, 2020-10-06,
v3.20.0-rc1~687^2) we use `check_symbol_exists` to check whether the
`intl` library is built in to the C library. On some platforms the
tested symbols are provided as macros so the check passes without
linking any symbol. Instead, check whether a sample source file both
compiles and links.
Fixes: #21979
Diffstat (limited to 'Modules')
-rw-r--r-- | Modules/FindIntl.cmake | 92 |
1 files changed, 53 insertions, 39 deletions
diff --git a/Modules/FindIntl.cmake b/Modules/FindIntl.cmake index f195f81..43398c1 100644 --- a/Modules/FindIntl.cmake +++ b/Modules/FindIntl.cmake @@ -37,24 +37,11 @@ The following cache variables may also be set: The libintl library (if any) -.. variable:: Intl_HAVE_GETTEXT_BUILTIN +.. variable:: Intl_IS_BUILT_IN .. versionadded:: 3.20 - True if gettext is in the C library - -.. variable:: Intl_HAVE_DCGETTEXT_BUILTIN - - .. versionadded:: 3.20 - - True if dcgettext is in the C library - -.. variable:: Intl_IS_BUILTIN - - .. versionadded:: 3.20 - - whether intl is a part of the C library determined from the result of - Intl_HAVE_GETTEXT_BUILTIN and Intl_HAVE_DCGETTEXT_BUILTIN + whether ``intl`` is a part of the C library. .. note:: On some platforms, such as Linux with GNU libc, the gettext @@ -68,46 +55,73 @@ The following cache variables may also be set: #]=======================================================================] include(${CMAKE_CURRENT_LIST_DIR}/CMakePushCheckState.cmake) -include(${CMAKE_CURRENT_LIST_DIR}/CheckSymbolExists.cmake) +if(CMAKE_C_COMPILER_LOADED) + include(${CMAKE_CURRENT_LIST_DIR}/CheckCSourceCompiles.cmake) +elseif(CMAKE_CXX_COMPILER_LOADED) + include(${CMAKE_CURRENT_LIST_DIR}/CheckCXXSourceCompiles.cmake) +else() + # If neither C nor CXX are loaded, implicit intl makes no sense. + set(Intl_IS_BUILT_IN FALSE) +endif() -# Check if we have libintl is a part of libc -cmake_push_check_state(RESET) -set(CMAKE_REQUIRED_QUIET TRUE) -check_symbol_exists(gettext libintl.h Intl_HAVE_GETTEXT_BUILTIN) -check_symbol_exists(dcgettext libintl.h Intl_HAVE_DCGETTEXT_BUILTIN) # redundant check -cmake_pop_check_state() +# Check if Intl is built in to the C library. +if(NOT DEFINED Intl_IS_BUILT_IN) + if(NOT DEFINED Intl_INCLUDE_DIR AND NOT DEFINED Intl_LIBRARY) + cmake_push_check_state(RESET) + set(CMAKE_REQUIRED_QUIET TRUE) + set(Intl_IMPLICIT_TEST_CODE [[ +#include <libintl.h> +int main(void) { + gettext(""); + dgettext("", ""); + dcgettext("", "", 0); + return 0; +} +]]) + if(CMAKE_C_COMPILER_LOADED) + check_c_source_compiles("${Intl_IMPLICIT_TEST_CODE}" Intl_IS_BUILT_IN) + else() + check_cxx_source_compiles("${Intl_IMPLICIT_TEST_CODE}" Intl_IS_BUILT_IN) + endif() + cmake_pop_check_state() + else() + set(Intl_IS_BUILT_IN FALSE) + endif() +endif() -if(Intl_HAVE_GETTEXT_BUILTIN AND Intl_HAVE_DCGETTEXT_BUILTIN) - set(Intl_IS_BUILTIN TRUE) +set(_Intl_REQUIRED_VARS) +if(Intl_IS_BUILT_IN) + set(_Intl_REQUIRED_VARS _Intl_IS_BUILT_IN_MSG) + set(_Intl_IS_BUILT_IN_MSG "built in to C library") else() - set(Intl_IS_BUILTIN FALSE) -endif() + set(_Intl_REQUIRED_VARS Intl_LIBRARY Intl_INCLUDE_DIR) -# Find include directory -find_path(Intl_INCLUDE_DIR - NAMES "libintl.h" - DOC "libintl include directory") -mark_as_advanced(Intl_INCLUDE_DIR) + find_path(Intl_INCLUDE_DIR + NAMES "libintl.h" + DOC "libintl include directory") + mark_as_advanced(Intl_INCLUDE_DIR) -# Find all Intl libraries -set(Intl_REQUIRED_VARS) -if(NOT Intl_IS_BUILTIN) find_library(Intl_LIBRARY "intl" "libintl" NAMES_PER_DIR DOC "libintl libraries (if not in the C library)") mark_as_advanced(Intl_LIBRARY) - list(APPEND Intl_REQUIRED_VARS Intl_LIBRARY) endif() include(${CMAKE_CURRENT_LIST_DIR}/FindPackageHandleStandardArgs.cmake) FIND_PACKAGE_HANDLE_STANDARD_ARGS(Intl FOUND_VAR Intl_FOUND - REQUIRED_VARS Intl_INCLUDE_DIR ${Intl_REQUIRED_VARS} + REQUIRED_VARS ${_Intl_REQUIRED_VARS} FAIL_MESSAGE "Failed to find Gettext libintl") -unset(Intl_REQUIRED_VARS) +unset(_Intl_REQUIRED_VARS) +unset(_Intl_IS_BUILT_IN_MSG) if(Intl_FOUND) - set(Intl_INCLUDE_DIRS "${Intl_INCLUDE_DIR}") - set(Intl_LIBRARIES "${Intl_LIBRARY}") + if(Intl_IS_BUILT_IN) + set(Intl_INCLUDE_DIRS "") + set(Intl_LIBRARIES "") + else() + set(Intl_INCLUDE_DIRS "${Intl_INCLUDE_DIR}") + set(Intl_LIBRARIES "${Intl_LIBRARY}") + endif() if(NOT TARGET Intl::Intl) add_library(Intl::Intl INTERFACE IMPORTED) set_target_properties(Intl::Intl PROPERTIES |