summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBrad King <brad.king@kitware.com>2020-05-25 14:58:54 (GMT)
committerKitware Robot <kwrobot@kitware.com>2020-05-25 14:59:01 (GMT)
commita354b7f21e858728606ddc7c275bad35914d8eaa (patch)
tree3766fcf93b02ebbe0ecc48bbce0f7e99258850d5
parentb82bdbf44aeef29ba7b266989f1557a0ffcaa969 (diff)
parentaf96c0f4faf5bf9f4a4dbc958b09a1dfc58dab38 (diff)
downloadCMake-a354b7f21e858728606ddc7c275bad35914d8eaa.zip
CMake-a354b7f21e858728606ddc7c275bad35914d8eaa.tar.gz
CMake-a354b7f21e858728606ddc7c275bad35914d8eaa.tar.bz2
Merge topic 'CheckLinkerFlag-module'
af96c0f4fa CheckLinkerFlag: Add module to check validity of linker flags 3c4cc77d55 Tests: Extend Fortran compiler information Acked-by: Kitware Robot <kwrobot@kitware.com> Merge-request: !4777
-rw-r--r--Help/manual/cmake-modules.7.rst1
-rw-r--r--Help/module/CheckLinkerFlag.rst1
-rw-r--r--Help/release/dev/CheckLinkerFlag.rst5
-rw-r--r--Modules/CheckLinkerFlag.cmake81
-rw-r--r--Tests/CheckFortran.cmake3
-rw-r--r--Tests/RunCMake/CMakeLists.txt6
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CMakeLists.txt5
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CheckCLinkerFlag.cmake3
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CheckCXXLinkerFlag.cmake3
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CheckFortranLinkerFlag.cmake3
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CheckLinkerFlag.cmake14
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CheckOBJCLinkerFlag.cmake3
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/CheckOBJCXXLinkerFlag.cmake3
-rw-r--r--Tests/RunCMake/CheckLinkerFlag/RunCMakeTest.cmake14
14 files changed, 145 insertions, 0 deletions
diff --git a/Help/manual/cmake-modules.7.rst b/Help/manual/cmake-modules.7.rst
index be64112..50131e8 100644
--- a/Help/manual/cmake-modules.7.rst
+++ b/Help/manual/cmake-modules.7.rst
@@ -36,6 +36,7 @@ These modules are loaded using the :command:`include` command.
/module/CheckIncludeFiles
/module/CheckLanguage
/module/CheckLibraryExists
+ /module/CheckLinkerFlag
/module/CheckOBJCCompilerFlag
/module/CheckOBJCSourceCompiles
/module/CheckOBJCSourceRuns
diff --git a/Help/module/CheckLinkerFlag.rst b/Help/module/CheckLinkerFlag.rst
new file mode 100644
index 0000000..4005725
--- /dev/null
+++ b/Help/module/CheckLinkerFlag.rst
@@ -0,0 +1 @@
+.. cmake-module:: ../../Modules/CheckLinkerFlag.cmake
diff --git a/Help/release/dev/CheckLinkerFlag.rst b/Help/release/dev/CheckLinkerFlag.rst
new file mode 100644
index 0000000..fd48d99
--- /dev/null
+++ b/Help/release/dev/CheckLinkerFlag.rst
@@ -0,0 +1,5 @@
+CheckLinkerFlag
+---------------
+
+* New :module:`CheckLinkerFlag` module has been added to provide a facility to
+ check validity of link flags.
diff --git a/Modules/CheckLinkerFlag.cmake b/Modules/CheckLinkerFlag.cmake
new file mode 100644
index 0000000..beda5fe
--- /dev/null
+++ b/Modules/CheckLinkerFlag.cmake
@@ -0,0 +1,81 @@
+# Distributed under the OSI-approved BSD 3-Clause License. See accompanying
+# file Copyright.txt or https://cmake.org/licensing for details.
+
+#[=======================================================================[.rst:
+CheckLinkerFlag
+---------------
+
+Check whether the compiler supports a given link flag.
+
+.. command:: check_linker_flag
+
+ .. code-block:: cmake
+
+ check_linker_flag(<lang> <flag> <var>)
+
+Check that the link ``<flag>`` is accepted by the ``<lang>`` compiler without
+a diagnostic. Stores the result in an internal cache entry named ``<var>``.
+
+This command temporarily sets the ``CMAKE_REQUIRED_LINK_OPTIONS`` variable
+and calls the ``check_<lang>_source_compiles`` macro from the
+``Check<lang>SourceCompiles`` module (:module:`CheckCSourceCompiles`,
+:module:`CheckCSourceCompiles`, :module:`CheckCXXSourceCompiles`,
+:module:`CheckOBJCSourceCompiles`, :module:`CheckOBJCXXSourceCompiles` or
+:module:`CheckFortranSourceCompiles`). See documentation of these
+modules for a listing of variables that can otherwise modify the build.
+
+The underlying implementation rely on :prop_tgt:`LINK_OPTIONS` property to
+check the specified flag. The ``LINKER:`` prefix, as described in
+:command:`target_link_options` command, can be used as well.
+
+A positive result from this check indicates only that the compiler did not
+issue a diagnostic message when given the link flag. Whether the flag has any
+effect or even a specific one is beyond the scope of this module.
+
+.. note::
+ Since the :command:`try_compile` command forwards flags from variables
+ like :variable:`CMAKE_<LANG>_FLAGS`, unknown flags in such variables may
+ cause a false negative for this check.
+#]=======================================================================]
+
+include_guard(GLOBAL)
+
+include(CMakeCheckCompilerFlagCommonPatterns)
+
+function(CHECK_LINKER_FLAG _lang _flag _var)
+ get_property (_supported_languages GLOBAL PROPERTY ENABLED_LANGUAGES)
+ if (NOT _lang IN_LIST _supported_languages)
+ message (SEND_ERROR "check_linker_flag: ${_lang}: unknown language.")
+ return()
+ endif()
+
+ include (Check${_lang}SourceCompiles)
+
+ set(CMAKE_REQUIRED_LINK_OPTIONS "${_flag}")
+
+ # Normalize locale during test compilation.
+ set(_locale_vars LC_ALL LC_MESSAGES LANG)
+ foreach(v IN LISTS _locale_vars)
+ set(_locale_vars_saved_${v} "$ENV{${v}}")
+ set(ENV{${v}} C)
+ endforeach()
+
+ if (_lang MATCHES "^(C|CXX)$")
+ set (_source "int main() { return 0; }")
+ elseif (_lang STREQUAL "Fortran")
+ set (_source " program test\n stop\n end program")
+ elseif (_lang MATCHES "^(OBJC|OBJCXX)$")
+ set (_source "#ifndef __OBJC__\n# error \"Not an Objective-C++ compiler\"\n#endif\nint main(void) { return 0; }")
+ else()
+ message (SEND_ERROR "check_linker_flag: ${_lang}: unsupported language.")
+ return()
+ endif()
+ check_compiler_flag_common_patterns(_common_patterns)
+
+ cmake_language (CALL check_${_lang}_source_compiles "${_source}" ${_var} ${_common_patterns})
+
+ foreach(v IN LISTS _locale_vars)
+ set(ENV{${v}} ${_locale_vars_saved_${v}})
+ endforeach()
+ set(${_var} "${${_var}}" PARENT_SCOPE)
+endfunction()
diff --git a/Tests/CheckFortran.cmake b/Tests/CheckFortran.cmake
index 16a8ed2..33e1bfb 100644
--- a/Tests/CheckFortran.cmake
+++ b/Tests/CheckFortran.cmake
@@ -11,6 +11,7 @@ if(NOT DEFINED CMAKE_Fortran_COMPILER)
project(CheckFortran Fortran)
file(WRITE \"\${CMAKE_CURRENT_BINARY_DIR}/result.cmake\"
\"set(CMAKE_Fortran_COMPILER \\\"\${CMAKE_Fortran_COMPILER}\\\")\\n\"
+ \"set(CMAKE_Fortran_COMPILER_ID \\\"\${CMAKE_Fortran_COMPILER_ID}\\\")\\n\"
\"set(CMAKE_Fortran_FLAGS \\\"\${CMAKE_Fortran_FLAGS}\\\")\\n\"
\"set(CMAKE_Fortran_COMPILER_SUPPORTS_F90 \\\"\${CMAKE_Fortran_COMPILER_SUPPORTS_F90}\\\")\\n\"
)
@@ -45,6 +46,8 @@ file(WRITE \"\${CMAKE_CURRENT_BINARY_DIR}/result.cmake\"
message(STATUS "${_desc} - ${CMAKE_Fortran_COMPILER}")
set(CMAKE_Fortran_COMPILER "${CMAKE_Fortran_COMPILER}" CACHE FILEPATH "Fortran compiler")
mark_as_advanced(CMAKE_Fortran_COMPILER)
+ set(CMAKE_Fortran_COMPILER_ID "${CMAKE_Fortran_COMPILER_ID}" CACHE STRING "Fortran compiler Id")
+ mark_as_advanced(CMAKE_Fortran_COMPILER_ID)
set(CMAKE_Fortran_FLAGS "${CMAKE_Fortran_FLAGS}" CACHE STRING "Fortran flags")
mark_as_advanced(CMAKE_Fortran_FLAGS)
set(CMAKE_Fortran_COMPILER_SUPPORTS_F90 "${CMAKE_Fortran_COMPILER_SUPPORTS_F90}" CACHE BOOL "Fortran compiler supports F90")
diff --git a/Tests/RunCMake/CMakeLists.txt b/Tests/RunCMake/CMakeLists.txt
index 5f3f38b..983f7e4 100644
--- a/Tests/RunCMake/CMakeLists.txt
+++ b/Tests/RunCMake/CMakeLists.txt
@@ -488,6 +488,12 @@ add_RunCMake_test(target_include_directories)
add_RunCMake_test(target_sources)
add_RunCMake_test(CheckModules)
add_RunCMake_test(CheckIPOSupported)
+if (CMAKE_SYSTEM_NAME MATCHES "(Linux|Darwin)"
+ AND (CMAKE_C_COMPILER_ID MATCHES "Clang|GNU" OR CMAKE_Fortran_COMPILER_ID MATCHES "GNU"))
+ add_RunCMake_test(CheckLinkerFlag -DCMAKE_C_COMPILER_ID=${CMAKE_C_COMPILER_ID}
+ -DCMAKE_Fortran_COMPILER_ID=${CMAKE_Fortran_COMPILER_ID})
+endif()
+
add_RunCMake_test(CommandLine -DCMAKE_SYSTEM_NAME=${CMAKE_SYSTEM_NAME} -DCYGWIN=${CYGWIN} -DPYTHON_EXECUTABLE=${PYTHON_EXECUTABLE})
add_RunCMake_test(CommandLineTar)
diff --git a/Tests/RunCMake/CheckLinkerFlag/CMakeLists.txt b/Tests/RunCMake/CheckLinkerFlag/CMakeLists.txt
new file mode 100644
index 0000000..0421e28
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CMakeLists.txt
@@ -0,0 +1,5 @@
+cmake_minimum_required(VERSION 3.13)
+
+project(${RunCMake_TEST} LANGUAGES NONE)
+
+include(${RunCMake_TEST}.cmake)
diff --git a/Tests/RunCMake/CheckLinkerFlag/CheckCLinkerFlag.cmake b/Tests/RunCMake/CheckLinkerFlag/CheckCLinkerFlag.cmake
new file mode 100644
index 0000000..c8e87a4
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CheckCLinkerFlag.cmake
@@ -0,0 +1,3 @@
+
+set (CHECK_LANGUAGE C)
+include ("${CMAKE_CURRENT_SOURCE_DIR}/CheckLinkerFlag.cmake")
diff --git a/Tests/RunCMake/CheckLinkerFlag/CheckCXXLinkerFlag.cmake b/Tests/RunCMake/CheckLinkerFlag/CheckCXXLinkerFlag.cmake
new file mode 100644
index 0000000..4e299b9
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CheckCXXLinkerFlag.cmake
@@ -0,0 +1,3 @@
+
+set (CHECK_LANGUAGE CXX)
+include ("${CMAKE_CURRENT_SOURCE_DIR}/CheckLinkerFlag.cmake")
diff --git a/Tests/RunCMake/CheckLinkerFlag/CheckFortranLinkerFlag.cmake b/Tests/RunCMake/CheckLinkerFlag/CheckFortranLinkerFlag.cmake
new file mode 100644
index 0000000..bca288e
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CheckFortranLinkerFlag.cmake
@@ -0,0 +1,3 @@
+
+set (CHECK_LANGUAGE Fortran)
+include ("${CMAKE_CURRENT_SOURCE_DIR}/CheckLinkerFlag.cmake")
diff --git a/Tests/RunCMake/CheckLinkerFlag/CheckLinkerFlag.cmake b/Tests/RunCMake/CheckLinkerFlag/CheckLinkerFlag.cmake
new file mode 100644
index 0000000..c3bd465
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CheckLinkerFlag.cmake
@@ -0,0 +1,14 @@
+
+enable_language (${CHECK_LANGUAGE})
+
+include(CheckLinkerFlag)
+
+check_linker_flag(${CHECK_LANGUAGE} "LINKER:-L,/dir" VALID_LINKER_FLAG)
+if(NOT VALID_LINKER_FLAG)
+ message(SEND_ERROR "Test fail for valid linker flag.")
+endif()
+
+check_linker_flag(${CHECK_LANGUAGE} "LINKER:-D" INVALID_LINKER_FLAG)
+if(INVALID_LINKER_FLAG)
+ message(SEND_ERROR "Test fail for invalid linker flag.")
+endif()
diff --git a/Tests/RunCMake/CheckLinkerFlag/CheckOBJCLinkerFlag.cmake b/Tests/RunCMake/CheckLinkerFlag/CheckOBJCLinkerFlag.cmake
new file mode 100644
index 0000000..fa1d18e
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CheckOBJCLinkerFlag.cmake
@@ -0,0 +1,3 @@
+
+set (CHECK_LANGUAGE OBJC)
+include ("${CMAKE_CURRENT_SOURCE_DIR}/CheckLinkerFlag.cmake")
diff --git a/Tests/RunCMake/CheckLinkerFlag/CheckOBJCXXLinkerFlag.cmake b/Tests/RunCMake/CheckLinkerFlag/CheckOBJCXXLinkerFlag.cmake
new file mode 100644
index 0000000..414efb8
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/CheckOBJCXXLinkerFlag.cmake
@@ -0,0 +1,3 @@
+
+set (CHECK_LANGUAGE OBJCXX)
+include ("${CMAKE_CURRENT_SOURCE_DIR}/CheckLinkerFlag.cmake")
diff --git a/Tests/RunCMake/CheckLinkerFlag/RunCMakeTest.cmake b/Tests/RunCMake/CheckLinkerFlag/RunCMakeTest.cmake
new file mode 100644
index 0000000..224a2a3
--- /dev/null
+++ b/Tests/RunCMake/CheckLinkerFlag/RunCMakeTest.cmake
@@ -0,0 +1,14 @@
+include(RunCMake)
+
+if (CMAKE_C_COMPILER_ID MATCHES "Clang|GNU")
+ run_cmake(CheckCLinkerFlag)
+ run_cmake(CheckCXXLinkerFlag)
+ if (APPLE)
+ run_cmake(CheckOBJCLinkerFlag)
+ run_cmake(CheckOBJCXXLinkerFlag)
+ endif()
+endif()
+
+if (CMAKE_Fortran_COMPILER_ID MATCHES "GNU")
+ run_cmake(CheckFortranLinkerFlag)
+endif()