Merge topic 'openssl-3.0.0' into release-3.17

61d746e592 FindOpenSSL: Detect OpenSSL 3.0.0

Acked-by: Kitware Robot <kwrobot@kitware.com>
Merge-request: !4805
diff --git a/CMakeLists.txt b/CMakeLists.txt
index fb7b9b7..0d6a38c 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -810,7 +810,7 @@
     PATTERN "*.sh*" PERMISSIONS OWNER_READ OWNER_EXECUTE OWNER_WRITE
                                 GROUP_READ GROUP_EXECUTE
                                 WORLD_READ WORLD_EXECUTE
-    PATTERN "ExportImportList"
+    REGEX "/(ExportImportList|cpp)$"
       PERMISSIONS OWNER_READ OWNER_EXECUTE OWNER_WRITE
                   GROUP_READ GROUP_EXECUTE
                   WORLD_READ WORLD_EXECUTE
diff --git a/Help/command/add_compile_definitions.rst b/Help/command/add_compile_definitions.rst
index 8225da7..e10aba0 100644
--- a/Help/command/add_compile_definitions.rst
+++ b/Help/command/add_compile_definitions.rst
@@ -7,10 +7,12 @@
 
   add_compile_definitions(<definition> ...)
 
-Adds preprocessor definitions to the compiler command line for targets in the
-current directory and below (whether added before or after this command is
-invoked). See documentation of the :prop_dir:`directory <COMPILE_DEFINITIONS>`
-and :prop_tgt:`target <COMPILE_DEFINITIONS>` ``COMPILE_DEFINITIONS`` properties.
+Adds preprocessor definitions to the compiler command line.
+
+The preprocessor definitions are added to the :prop_dir:`COMPILE_DEFINITIONS`
+directory property for the current ``CMakeLists`` file. They are also added to
+the :prop_tgt:`COMPILE_DEFINITIONS` target property for each target in the
+current ``CMakeLists`` file.
 
 Definitions are specified using the syntax ``VAR`` or ``VAR=value``.
 Function-style definitions are not supported. CMake will automatically
diff --git a/Help/command/add_definitions.rst b/Help/command/add_definitions.rst
index d06b01c..fe69188 100644
--- a/Help/command/add_definitions.rst
+++ b/Help/command/add_definitions.rst
@@ -8,9 +8,9 @@
   add_definitions(-DFOO -DBAR ...)
 
 Adds definitions to the compiler command line for targets in the current
-directory and below (whether added before or after this command is invoked).
-This command can be used to add any flags, but it is intended to add
-preprocessor definitions.
+directory, whether added before or after this command is invoked, and for
+the ones in sub-directories added after. This command can be used to add any
+flags, but it is intended to add preprocessor definitions.
 
 .. note::
 
diff --git a/Help/command/try_compile.rst b/Help/command/try_compile.rst
index edbf92c..323077a 100644
--- a/Help/command/try_compile.rst
+++ b/Help/command/try_compile.rst
@@ -135,6 +135,7 @@
 try_compile CMakeLists.txt to initialize compile target properties with
 default values:
 
+* :variable:`CMAKE_CUDA_RUNTIME_LIBRARY`
 * :variable:`CMAKE_ENABLE_EXPORTS`
 * :variable:`CMAKE_LINK_SEARCH_START_STATIC`
 * :variable:`CMAKE_LINK_SEARCH_END_STATIC`
diff --git a/Help/envvar/OBJC.rst b/Help/envvar/OBJC.rst
new file mode 100644
index 0000000..30c0d13
--- /dev/null
+++ b/Help/envvar/OBJC.rst
@@ -0,0 +1,14 @@
+OBJC
+----
+
+.. include:: ENV_VAR.txt
+
+Preferred executable for compiling ``OBJC`` language files. Will only be used
+by CMake on the first configuration to determine ``OBJC`` compiler, after
+which the value for ``OBJC`` is stored in the cache as
+:variable:`CMAKE_OBJC_COMPILER <CMAKE_<LANG>_COMPILER>`. For any configuration
+run (including the first), the environment variable will be ignored if the
+:variable:`CMAKE_OBJC_COMPILER <CMAKE_<LANG>_COMPILER>` variable is defined.
+
+If ``OBJC`` is not defined, the :envvar:`CC` environment variable will
+be checked instead.
diff --git a/Help/envvar/OBJCXX.rst b/Help/envvar/OBJCXX.rst
new file mode 100644
index 0000000..a72f7e7
--- /dev/null
+++ b/Help/envvar/OBJCXX.rst
@@ -0,0 +1,14 @@
+OBJCXX
+------
+
+.. include:: ENV_VAR.txt
+
+Preferred executable for compiling ``OBJCXX`` language files. Will only be used
+by CMake on the first configuration to determine ``OBJCXX`` compiler, after
+which the value for ``OBJCXX`` is stored in the cache as
+:variable:`CMAKE_OBJCXX_COMPILER <CMAKE_<LANG>_COMPILER>`. For any configuration
+run (including the first), the environment variable will be ignored if the
+:variable:`CMAKE_OBJCXX_COMPILER <CMAKE_<LANG>_COMPILER>` variable is defined.
+
+If ``OBJCXX`` is not defined, the :envvar:`CXX` environment variable will
+be checked instead.
diff --git a/Help/manual/cmake-env-variables.7.rst b/Help/manual/cmake-env-variables.7.rst
index adfc39e..f72e414 100644
--- a/Help/manual/cmake-env-variables.7.rst
+++ b/Help/manual/cmake-env-variables.7.rst
@@ -56,6 +56,8 @@
    /envvar/CXXFLAGS
    /envvar/FC
    /envvar/FFLAGS
+   /envvar/OBJC
+   /envvar/OBJCXX
    /envvar/RC
    /envvar/RCFLAGS
    /envvar/SWIFTC
diff --git a/Help/prop_tgt/CUDA_RUNTIME_LIBRARY.rst b/Help/prop_tgt/CUDA_RUNTIME_LIBRARY.rst
index 0782765..11b344c 100644
--- a/Help/prop_tgt/CUDA_RUNTIME_LIBRARY.rst
+++ b/Help/prop_tgt/CUDA_RUNTIME_LIBRARY.rst
@@ -10,8 +10,8 @@
 Contents of ``CUDA_RUNTIME_LIBRARY`` may use
 :manual:`generator expressions <cmake-generator-expressions(7)>`.
 
-If this property is not set then CMake uses the default value
-``Static`` to select the CUDA runtime library.
+If that property is not set then CMake uses an appropriate default
+value based on the compiler to select the CUDA runtime library.
 
 .. note::
 
diff --git a/Help/release/3.16.rst b/Help/release/3.16.rst
index e2d6788..f3fdb08 100644
--- a/Help/release/3.16.rst
+++ b/Help/release/3.16.rst
@@ -303,3 +303,16 @@
   Additionally, the modules no longer expose their internal ``_Python*``
   cache entries publicly.  CMake 3.16.0 through 3.16.4 accidentally
   made them visible as advanced cache entries.
+
+3.16.7
+------
+
+* Selection of the Objective C or C++ compiler now considers the
+  :envvar:`CC` or :envvar:`CXX` environment variable if the
+  :envvar:`OBJC` or :envvar:`OBJCXX` environment variable is not set.
+
+* The :module:`FindPkgConfig` module now extracts include directories
+  prefixed with ``-isystem`` into the ``*_INCLUDE_DIRS`` variables and
+  :prop_tgt:`INTERFACE_INCLUDE_DIRECTORIES` target properties.
+  Previously they would be places in ``*_CFLAGS_OTHER`` variables and
+  :prop_tgt:`INTERFACE_COMPILE_OPTIONS` target properties.
diff --git a/Help/release/3.17.rst b/Help/release/3.17.rst
index 7c5b44d..b7c66d8 100644
--- a/Help/release/3.17.rst
+++ b/Help/release/3.17.rst
@@ -333,3 +333,16 @@
 * CMake 3.17.0 updated the :cpack_gen:`CPack NSIS Generator` with changes
   that require NSIS 3.0 or later.  CMake 3.17.1 now enforces the use
   of a sufficiently new version.
+
+3.17.3
+------
+
+* Selection of the Objective C or C++ compiler now considers the
+  :envvar:`CC` or :envvar:`CXX` environment variable if the
+  :envvar:`OBJC` or :envvar:`OBJCXX` environment variable is not set.
+
+* The :module:`FindPkgConfig` module now extracts include directories
+  prefixed with ``-isystem`` into the ``*_INCLUDE_DIRS`` variables and
+  :prop_tgt:`INTERFACE_INCLUDE_DIRECTORIES` target properties.
+  Previously they would be places in ``*_CFLAGS_OTHER`` variables and
+  :prop_tgt:`INTERFACE_COMPILE_OPTIONS` target properties.
diff --git a/Help/variable/CMAKE_CUDA_RUNTIME_LIBRARY.rst b/Help/variable/CMAKE_CUDA_RUNTIME_LIBRARY.rst
index ea1c1b8..e3205d3 100644
--- a/Help/variable/CMAKE_CUDA_RUNTIME_LIBRARY.rst
+++ b/Help/variable/CMAKE_CUDA_RUNTIME_LIBRARY.rst
@@ -1,7 +1,7 @@
 CMAKE_CUDA_RUNTIME_LIBRARY
 --------------------------
 
-Select the CUDA runtime library for use by compilers targeting the MSVC ABI.
+Select the CUDA runtime library for use when compiling and linking CUDA.
 This variable is used to initialize the :prop_tgt:`CUDA_RUNTIME_LIBRARY`
 property on all targets as they are created.
 
@@ -14,7 +14,8 @@
 
 If this variable is not set then the :prop_tgt:`CUDA_RUNTIME_LIBRARY` target
 property will not be set automatically.  If that property is not set then
-CMake uses the default value ``Static`` to select the CUDA runtime library.
+CMake uses an appropriate default value based on the compiler to select the
+CUDA runtime library.
 
 .. note::
 
diff --git a/Modules/CMakeCUDACompiler.cmake.in b/Modules/CMakeCUDACompiler.cmake.in
index 4a615a3..04a4c42 100644
--- a/Modules/CMakeCUDACompiler.cmake.in
+++ b/Modules/CMakeCUDACompiler.cmake.in
@@ -53,5 +53,7 @@
 set(CMAKE_CUDA_IMPLICIT_LINK_DIRECTORIES "@CMAKE_CUDA_IMPLICIT_LINK_DIRECTORIES@")
 set(CMAKE_CUDA_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES "@CMAKE_CUDA_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES@")
 
+@_SET_CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT@
+
 set(CMAKE_LINKER "@CMAKE_LINKER@")
 set(CMAKE_MT "@CMAKE_MT@")
diff --git a/Modules/CMakeDetermineCUDACompiler.cmake b/Modules/CMakeDetermineCUDACompiler.cmake
index 7d7fb9a..baf1501 100644
--- a/Modules/CMakeDetermineCUDACompiler.cmake
+++ b/Modules/CMakeDetermineCUDACompiler.cmake
@@ -86,6 +86,20 @@
   set(CMAKE_CUDA_HOST_IMPLICIT_LINK_LIBRARIES "")
   set(CMAKE_CUDA_HOST_IMPLICIT_LINK_DIRECTORIES "")
   set(CMAKE_CUDA_HOST_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES "")
+
+  # We do not currently detect CMAKE_CUDA_HOST_IMPLICIT_LINK_LIBRARIES but we
+  # do need to detect CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT from the compiler by
+  # looking at which cudart library exists in the implicit link libraries passed
+  # to the host linker.
+  if(CMAKE_CUDA_COMPILER_PRODUCED_OUTPUT MATCHES "link\\.exe [^\n]*cudart_static\\.lib")
+    set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "STATIC")
+  elseif(CMAKE_CUDA_COMPILER_PRODUCED_OUTPUT MATCHES "link\\.exe [^\n]*cudart\\.lib")
+    set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "SHARED")
+  else()
+    set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "NONE")
+  endif()
+  set(_SET_CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT
+    "set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT \"${CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT}\")")
 elseif(CMAKE_CUDA_COMPILER_ID STREQUAL NVIDIA)
   set(_nvcc_log "")
   string(REPLACE "\r" "" _nvcc_output_orig "${CMAKE_CUDA_COMPILER_PRODUCED_OUTPUT}")
@@ -179,6 +193,20 @@
                                    log
                                    "${CMAKE_CUDA_IMPLICIT_OBJECT_REGEX}")
 
+    # Detect CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT from the compiler by looking at which
+    # cudart library exists in the implicit link libraries passed to the host linker.
+    # This is required when a project sets the cuda runtime library as part of the
+    # initial flags.
+    if(";${CMAKE_CUDA_HOST_IMPLICIT_LINK_LIBRARIES};" MATCHES [[;cudart_static(\.lib)?;]])
+      set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "STATIC")
+    elseif(";${CMAKE_CUDA_HOST_IMPLICIT_LINK_LIBRARIES};" MATCHES [[;cudart(\.lib)?;]])
+      set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "SHARED")
+    else()
+      set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "NONE")
+    endif()
+    set(_SET_CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT
+      "set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT \"${CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT}\")")
+
     file(APPEND ${CMAKE_BINARY_DIR}${CMAKE_FILES_DIRECTORY}/CMakeOutput.log
       "Parsed CUDA nvcc implicit link information from above output:\n${_nvcc_log}\n${log}\n\n")
   else()
diff --git a/Modules/CMakeDetermineCompilerId.cmake b/Modules/CMakeDetermineCompilerId.cmake
index d3ed45b..9eeb7a1 100644
--- a/Modules/CMakeDetermineCompilerId.cmake
+++ b/Modules/CMakeDetermineCompilerId.cmake
@@ -381,7 +381,11 @@
       if(CMAKE_VS_PLATFORM_NAME STREQUAL x64)
         set(id_ItemDefinitionGroup_entry "<CudaCompile><TargetMachinePlatform>64</TargetMachinePlatform><AdditionalOptions>%(AdditionalOptions)-v</AdditionalOptions></CudaCompile>")
       endif()
-      set(id_Link_AdditionalDependencies "<AdditionalDependencies>cudart.lib</AdditionalDependencies>")
+      if(CMAKE_CUDA_FLAGS MATCHES "(^| )-cudart +shared( |$)")
+        set(id_Link_AdditionalDependencies "<AdditionalDependencies>cudart.lib</AdditionalDependencies>")
+      else()
+        set(id_Link_AdditionalDependencies "<AdditionalDependencies>cudart_static.lib</AdditionalDependencies>")
+      endif()
     endif()
     configure_file(${CMAKE_ROOT}/Modules/CompilerId/VS-${v}.${ext}.in
       ${id_dir}/CompilerId${lang}.${ext} @ONLY)
diff --git a/Modules/CMakeDetermineOBJCCompiler.cmake b/Modules/CMakeDetermineOBJCCompiler.cmake
index ad13eab..11b47fd 100644
--- a/Modules/CMakeDetermineOBJCCompiler.cmake
+++ b/Modules/CMakeDetermineOBJCCompiler.cmake
@@ -34,16 +34,19 @@
   if(NOT CMAKE_OBJC_COMPILER)
     set(CMAKE_OBJC_COMPILER_INIT NOTFOUND)
 
-    # prefer the environment variable OBJC
-    if($ENV{OBJC} MATCHES ".+")
-      get_filename_component(CMAKE_OBJC_COMPILER_INIT $ENV{OBJC} PROGRAM PROGRAM_ARGS CMAKE_OBJC_FLAGS_ENV_INIT)
-      if(CMAKE_OBJC_FLAGS_ENV_INIT)
-        set(CMAKE_OBJC_COMPILER_ARG1 "${CMAKE_OBJC_FLAGS_ENV_INIT}" CACHE STRING "First argument to Objective-C compiler")
+    # prefer the environment variable OBJC or CC
+    foreach(var OBJC CC)
+      if($ENV{${var}} MATCHES ".+")
+        get_filename_component(CMAKE_OBJC_COMPILER_INIT $ENV{${var}} PROGRAM PROGRAM_ARGS CMAKE_OBJC_FLAGS_ENV_INIT)
+        if(CMAKE_OBJC_FLAGS_ENV_INIT)
+          set(CMAKE_OBJC_COMPILER_ARG1 "${CMAKE_OBJC_FLAGS_ENV_INIT}" CACHE STRING "First argument to Objective-C compiler")
+        endif()
+        if(NOT EXISTS ${CMAKE_OBJC_COMPILER_INIT})
+          message(FATAL_ERROR "Could not find compiler set in environment variable ${var}:\n  $ENV{${var}}")
+        endif()
+        break()
       endif()
-      if(NOT EXISTS ${CMAKE_OBJC_COMPILER_INIT})
-        message(FATAL_ERROR "Could not find compiler set in environment variable OBJC:\n$ENV{OBJC}.")
-      endif()
-    endif()
+    endforeach()
 
     # next try prefer the compiler specified by the generator
     if(CMAKE_GENERATOR_OBJC)
diff --git a/Modules/CMakeDetermineOBJCXXCompiler.cmake b/Modules/CMakeDetermineOBJCXXCompiler.cmake
index 60fcbb3..db874d1 100644
--- a/Modules/CMakeDetermineOBJCXXCompiler.cmake
+++ b/Modules/CMakeDetermineOBJCXXCompiler.cmake
@@ -36,16 +36,19 @@
   if(NOT CMAKE_OBJCXX_COMPILER)
     set(CMAKE_OBJCXX_COMPILER_INIT NOTFOUND)
 
-    # prefer the environment variable OBJCXX
-    if($ENV{OBJCXX} MATCHES ".+")
-      get_filename_component(CMAKE_OBJCXX_COMPILER_INIT $ENV{OBJCXX} PROGRAM PROGRAM_ARGS CMAKE_OBJCXX_FLAGS_ENV_INIT)
-      if(CMAKE_OBJCXX_FLAGS_ENV_INIT)
-        set(CMAKE_OBJCXX_COMPILER_ARG1 "${CMAKE_OBJCXX_FLAGS_ENV_INIT}" CACHE STRING "First argument to Objective-C++ compiler")
+    # prefer the environment variable OBJCXX or CXX
+    foreach(var OBJCXX CXX)
+      if($ENV{${var}} MATCHES ".+")
+        get_filename_component(CMAKE_OBJCXX_COMPILER_INIT $ENV{${var}} PROGRAM PROGRAM_ARGS CMAKE_OBJCXX_FLAGS_ENV_INIT)
+        if(CMAKE_OBJCXX_FLAGS_ENV_INIT)
+          set(CMAKE_OBJCXX_COMPILER_ARG1 "${CMAKE_OBJCXX_FLAGS_ENV_INIT}" CACHE STRING "First argument to Objective-C++ compiler")
+        endif()
+        if(NOT EXISTS ${CMAKE_OBJCXX_COMPILER_INIT})
+          message(FATAL_ERROR "Could not find compiler set in environment variable ${var}:\n  $ENV{${var}}")
+        endif()
+        break()
       endif()
-      if(NOT EXISTS ${CMAKE_OBJCXX_COMPILER_INIT})
-        message(FATAL_ERROR "Could not find compiler set in environment variable OBJCXX:\n$ENV{OBJCXX}.\n${CMAKE_OBJCXX_COMPILER_INIT}")
-      endif()
-    endif()
+    endforeach()
 
     # next prefer the generator specified compiler
     if(CMAKE_GENERATOR_OBJCXX)
diff --git a/Modules/CheckLanguage.cmake b/Modules/CheckLanguage.cmake
index 997cc8d..1c4e7d3 100644
--- a/Modules/CheckLanguage.cmake
+++ b/Modules/CheckLanguage.cmake
@@ -43,7 +43,7 @@
     file(REMOVE_RECURSE ${CMAKE_CURRENT_BINARY_DIR}/CMakeFiles/Check${lang})
 
     set(extra_compiler_variables)
-    if(lang STREQUAL CUDA)
+    if(${lang} STREQUAL CUDA)
       set(extra_compiler_variables "set(CMAKE_CUDA_HOST_COMPILER \\\"\${CMAKE_CUDA_HOST_COMPILER}\\\")")
     endif()
 
diff --git a/Modules/Compiler/NVIDIA-CUDA.cmake b/Modules/Compiler/NVIDIA-CUDA.cmake
index 1f4d54d..671468d 100644
--- a/Modules/Compiler/NVIDIA-CUDA.cmake
+++ b/Modules/Compiler/NVIDIA-CUDA.cmake
@@ -43,7 +43,6 @@
 set(CMAKE_SHARED_LIBRARY_CREATE_CUDA_FLAGS -shared)
 set(CMAKE_INCLUDE_SYSTEM_FLAG_CUDA -isystem=)
 
-set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "STATIC")
 set(CMAKE_CUDA_RUNTIME_LIBRARY_LINK_OPTIONS_STATIC  "cudadevrt;cudart_static")
 set(CMAKE_CUDA_RUNTIME_LIBRARY_LINK_OPTIONS_SHARED  "cudadevrt;cudart")
 set(CMAKE_CUDA_RUNTIME_LIBRARY_LINK_OPTIONS_NONE    "")
diff --git a/Modules/ExternalProject.cmake b/Modules/ExternalProject.cmake
index a9448e5..12a91b3 100644
--- a/Modules/ExternalProject.cmake
+++ b/Modules/ExternalProject.cmake
@@ -2974,6 +2974,10 @@
       endif()
       _ep_write_initial_cache(${name} "${_ep_cache_args_script}" "${script_initial_cache_force}${script_initial_cache_default}")
       list(APPEND cmd "-C${_ep_cache_args_script}")
+      _ep_replace_location_tags(${name} _ep_cache_args_script)
+      set(_ep_cache_args_script
+        "${_ep_cache_args_script}"
+        PARENT_SCOPE)
     endif()
 
     list(APPEND cmd "<SOURCE_DIR><SOURCE_SUBDIR>")
diff --git a/Modules/FindBoost.cmake b/Modules/FindBoost.cmake
index 53fc4b7..1e815a0 100644
--- a/Modules/FindBoost.cmake
+++ b/Modules/FindBoost.cmake
@@ -750,7 +750,11 @@
         set(_boost_COMPILER "-mgw") # no GCC version encoding prior to 1.34
     else()
       _Boost_COMPILER_DUMPVERSION(_boost_COMPILER_VERSION _boost_COMPILER_VERSION_MAJOR _boost_COMPILER_VERSION_MINOR)
-      set(_boost_COMPILER "-mgw${_boost_COMPILER_VERSION}")
+      if(Boost_VERSION_STRING VERSION_GREATER_EQUAL 1.73 AND _boost_COMPILER_VERSION_MAJOR VERSION_GREATER_EQUAL 5)
+        set(_boost_COMPILER "-mgw${_boost_COMPILER_VERSION_MAJOR}")
+      else()
+        set(_boost_COMPILER "-mgw${_boost_COMPILER_VERSION}")
+      endif()
     endif()
   elseif (UNIX)
     _Boost_COMPILER_DUMPVERSION(_boost_COMPILER_VERSION _boost_COMPILER_VERSION_MAJOR _boost_COMPILER_VERSION_MINOR)
@@ -1449,7 +1453,7 @@
   # _Boost_COMPONENT_HEADERS.  See the instructions at the top of
   # _Boost_COMPONENT_DEPENDENCIES.
   set(_Boost_KNOWN_VERSIONS ${Boost_ADDITIONAL_VERSIONS}
-    "1.72.0" "1.72" "1.71.0" "1.71" "1.70.0" "1.70" "1.69.0" "1.69"
+    "1.73.0" "1.73" "1.72.0" "1.72" "1.71.0" "1.71" "1.70.0" "1.70" "1.69.0" "1.69"
     "1.68.0" "1.68" "1.67.0" "1.67" "1.66.0" "1.66" "1.65.1" "1.65.0" "1.65"
     "1.64.0" "1.64" "1.63.0" "1.63" "1.62.0" "1.62" "1.61.0" "1.61" "1.60.0" "1.60"
     "1.59.0" "1.59" "1.58.0" "1.58" "1.57.0" "1.57" "1.56.0" "1.56" "1.55.0" "1.55"
diff --git a/Modules/FindGTK2.cmake b/Modules/FindGTK2.cmake
index 565763d..62f1614 100644
--- a/Modules/FindGTK2.cmake
+++ b/Modules/FindGTK2.cmake
@@ -695,11 +695,14 @@
         _GTK2_FIND_LIBRARY    (CAIRO cairo false false)
         _GTK2_ADD_TARGET      (CAIRO)
 
+        _GTK2_FIND_INCLUDE_DIR(HARFBUZZ hb.h)
+        _GTK2_FIND_LIBRARY    (HARFBUZZ harfbuzz false false)
+        _GTK2_ADD_TARGET      (HARFBUZZ)
+
         _GTK2_FIND_INCLUDE_DIR(PANGO pango/pango.h)
         _GTK2_FIND_LIBRARY    (PANGO pango false true)
-        _GTK2_ADD_TARGET      (PANGO GTK2_DEPENDS gobject glib)
-
-        _GTK2_FIND_INCLUDE_DIR(HARFBUZZ hb.h)
+        _GTK2_ADD_TARGET      (PANGO GTK2_DEPENDS gobject glib
+                                     GTK2_OPTIONAL_DEPENDS harfbuzz)
 
         _GTK2_FIND_LIBRARY    (PANGOCAIRO pangocairo false true)
         _GTK2_ADD_TARGET      (PANGOCAIRO GTK2_DEPENDS pango cairo gobject glib)
diff --git a/Modules/FindPkgConfig.cmake b/Modules/FindPkgConfig.cmake
index c79f20f..28de575 100644
--- a/Modules/FindPkgConfig.cmake
+++ b/Modules/FindPkgConfig.cmake
@@ -364,6 +364,36 @@
   unset(_pkgconfig_path_old)
 endmacro()
 
+# pkg-config returns -isystem include directories in --cflags-only-other,
+# depending on the version and if there is a space between -isystem and
+# the actual path
+function(_pkgconfig_extract_isystem _prefix)
+  set(cflags "${${_prefix}_CFLAGS_OTHER}")
+  set(outflags "")
+  set(incdirs "${${_prefix}_INCLUDE_DIRS}")
+
+  set(next_is_isystem FALSE)
+  foreach (THING IN LISTS cflags)
+    # This may filter "-isystem -isystem". That would not work anyway,
+    # so let it happen.
+    if (THING STREQUAL "-isystem")
+      set(next_is_isystem TRUE)
+      continue()
+    endif ()
+    if (next_is_isystem)
+      set(next_is_isystem FALSE)
+      list(APPEND incdirs "${THING}")
+    elseif (THING MATCHES "^-isystem")
+      string(SUBSTRING "${THING}" 8 -1 THING)
+      list(APPEND incdirs "${THING}")
+    else ()
+      list(APPEND outflags "${THING}")
+    endif ()
+  endforeach ()
+  set(${_prefix}_CFLAGS_OTHER "${outflags}" PARENT_SCOPE)
+  set(${_prefix}_INCLUDE_DIRS "${incdirs}" PARENT_SCOPE)
+endfunction()
+
 ###
 macro(_pkg_check_modules_internal _is_required _is_silent _no_cmake_path _no_cmake_environment_path _imp_target _imp_target_global _prefix)
   _pkgconfig_unset(${_prefix}_FOUND)
@@ -497,14 +527,18 @@
       endforeach()
 
       # set variables which are combined for multiple modules
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LIBRARIES           "(^| )-l" --libs-only-l )
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LIBRARY_DIRS        "(^| )-L" --libs-only-L )
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LDFLAGS             ""        --libs )
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LDFLAGS_OTHER       ""        --libs-only-other )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LIBRARIES     "(^| )-l"             --libs-only-l )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LIBRARY_DIRS  "(^| )-L"             --libs-only-L )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LDFLAGS       ""                    --libs )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" LDFLAGS_OTHER ""                    --libs-only-other )
 
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" INCLUDE_DIRS        "(^| )-I" --cflags-only-I )
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" CFLAGS              ""        --cflags )
-      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" CFLAGS_OTHER        ""        --cflags-only-other )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" INCLUDE_DIRS  "(^| )(-I|-isystem ?)" --cflags-only-I )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" CFLAGS        ""                    --cflags )
+      _pkgconfig_invoke_dyn("${_pkg_check_modules_packages}" "${_prefix}" CFLAGS_OTHER  ""                    --cflags-only-other )
+
+      if (${_prefix}_CFLAGS_OTHER MATCHES "-isystem")
+        _pkgconfig_extract_isystem("${_prefix}")
+      endif ()
 
       _pkg_recalculate("${_prefix}" ${_no_cmake_path} ${_no_cmake_environment_path} ${_imp_target} ${_imp_target_global})
     endif()
diff --git a/Modules/FindPython/Support.cmake b/Modules/FindPython/Support.cmake
index 8789d7b..8aa7b97 100644
--- a/Modules/FindPython/Support.cmake
+++ b/Modules/FindPython/Support.cmake
@@ -22,9 +22,9 @@
 if (NOT DEFINED _${_PYTHON_PREFIX}_REQUIRED_VERSION_MAJOR)
   message (FATAL_ERROR "FindPython: INTERNAL ERROR")
 endif()
-if (_${_PYTHON_PREFIX}_REQUIRED_VERSION_MAJOR EQUAL 3)
+if (_${_PYTHON_PREFIX}_REQUIRED_VERSION_MAJOR EQUAL "3")
   set(_${_PYTHON_PREFIX}_VERSIONS 3.9 3.8 3.7 3.6 3.5 3.4 3.3 3.2 3.1 3.0)
-elseif (_${_PYTHON_PREFIX}_REQUIRED_VERSION_MAJOR EQUAL 2)
+elseif (_${_PYTHON_PREFIX}_REQUIRED_VERSION_MAJOR EQUAL "2")
   set(_${_PYTHON_PREFIX}_VERSIONS 2.7 2.6 2.5 2.4 2.3 2.2 2.1 2.0)
 else()
   message (FATAL_ERROR "FindPython: INTERNAL ERROR")
@@ -434,7 +434,7 @@
       list (GET versions 1 version_minor)
       list (GET versions 2 version_patch)
 
-      set (${_PGV_PREFIX}VERSION "${version_major}.${version_minor}" PARENT_SCOPE)
+      set (${_PGV_PREFIX}VERSION "${version_major}.${version_minor}.${version_patch}" PARENT_SCOPE)
       set (${_PGV_PREFIX}VERSION_MAJOR ${version_major} PARENT_SCOPE)
       set (${_PGV_PREFIX}VERSION_MINOR ${version_minor} PARENT_SCOPE)
       set (${_PGV_PREFIX}VERSION_PATCH ${version_patch} PARENT_SCOPE)
@@ -508,36 +508,46 @@
 
   get_filename_component (python_name "${_${_PYTHON_PREFIX}_EXECUTABLE}" NAME)
 
-  if (expected_version AND NOT python_name STREQUAL "python${expected_version}${abi}${CMAKE_EXECUTABLE_SUFFIX}")
-    # executable found must have a specific version
-    execute_process (COMMAND "${_${_PYTHON_PREFIX}_EXECUTABLE}" -c
-                             "import sys; sys.stdout.write('.'.join([str(x) for x in sys.version_info[:2]]))"
-                     RESULT_VARIABLE result
-                     OUTPUT_VARIABLE version
-                     ERROR_QUIET
-                     OUTPUT_STRIP_TRAILING_WHITESPACE)
-    if (result)
-      # interpreter is not usable
-      set (_${_PYTHON_PREFIX}_Interpreter_REASON_FAILURE "Cannot use the interpreter \"${_${_PYTHON_PREFIX}_EXECUTABLE}\"" PARENT_SCOPE)
-      set_property (CACHE _${_PYTHON_PREFIX}_EXECUTABLE PROPERTY VALUE "${_PYTHON_PREFIX}_EXECUTABLE-NOTFOUND")
-    else()
-      if (_PVI_EXACT AND NOT version VERSION_EQUAL expected_version)
-        # interpreter has wrong version
-        set (_${_PYTHON_PREFIX}_Interpreter_REASON_FAILURE "Wrong version for the interpreter \"${_${_PYTHON_PREFIX}_EXECUTABLE}\"" PARENT_SCOPE)
+  if (expected_version)
+    if (NOT python_name STREQUAL "python${expected_version}${abi}${CMAKE_EXECUTABLE_SUFFIX}")
+      # compute number of components for version
+      string (REGEX REPLACE "[^.]" "" dots "${expected_version}")
+      # add one dot because there is one dot less than there are components
+      string (LENGTH "${dots}." count)
+      if (count GREATER 3)
+        set (count 3)
+      endif()
+
+      # executable found must have a specific version
+      execute_process (COMMAND "${_${_PYTHON_PREFIX}_EXECUTABLE}" -c
+                               "import sys; sys.stdout.write('.'.join([str(x) for x in sys.version_info[:${count}]]))"
+                       RESULT_VARIABLE result
+                       OUTPUT_VARIABLE version
+                       ERROR_QUIET
+                       OUTPUT_STRIP_TRAILING_WHITESPACE)
+      if (result)
+        # interpreter is not usable
+        set (_${_PYTHON_PREFIX}_Interpreter_REASON_FAILURE "Cannot use the interpreter \"${_${_PYTHON_PREFIX}_EXECUTABLE}\"" PARENT_SCOPE)
         set_property (CACHE _${_PYTHON_PREFIX}_EXECUTABLE PROPERTY VALUE "${_PYTHON_PREFIX}_EXECUTABLE-NOTFOUND")
       else()
-        # check that version is OK
-        string(REGEX REPLACE "^([0-9]+)\\..*$" "\\1" major_version "${version}")
-        string(REGEX REPLACE "^([0-9]+)\\.?.*$" "\\1" expected_major_version "${expected_version}")
-        if (NOT major_version VERSION_EQUAL expected_major_version
-            OR NOT version VERSION_GREATER_EQUAL expected_version)
+        if (_PVI_EXACT AND NOT version VERSION_EQUAL expected_version)
+          # interpreter has wrong version
           set (_${_PYTHON_PREFIX}_Interpreter_REASON_FAILURE "Wrong version for the interpreter \"${_${_PYTHON_PREFIX}_EXECUTABLE}\"" PARENT_SCOPE)
           set_property (CACHE _${_PYTHON_PREFIX}_EXECUTABLE PROPERTY VALUE "${_PYTHON_PREFIX}_EXECUTABLE-NOTFOUND")
+        else()
+          # check that version is OK
+          string(REGEX REPLACE "^([0-9]+)\\.?.*$" "\\1" major_version "${version}")
+          string(REGEX REPLACE "^([0-9]+)\\.?.*$" "\\1" expected_major_version "${expected_version}")
+          if (NOT major_version VERSION_EQUAL expected_major_version
+              OR NOT version VERSION_GREATER_EQUAL expected_version)
+            set (_${_PYTHON_PREFIX}_Interpreter_REASON_FAILURE "Wrong version for the interpreter \"${_${_PYTHON_PREFIX}_EXECUTABLE}\"" PARENT_SCOPE)
+            set_property (CACHE _${_PYTHON_PREFIX}_EXECUTABLE PROPERTY VALUE "${_PYTHON_PREFIX}_EXECUTABLE-NOTFOUND")
+          endif()
         endif()
       endif()
-    endif()
-    if (NOT _${_PYTHON_PREFIX}_EXECUTABLE)
-      return()
+      if (NOT _${_PYTHON_PREFIX}_EXECUTABLE)
+        return()
+      endif()
     endif()
   else()
     if (NOT python_name STREQUAL "python${_${_PYTHON_PREFIX}_REQUIRED_VERSION_MAJOR}${CMAKE_EXECUTABLE_SUFFIX}")
@@ -613,7 +623,14 @@
     # check only major version
     file (WRITE "${working_dir}/version.py" "import sys; sys.stdout.write(str(sys.version_info[0]))")
   else()
-    file (WRITE "${working_dir}/version.py" "import sys; sys.stdout.write('.'.join([str(x) for x in sys.version_info[:2]]))\n")
+    # compute number of components for version
+    string (REGEX REPLACE "[^.]" "" dots "${expected_version}")
+    # add one dot because there is one dot less than there are components
+    string (LENGTH "${dots}." count)
+    if (count GREATER 3)
+      set (count 3)
+    endif()
+    file (WRITE "${working_dir}/version.py" "import sys; sys.stdout.write('.'.join([str(x) for x in sys.version_info[:${count}]]))\n")
   endif()
   execute_process (COMMAND "${_${_PYTHON_PREFIX}_COMPILER}" /target:exe /embed "${working_dir}/version.py"
                    WORKING_DIRECTORY "${working_dir}"
@@ -671,7 +688,9 @@
     set_property (CACHE _${_PYTHON_PREFIX}_LIBRARY_RELEASE PROPERTY VALUE "${_PYTHON_PREFIX}_LIBRARY_RELEASE-NOTFOUND")
   else()
     if (expected_version)
-      if ((_PVL_EXACT AND NOT lib_VERSION VERSION_EQUAL expected_version) OR (lib_VERSION VERSION_LESS expected_version))
+      # library have only major.minor information
+      string (REGEX MATCH "[0-9](\\.[0-9]+)?" version "${expected_version}")
+      if ((_PVL_EXACT AND NOT lib_VERSION VERSION_EQUAL version) OR (lib_VERSION VERSION_LESS version))
         # library has wrong version
         set (_${_PYTHON_PREFIX}_Development_REASON_FAILURE "Wrong version for the library \"${_${_PYTHON_PREFIX}_LIBRARY_RELEASE}\"" PARENT_SCOPE)
         set_property (CACHE _${_PYTHON_PREFIX}_LIBRARY_RELEASE PROPERTY VALUE "${_PYTHON_PREFIX}_LIBRARY_RELEASE-NOTFOUND")
@@ -791,21 +810,22 @@
 foreach (_${_PYTHON_PREFIX}_COMPONENT IN ITEMS Interpreter Compiler Development NumPy)
   set (${_PYTHON_PREFIX}_${_${_PYTHON_PREFIX}_COMPONENT}_FOUND FALSE)
 endforeach()
-unset (_${_PYTHON_PREFIX}_FIND_VERSIONS)
 
 # Set versions to search
 ## default: search any version
 set (_${_PYTHON_PREFIX}_FIND_VERSIONS ${_${_PYTHON_PREFIX}_VERSIONS})
+unset (_${_PYTHON_PREFIX}_FIND_VERSION_EXACT)
 
-if (${_PYTHON_PREFIX}_FIND_VERSION_COUNT GREATER 1)
+if (${_PYTHON_PREFIX}_FIND_VERSION_COUNT)
   if (${_PYTHON_PREFIX}_FIND_VERSION_EXACT)
-    set (_${_PYTHON_PREFIX}_FIND_VERSIONS ${${_PYTHON_PREFIX}_FIND_VERSION_MAJOR}.${${_PYTHON_PREFIX}_FIND_VERSION_MINOR})
+    set (_${_PYTHON_PREFIX}_FIND_VERSION_EXACT "EXACT")
+    set (_${_PYTHON_PREFIX}_FIND_VERSIONS "${${_PYTHON_PREFIX}_FIND_VERSION_MAJOR}.${${_PYTHON_PREFIX}_FIND_VERSION_MINOR}")
   else()
     unset (_${_PYTHON_PREFIX}_FIND_VERSIONS)
     # add all compatible versions
     foreach (_${_PYTHON_PREFIX}_VERSION IN LISTS _${_PYTHON_PREFIX}_VERSIONS)
-      if (_${_PYTHON_PREFIX}_VERSION VERSION_GREATER_EQUAL ${_PYTHON_PREFIX}_FIND_VERSION)
-        list (APPEND _${_PYTHON_PREFIX}_FIND_VERSIONS ${_${_PYTHON_PREFIX}_VERSION})
+      if (_${_PYTHON_PREFIX}_VERSION VERSION_GREATER_EQUAL "${${_PYTHON_PREFIX}_FIND_VERSION_MAJOR}.${${_PYTHON_PREFIX}_FIND_VERSION_MINOR}")
+        list (APPEND _${_PYTHON_PREFIX}_FIND_VERSIONS "${_${_PYTHON_PREFIX}_VERSION}")
       endif()
     endforeach()
   endif()
@@ -1033,7 +1053,7 @@
                         NO_SYSTEM_ENVIRONMENT_PATH
                         NO_CMAKE_SYSTEM_PATH)
 
-          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
           if (_${_PYTHON_PREFIX}_EXECUTABLE)
             break()
           endif()
@@ -1054,7 +1074,7 @@
                         NO_CMAKE_ENVIRONMENT_PATH
                         NO_SYSTEM_ENVIRONMENT_PATH
                         NO_CMAKE_SYSTEM_PATH)
-          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
           if (_${_PYTHON_PREFIX}_EXECUTABLE)
             break()
           endif()
@@ -1070,7 +1090,7 @@
                         PATH_SUFFIXES bin ${_${_PYTHON_PREFIX}_IRON_PYTHON_PATH_SUFFIXES}
                         NO_SYSTEM_ENVIRONMENT_PATH
                         NO_CMAKE_SYSTEM_PATH)
-          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
           if (_${_PYTHON_PREFIX}_EXECUTABLE)
             break()
           endif()
@@ -1085,7 +1105,7 @@
                       PATH_SUFFIXES bin ${_${_PYTHON_PREFIX}_IRON_PYTHON_PATH_SUFFIXES}
                       NO_SYSTEM_ENVIRONMENT_PATH
                       NO_CMAKE_SYSTEM_PATH)
-        _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+        _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
         if (_${_PYTHON_PREFIX}_EXECUTABLE)
           break()
         endif()
@@ -1095,7 +1115,7 @@
                             ${_${_PYTHON_PREFIX}_IRON_PYTHON_NAMES}
                       NAMES_PER_DIR
                       PATH_SUFFIXES bin ${_${_PYTHON_PREFIX}_IRON_PYTHON_PATH_SUFFIXES})
-        _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+        _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
         if (_${_PYTHON_PREFIX}_EXECUTABLE)
           break()
         endif()
@@ -1108,7 +1128,7 @@
                         PATHS ${_${_PYTHON_PREFIX}_FRAMEWORK_PATHS}
                         PATH_SUFFIXES bin
                         NO_DEFAULT_PATH)
-          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
           if (_${_PYTHON_PREFIX}_EXECUTABLE)
             break()
           endif()
@@ -1122,7 +1142,7 @@
                         PATHS ${_${_PYTHON_PREFIX}_REGISTRY_PATHS}
                         PATH_SUFFIXES bin ${_${_PYTHON_PREFIX}_IRON_PYTHON_PATH_SUFFIXES}
                         NO_DEFAULT_PATH)
-          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION})
+          _python_validate_interpreter (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
           if (_${_PYTHON_PREFIX}_EXECUTABLE)
             break()
           endif()
@@ -1472,7 +1492,7 @@
                         PATH_SUFFIXES ${_${_PYTHON_PREFIX}_IRON_PYTHON_PATH_SUFFIXES}
                         NO_SYSTEM_ENVIRONMENT_PATH
                         NO_CMAKE_SYSTEM_PATH)
-          _python_validate_compiler (${${_PYTHON_PREFIX}_FIND_VERSION})
+          _python_validate_compiler (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
           if (_${_PYTHON_PREFIX}_COMPILER)
             break()
           endif()
@@ -1484,7 +1504,7 @@
                       PATH_SUFFIXES ${_${_PYTHON_PREFIX}_IRON_PYTHON_PATH_SUFFIXES}
                       NO_SYSTEM_ENVIRONMENT_PATH
                       NO_CMAKE_SYSTEM_PATH)
-        _python_validate_compiler (${${_PYTHON_PREFIX}_FIND_VERSION})
+        _python_validate_compiler (${${_PYTHON_PREFIX}_FIND_VERSION} ${_${_PYTHON_PREFIX}_FIND_VERSION_EXACT})
         if (_${_PYTHON_PREFIX}_COMPILER)
           break()
         endif()
@@ -1615,6 +1635,10 @@
 
 
 # third step, search for the development artifacts
+if (${_PYTHON_PREFIX}_FIND_REQUIRED_Development)
+  list (APPEND _${_PYTHON_PREFIX}_REQUIRED_VARS ${_PYTHON_PREFIX}_LIBRARIES
+                                                ${_PYTHON_PREFIX}_INCLUDE_DIRS)
+endif()
 ## Development environment is not compatible with IronPython interpreter
 if ("Development" IN_LIST ${_PYTHON_PREFIX}_FIND_COMPONENTS
     AND NOT ${_PYTHON_PREFIX}_INTERPRETER_ID STREQUAL "IronPython")
@@ -1623,10 +1647,6 @@
                                               _${_PYTHON_PREFIX}_LIBRARY_DEBUG
                                               _${_PYTHON_PREFIX}_RUNTIME_LIBRARY_DEBUG
                                               _${_PYTHON_PREFIX}_INCLUDE_DIR)
-  if (${_PYTHON_PREFIX}_FIND_REQUIRED_Development)
-    list (APPEND _${_PYTHON_PREFIX}_REQUIRED_VARS ${_PYTHON_PREFIX}_LIBRARIES
-                                                  ${_PYTHON_PREFIX}_INCLUDE_DIRS)
-  endif()
 
   if (DEFINED _${_PYTHON_PREFIX}_LIBRARY_RELEASE OR DEFINED _${_PYTHON_PREFIX}_INCLUDE_DIR)
     # compute development signature and check validity of definition
@@ -2099,6 +2119,12 @@
                   NAMES_PER_DIR
                   HINTS "${_${_PYTHON_PREFIX}_PATH}" ${_${_PYTHON_PREFIX}_HINTS}
                   NO_DEFAULT_PATH)
+    # second try including CMAKE variables to catch-up non conventional layouts
+    find_library (_${_PYTHON_PREFIX}_LIBRARY_DEBUG
+                  NAMES ${_${_PYTHON_PREFIX}_LIB_NAMES_DEBUG}
+                  NAMES_PER_DIR
+                  NO_SYSTEM_ENVIRONMENT_PATH
+                  NO_CMAKE_SYSTEM_PATH)
   endif()
 
   # retrieve runtime libraries
@@ -2224,8 +2250,18 @@
     # retrieve version from header file
     _python_get_version (INCLUDE PREFIX _${_PYTHON_PREFIX}_INC_)
 
-    # update versioning
-    if (_${_PYTHON_PREFIX}_INC_VERSION VERSION_EQUAL _${_PYTHON_PREFIX}_VERSION)
+    if (_${_PYTHON_PREFIX}_LIBRARY_RELEASE)
+      if ("${_${_PYTHON_PREFIX}_INC_VERSION_MAJOR}.${_${_PYTHON_PREFIX}_INC_VERSION_MINOR}"
+          VERSION_EQUAL _${_PYTHON_PREFIX}_VERSION)
+        # update versioning
+        set (_${_PYTHON_PREFIX}_VERSION ${_${_PYTHON_PREFIX}_INC_VERSION})
+        set (_${_PYTHON_PREFIX}_VERSION_PATCH ${_${_PYTHON_PREFIX}_INC_VERSION_PATCH})
+      endif()
+    else()
+      # library is not defined, rely on header for version
+      set (_${_PYTHON_PREFIX}_VERSION ${_${_PYTHON_PREFIX}_INC_VERSION})
+      set (_${_PYTHON_PREFIX}_VERSION_MAJOR ${_${_PYTHON_PREFIX}_INC_VERSION_MAJOR})
+      set (_${_PYTHON_PREFIX}_VERSION_MINOR ${_${_PYTHON_PREFIX}_INC_VERSION_MINOR})
       set (_${_PYTHON_PREFIX}_VERSION_PATCH ${_${_PYTHON_PREFIX}_INC_VERSION_PATCH})
     endif()
   endif()
@@ -2309,11 +2345,11 @@
                             _${_PYTHON_PREFIX}_DEVELOPMENT_SIGNATURE)
 endif()
 
+if (${_PYTHON_PREFIX}_FIND_REQUIRED_NumPy)
+  list (APPEND _${_PYTHON_PREFIX}_REQUIRED_VARS ${_PYTHON_PREFIX}_NumPy_INCLUDE_DIRS)
+endif()
 if ("NumPy" IN_LIST ${_PYTHON_PREFIX}_FIND_COMPONENTS AND ${_PYTHON_PREFIX}_Interpreter_FOUND)
   list (APPEND _${_PYTHON_PREFIX}_CACHED_VARS _${_PYTHON_PREFIX}_NumPy_INCLUDE_DIR)
-  if (${_PYTHON_PREFIX}_FIND_REQUIRED_NumPy)
-    list (APPEND _${_PYTHON_PREFIX}_REQUIRED_VARS ${_PYTHON_PREFIX}_NumPy_INCLUDE_DIRS)
-  endif()
 
   if (DEFINED ${_PYTHON_PREFIX}_NumPy_INCLUDE_DIR
       AND IS_ABSOLUTE "${${_PYTHON_PREFIX}_NumPy_INCLUDE_DIR}")
diff --git a/Modules/Internal/CPack/CPackDeb.cmake b/Modules/Internal/CPack/CPackDeb.cmake
index 14bb104..db35e3a 100644
--- a/Modules/Internal/CPack/CPackDeb.cmake
+++ b/Modules/Internal/CPack/CPackDeb.cmake
@@ -83,6 +83,16 @@
   string(REPLACE "\n" ";" _lines "${_text}")
   list(POP_FRONT _lines _summary)
 
+  # If the description ends with a newline (e.g. typically if it was read
+  # from a file) the last line will be empty. We drop it here, otherwise
+  # it would be replaced by a `.` which would lead to the package violating
+  # the extended-description-contains-empty-paragraph debian policy
+  list(POP_BACK _lines _last_line)
+  string(STRIP "${_last_line}" _last_line_strip)
+  if(_last_line_strip)
+    list(APPEND _lines "${_last_line_strip}")
+  endif()
+
   # Check if reformatting required
   cpack_deb_check_description("${_summary}" "${_lines}" _result)
   if(_result)
diff --git a/Modules/Platform/Windows-MSVC.cmake b/Modules/Platform/Windows-MSVC.cmake
index e1d6733..fb23058 100644
--- a/Modules/Platform/Windows-MSVC.cmake
+++ b/Modules/Platform/Windows-MSVC.cmake
@@ -331,13 +331,11 @@
 
   set(CMAKE_PCH_EXTENSION .pch)
   set(CMAKE_LINK_PCH ON)
-  if(MSVC_VERSION GREATER_EQUAL 1910)
-    # VS 2017 or greater
-    if (NOT ${CMAKE_${lang}_COMPILER_ID} STREQUAL "Clang")
-        set(CMAKE_PCH_PROLOGUE "#pragma system_header")
-    else()
-        set(CMAKE_PCH_PROLOGUE "#pragma clang system_header")
-    endif()
+  if (CMAKE_${lang}_COMPILER_ID STREQUAL "Clang")
+    set(CMAKE_PCH_PROLOGUE "#pragma clang system_header")
+  elseif(MSVC_VERSION GREATER_EQUAL 1913)
+    # At least MSVC toolet 14.13 from VS 2017 15.6
+    set(CMAKE_PCH_PROLOGUE "#pragma system_header")
   endif()
   if (NOT ${CMAKE_${lang}_COMPILER_ID} STREQUAL "Clang")
     set(CMAKE_PCH_COPY_COMPILE_PDB ON)
diff --git a/Modules/Platform/Windows-NVIDIA-CUDA.cmake b/Modules/Platform/Windows-NVIDIA-CUDA.cmake
index f809094..98cd5ef 100644
--- a/Modules/Platform/Windows-NVIDIA-CUDA.cmake
+++ b/Modules/Platform/Windows-NVIDIA-CUDA.cmake
@@ -69,7 +69,6 @@
 endif()
 unset(_cmp0092)
 
-set(CMAKE_CUDA_RUNTIME_LIBRARY_DEFAULT "STATIC")
 set(CMAKE_CUDA_RUNTIME_LIBRARY_LINK_OPTIONS_STATIC  "cudadevrt;cudart_static")
 set(CMAKE_CUDA_RUNTIME_LIBRARY_LINK_OPTIONS_SHARED  "cudadevrt;cudart")
 set(CMAKE_CUDA_RUNTIME_LIBRARY_LINK_OPTIONS_NONE    "")
diff --git a/Source/CTest/cmCTestRunTest.cxx b/Source/CTest/cmCTestRunTest.cxx
index ec54960..58289ea 100644
--- a/Source/CTest/cmCTestRunTest.cxx
+++ b/Source/CTest/cmCTestRunTest.cxx
@@ -340,6 +340,11 @@
   if (this->NumberOfRunsLeft == 0) {
     return false;
   }
+  // If a test is marked as NOT_RUN it will not be repeated
+  // no matter the repeat settings, so just record it as-is.
+  if (this->TestResult.Status == cmCTestTestHandler::NOT_RUN) {
+    return false;
+  }
   // if number of runs left is not 0, and we are running until
   // we find a failed (or passed) test, then return true so the test can be
   // restarted
diff --git a/Source/Checks/cm_cxx_features.cmake b/Source/Checks/cm_cxx_features.cmake
index c16286c..2a67748 100644
--- a/Source/Checks/cm_cxx_features.cmake
+++ b/Source/Checks/cm_cxx_features.cmake
@@ -28,8 +28,12 @@
     string(REGEX REPLACE "[^\n]*warning:[^\n]*object file compiled with -mlong-branch which is no longer needed[^\n]*" "" check_output "${check_output}")
     # Filter out other warnings unrelated to feature checks.
     string(REGEX REPLACE "[^\n]*warning:[^\n]*sprintf\\(\\) is often misused, please use snprintf[^\n]*" "" check_output "${check_output}")
+    # Filter out libhugetlbfs warnings.
+    string(REGEX REPLACE "[^\n]*libhugetlbfs [^\n]*: WARNING[^\n]*" "" check_output "${check_output}")
     # Filter out xcodebuild warnings.
     string(REGEX REPLACE "[^\n]* xcodebuild\\[[0-9]*:[0-9]*\\] warning: [^\n]*" "" check_output "${check_output}")
+    # Filter out icpc warnings
+    string(REGEX REPLACE "[^\n]*icpc: command line warning #10121: overriding [^\n]*" "" check_output "${check_output}")
     # Filter out ld warnings.
     string(REGEX REPLACE "[^\n]*ld: warning: [^\n]*" "" check_output "${check_output}")
     # Filter out CUDA installation warnings.
diff --git a/Source/cmCoreTryCompile.cxx b/Source/cmCoreTryCompile.cxx
index da04396..73f099b 100644
--- a/Source/cmCoreTryCompile.cxx
+++ b/Source/cmCoreTryCompile.cxx
@@ -40,6 +40,8 @@
   "CMAKE_CXX_LINK_NO_PIE_SUPPORTED";
 static std::string const kCMAKE_CXX_LINK_PIE_SUPPORTED =
   "CMAKE_CXX_LINK_PIE_SUPPORTED";
+static std::string const kCMAKE_CUDA_RUNTIME_LIBRARY =
+  "CMAKE_CUDA_RUNTIME_LIBRARY";
 static std::string const kCMAKE_ENABLE_EXPORTS = "CMAKE_ENABLE_EXPORTS";
 static std::string const kCMAKE_LINK_SEARCH_END_STATIC =
   "CMAKE_LINK_SEARCH_END_STATIC";
@@ -719,6 +721,7 @@
       vars.insert(kCMAKE_C_COMPILER_TARGET);
       vars.insert(kCMAKE_CXX_COMPILER_EXTERNAL_TOOLCHAIN);
       vars.insert(kCMAKE_CXX_COMPILER_TARGET);
+      vars.insert(kCMAKE_CUDA_RUNTIME_LIBRARY);
       vars.insert(kCMAKE_ENABLE_EXPORTS);
       vars.insert(kCMAKE_LINK_SEARCH_END_STATIC);
       vars.insert(kCMAKE_LINK_SEARCH_START_STATIC);
diff --git a/Source/cmGeneratorTarget.cxx b/Source/cmGeneratorTarget.cxx
index ba2e314..5828651 100644
--- a/Source/cmGeneratorTarget.cxx
+++ b/Source/cmGeneratorTarget.cxx
@@ -647,6 +647,7 @@
 
 void cmGeneratorTarget::ClearSourcesCache()
 {
+  this->AllConfigSources.clear();
   this->KindedSourcesMap.clear();
   this->LinkImplementationLanguageIsContextDependent = true;
   this->Objects.clear();
diff --git a/Source/cmGlobalNinjaGenerator.h b/Source/cmGlobalNinjaGenerator.h
index b89fb8f..44e632f 100644
--- a/Source/cmGlobalNinjaGenerator.h
+++ b/Source/cmGlobalNinjaGenerator.h
@@ -415,6 +415,11 @@
 
   std::set<std::string> GetCrossConfigs(const std::string& config) const;
 
+  const std::set<std::string>& GetDefaultConfigs() const
+  {
+    return this->DefaultConfigs;
+  }
+
 protected:
   void Generate() override;
 
diff --git a/Source/cmGlobalVisualStudioGenerator.cxx b/Source/cmGlobalVisualStudioGenerator.cxx
index 1ec1559..4b4d72a 100644
--- a/Source/cmGlobalVisualStudioGenerator.cxx
+++ b/Source/cmGlobalVisualStudioGenerator.cxx
@@ -112,6 +112,7 @@
 {
   char utf8bom[] = { char(0xEF), char(0xBB), char(0xBF) };
   fout.write(utf8bom, 3);
+  fout << '\n';
 
   switch (this->Version) {
     case cmGlobalVisualStudioGenerator::VS9:
diff --git a/Source/cmLocalGenerator.cxx b/Source/cmLocalGenerator.cxx
index c2ec5f5..f592b7b 100644
--- a/Source/cmLocalGenerator.cxx
+++ b/Source/cmLocalGenerator.cxx
@@ -2604,9 +2604,11 @@
             std::string pchSourceObj =
               reuseTarget->GetPchFileObject(config, lang);
 
+            const std::string configUpper = cmSystemTools::UpperCase(config);
+
             // Link to the pch object file
             target->Target->AppendProperty(
-              "LINK_FLAGS",
+              cmStrCat("LINK_FLAGS_", configUpper),
               cmStrCat(" ", this->ConvertToOutputFormat(pchSourceObj, SHELL)),
               true);
           }
diff --git a/Source/cmLocalNinjaGenerator.cxx b/Source/cmLocalNinjaGenerator.cxx
index be1dd0d..56e9f81 100644
--- a/Source/cmLocalNinjaGenerator.cxx
+++ b/Source/cmLocalNinjaGenerator.cxx
@@ -97,6 +97,43 @@
       if (target->Target->IsPerConfig()) {
         for (auto const& config : this->GetConfigNames()) {
           tg->Generate(config);
+          if (target->GetType() == cmStateEnums::GLOBAL_TARGET &&
+              this->GetGlobalGenerator()->IsMultiConfig()) {
+            cmNinjaBuild phonyAlias("phony");
+            this->GetGlobalNinjaGenerator()->AppendTargetOutputs(
+              target.get(), phonyAlias.Outputs, "");
+            this->GetGlobalNinjaGenerator()->AppendTargetOutputs(
+              target.get(), phonyAlias.ExplicitDeps, config);
+            this->GetGlobalNinjaGenerator()->WriteBuild(
+              *this->GetGlobalNinjaGenerator()->GetConfigFileStream(config),
+              phonyAlias);
+          }
+        }
+        if (target->GetType() == cmStateEnums::GLOBAL_TARGET &&
+            this->GetGlobalGenerator()->IsMultiConfig()) {
+          if (!this->GetGlobalNinjaGenerator()->GetDefaultConfigs().empty()) {
+            cmNinjaBuild phonyAlias("phony");
+            this->GetGlobalNinjaGenerator()->AppendTargetOutputs(
+              target.get(), phonyAlias.Outputs, "");
+            for (auto const& config :
+                 this->GetGlobalNinjaGenerator()->GetDefaultConfigs()) {
+              this->GetGlobalNinjaGenerator()->AppendTargetOutputs(
+                target.get(), phonyAlias.ExplicitDeps, config);
+            }
+            this->GetGlobalNinjaGenerator()->WriteBuild(
+              *this->GetGlobalNinjaGenerator()->GetDefaultFileStream(),
+              phonyAlias);
+          }
+          cmNinjaBuild phonyAlias("phony");
+          this->GetGlobalNinjaGenerator()->AppendTargetOutputs(
+            target.get(), phonyAlias.Outputs, "all");
+          for (auto const& config : this->GetConfigNames()) {
+            this->GetGlobalNinjaGenerator()->AppendTargetOutputs(
+              target.get(), phonyAlias.ExplicitDeps, config);
+          }
+          this->GetGlobalNinjaGenerator()->WriteBuild(
+            *this->GetGlobalNinjaGenerator()->GetDefaultFileStream(),
+            phonyAlias);
         }
       } else {
         tg->Generate("");
diff --git a/Source/cmNinjaUtilityTargetGenerator.cxx b/Source/cmNinjaUtilityTargetGenerator.cxx
index a42d65d..6e39242 100644
--- a/Source/cmNinjaUtilityTargetGenerator.cxx
+++ b/Source/cmNinjaUtilityTargetGenerator.cxx
@@ -160,10 +160,5 @@
   // be per-directory and have one at the top-level anyway.
   if (genTarget->GetType() != cmStateEnums::GLOBAL_TARGET) {
     gg->AddTargetAlias(this->GetTargetName(), genTarget, config);
-  } else if (gg->IsMultiConfig() && genTarget->Target->IsPerConfig()) {
-    cmNinjaBuild phonyAlias("phony");
-    gg->AppendTargetOutputs(genTarget, phonyAlias.Outputs, "");
-    phonyAlias.ExplicitDeps = phonyBuild.Outputs;
-    gg->WriteBuild(this->GetImplFileStream(config), phonyAlias);
   }
 }
diff --git a/Source/cmVisualStudio10TargetGenerator.cxx b/Source/cmVisualStudio10TargetGenerator.cxx
index 8da113e..163ff19 100644
--- a/Source/cmVisualStudio10TargetGenerator.cxx
+++ b/Source/cmVisualStudio10TargetGenerator.cxx
@@ -2369,7 +2369,7 @@
         pchOptions =
           this->GeneratorTarget->GetPchUseCompileOptions(config, lang);
       }
-      customAndPchOptions += pchOptions;
+      customAndPchOptions = cmStrCat(customAndPchOptions, ';', pchOptions);
     }
 
     // if we have flags or defines for this config then
diff --git a/Tests/CMakeOnly/CheckLanguage/CMakeLists.txt b/Tests/CMakeOnly/CheckLanguage/CMakeLists.txt
index 90aa921..1570c37 100644
--- a/Tests/CMakeOnly/CheckLanguage/CMakeLists.txt
+++ b/Tests/CMakeOnly/CheckLanguage/CMakeLists.txt
@@ -18,16 +18,16 @@
   list(APPEND LANGUAGES OBJC OBJCXX)
 endif()
 
-foreach(lang ${LANGUAGES})
-  check_language(${lang})
-  if(NOT DEFINED CMAKE_${lang}_COMPILER)
-    message(FATAL_ERROR "check_language(${lang}) did not set result")
+foreach(test_lang ${LANGUAGES})
+  check_language(${test_lang})
+  if(NOT DEFINED CMAKE_${test_lang}_COMPILER)
+    message(FATAL_ERROR "check_language(${test_lang}) did not set result")
   endif()
-  if(DEFINED expect_${lang})
-    if(expect_${lang} AND NOT CMAKE_${lang}_COMPILER)
-      message(FATAL_ERROR "check_language(${lang}) should not fail!")
-    elseif(NOT expect_${lang} AND CMAKE_${lang}_COMPILER)
-      message(FATAL_ERROR "check_language(${lang}) should not succeed!")
+  if(DEFINED expect_${test_lang})
+    if(expect_${test_lang} AND NOT CMAKE_${test_lang}_COMPILER)
+      message(FATAL_ERROR "check_language(${test_lang}) should not fail!")
+    elseif(NOT expect_${test_lang} AND CMAKE_${test_lang}_COMPILER)
+      message(FATAL_ERROR "check_language(${test_lang}) should not succeed!")
     endif()
   endif()
 endforeach()
diff --git a/Tests/CPackComponentsDEB/MyLibCPackConfig-components-description1.cmake.in b/Tests/CPackComponentsDEB/MyLibCPackConfig-components-description1.cmake.in
index 67b108b..fb973ad 100644
--- a/Tests/CPackComponentsDEB/MyLibCPackConfig-components-description1.cmake.in
+++ b/Tests/CPackComponentsDEB/MyLibCPackConfig-components-description1.cmake.in
@@ -16,7 +16,7 @@
 
 # overriding previous descriptions
 set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "main description") # This become a summary line (the first one) of all descriptions
-set(CPACK_COMPONENT_APPLICATIONS_DESCRIPTION "applications_description")
+set(CPACK_COMPONENT_APPLICATIONS_DESCRIPTION "applications_description\n")
 set(CPACK_COMPONENT_HEADERS_DESCRIPTION "headers_description")
 # libraries does not have any description and should inherit from CPACK_PACKAGE_DESCRIPTION_SUMMARY
 # plus content of the `CPACK_PACKAGE_DESCRIPTION_FILE`.
diff --git a/Tests/CudaOnly/CMakeLists.txt b/Tests/CudaOnly/CMakeLists.txt
index cc1ee1a..3e3e44c 100644
--- a/Tests/CudaOnly/CMakeLists.txt
+++ b/Tests/CudaOnly/CMakeLists.txt
@@ -6,6 +6,7 @@
 ADD_TEST_MACRO(CudaOnly.ResolveDeviceSymbols CudaOnlyResolveDeviceSymbols)
 ADD_TEST_MACRO(CudaOnly.SeparateCompilation CudaOnlySeparateCompilation)
 ADD_TEST_MACRO(CudaOnly.SharedRuntimePlusToolkit CudaOnlySharedRuntimePlusToolkit)
+ADD_TEST_MACRO(CudaOnly.SharedRuntimeViaCUDAFlags CudaOnlySharedRuntimeViaCUDAFlags)
 ADD_TEST_MACRO(CudaOnly.Standard98 CudaOnlyStandard98)
 ADD_TEST_MACRO(CudaOnly.Toolkit CudaOnlyToolkit)
 ADD_TEST_MACRO(CudaOnly.WithDefs CudaOnlyWithDefs)
diff --git a/Tests/CudaOnly/SharedRuntimeViaCUDAFlags/CMakeLists.txt b/Tests/CudaOnly/SharedRuntimeViaCUDAFlags/CMakeLists.txt
new file mode 100644
index 0000000..24ff478
--- /dev/null
+++ b/Tests/CudaOnly/SharedRuntimeViaCUDAFlags/CMakeLists.txt
@@ -0,0 +1,15 @@
+cmake_minimum_required(VERSION 3.17)
+project(SharedRuntimeViaCUDAFlags NONE)
+
+set(CMAKE_CUDA_FLAGS "")
+string(APPEND CMAKE_CUDA_FLAGS "-cudart shared")
+
+enable_language(CUDA)
+
+add_executable(CudaOnlySharedRuntimeViaCUDAFlags main.cu)
+
+if(UNIX)
+  # Help the shared cuda runtime find libcudart as it is not located
+  # in a default system searched location
+  set_property(TARGET CudaOnlySharedRuntimeViaCUDAFlags PROPERTY BUILD_RPATH ${CMAKE_CUDA_IMPLICIT_LINK_DIRECTORIES})
+endif()
diff --git a/Tests/CudaOnly/SharedRuntimeViaCUDAFlags/main.cu b/Tests/CudaOnly/SharedRuntimeViaCUDAFlags/main.cu
new file mode 100644
index 0000000..766b775
--- /dev/null
+++ b/Tests/CudaOnly/SharedRuntimeViaCUDAFlags/main.cu
@@ -0,0 +1,5 @@
+
+int main()
+{
+  return 0;
+}
diff --git a/Tests/FindPython/CMakeLists.txt b/Tests/FindPython/CMakeLists.txt
index 5c954e2..9b89832 100644
--- a/Tests/FindPython/CMakeLists.txt
+++ b/Tests/FindPython/CMakeLists.txt
@@ -128,6 +128,99 @@
     --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
     )
 
+  add_test(NAME FindPython.Python2.ExactVersion.LOCATION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python2.ExactVersion.LOCATION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_MAJOR_VERSION=2
+                                     -DPython_REQUESTED_VERSION=2.1.2
+                                     -DPython2_FIND_STRATEGY=LOCATION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python2.ExactVersion.VERSION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python2.ExactVersion.VERSION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_MAJOR_VERSION=2
+                                     -DPython_REQUESTED_VERSION=2.1.2
+                                     -DPython2_FIND_STRATEGY=VERSION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python3.ExactVersion.LOCATION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python3.ExactVersion.LOCATION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_MAJOR_VERSION=3
+                                     -DPython_REQUESTED_VERSION=3.1.2
+                                     -DPython3_FIND_STRATEGY=LOCATION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python3.ExactVersion.VERSION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python3.ExactVersion.VERSION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_MAJOR_VERSION=3
+                                     -DPython_REQUESTED_VERSION=3.1.2
+                                     -DPython3_FIND_STRATEGY=VERSION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python.V2.ExactVersion.LOCATION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python.V2.ExactVersion.LOCATION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_REQUESTED_VERSION=2.1.2
+                                     -DPython_FIND_STRATEGY=LOCATION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python.V2.ExactVersion.VERSION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python.V2.ExactVersion.VERSION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_REQUESTED_VERSION=2.1.2
+                                     -DPython_FIND_STRATEGY=VERSION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python.V3.ExactVersion.LOCATION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python.V3.ExactVersion.LOCATION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_REQUESTED_VERSION=3.1.2
+                                     -DPython_FIND_STRATEGY=LOCATION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+  add_test(NAME FindPython.Python.V3.ExactVersion.VERSION COMMAND
+    ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
+    --build-and-test
+    "${CMake_SOURCE_DIR}/Tests/FindPython/ExactVersion"
+    "${CMake_BINARY_DIR}/Tests/FindPython/Python.V3.ExactVersion.VERSION"
+    ${build_generator_args}
+    --build-project TestExactVersion
+    --build-options ${build_options} -DPython_REQUESTED_VERSION=3.1.2
+                                     -DPython_FIND_STRATEGY=VERSION
+    --test-command ${CMAKE_CTEST_COMMAND} -V -C $<CONFIGURATION>
+    )
+
   add_test(NAME FindPython.MultiplePackages COMMAND
     ${CMAKE_CTEST_COMMAND} -C $<CONFIGURATION>
     --build-and-test
diff --git a/Tests/FindPython/ExactVersion/CMakeLists.txt b/Tests/FindPython/ExactVersion/CMakeLists.txt
new file mode 100644
index 0000000..e09f73a
--- /dev/null
+++ b/Tests/FindPython/ExactVersion/CMakeLists.txt
@@ -0,0 +1,56 @@
+cmake_minimum_required(VERSION 3.1)
+
+project(TestExactVersion C)
+
+find_package(Python${Python_MAJOR_VERSION} ${Python_REQUESTED_VERSION} COMPONENTS Interpreter Development)
+if (NOT Python${Python_MAJOR_VERSION}_FOUND)
+  message (FATAL_ERROR "Fail to found Python ${Python_REQUESTED_VERSION}")
+endif()
+if (NOT Python${Python_MAJOR_VERSION}_Interpreter_FOUND)
+  message (FATAL_ERROR "Fail to found Python ${Python_REQUESTED_VERSION} Interpreter")
+endif()
+if (NOT Python${Python_MAJOR_VERSION}_Development_FOUND)
+  message (FATAL_ERROR "Fail to found Python ${Python_REQUESTED_VERSION} Development")
+endif()
+
+if(NOT TARGET Python${Python_MAJOR_VERSION}::Interpreter)
+  message(SEND_ERROR "Python${Python_MAJOR_VERSION}::Interpreter not found")
+endif()
+
+if(NOT TARGET Python${Python_MAJOR_VERSION}::Python)
+  message(SEND_ERROR "Python${Python_MAJOR_VERSION}::Python not found")
+endif()
+if(NOT TARGET Python${Python_MAJOR_VERSION}::Module)
+  message(SEND_ERROR "Python${Python_MAJOR_VERSION}::Module not found")
+endif()
+
+
+# reset artifacts and second search with exact version already founded
+unset (Python${Python_MAJOR_VERSION}_EXECUTABLE)
+unset (_Python${Python_MAJOR_VERSION}_EXECUTABLE CACHE)
+
+unset (_Python${Python_MAJOR_VERSION}_LIBRARY_RELEASE CACHE)
+unset (_Python${Python_MAJOR_VERSION}_INCLUDE_DIR CACHE)
+
+set (Python_REQUESTED_VERSION ${Python${Python_MAJOR_VERSION}_VERSION})
+find_package(Python${Python_MAJOR_VERSION} ${Python_REQUESTED_VERSION} EXACT COMPONENTS Interpreter Development)
+if (NOT Python${Python_MAJOR_VERSION}_FOUND)
+  message (FATAL_ERROR "Fail to found Python ${Python_REQUESTED_VERSION}")
+endif()
+if (NOT Python${Python_MAJOR_VERSION}_Interpreter_FOUND)
+  message (FATAL_ERROR "Fail to found Python ${Python_REQUESTED_VERSION} Interpreter")
+endif()
+if (NOT Python${Python_MAJOR_VERSION}_Development_FOUND)
+  message (FATAL_ERROR "Fail to found Python ${Python_REQUESTED_VERSION} Development")
+endif()
+
+if(NOT TARGET Python${Python_MAJOR_VERSION}::Interpreter)
+  message(SEND_ERROR "Python${Python_MAJOR_VERSION}::Interpreter not found")
+endif()
+
+if(NOT TARGET Python${Python_MAJOR_VERSION}::Python)
+  message(SEND_ERROR "Python${Python_MAJOR_VERSION}::Python not found")
+endif()
+if(NOT TARGET Python${Python_MAJOR_VERSION}::Module)
+  message(SEND_ERROR "Python${Python_MAJOR_VERSION}::Module not found")
+endif()
diff --git a/Tests/RunCMake/BuildDepends/ExternalProject/CMakeLists.txt b/Tests/RunCMake/BuildDepends/ExternalProject/CMakeLists.txt
new file mode 100644
index 0000000..57a0f6e
--- /dev/null
+++ b/Tests/RunCMake/BuildDepends/ExternalProject/CMakeLists.txt
@@ -0,0 +1,14 @@
+cmake_minimum_required(VERSION 3.12)
+project(External NONE)
+
+if (DEFINED cache_arg)
+  message("configured with: ${cache_arg}")
+else ()
+  message("cache_arg is undefined")
+endif ()
+
+if (DEFINED second_cache_arg)
+  message("configured again with: ${second_cache_arg}")
+else ()
+  message("second_cache_arg is undefined")
+endif ()
diff --git a/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs-build1-stdout.txt b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs-build1-stdout.txt
new file mode 100644
index 0000000..fea7fd9
--- /dev/null
+++ b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs-build1-stdout.txt
@@ -0,0 +1,2 @@
+.*configured with: first
+.*second_cache_arg is undefined
diff --git a/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs-build2-stdout.txt b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs-build2-stdout.txt
new file mode 100644
index 0000000..e19e743
--- /dev/null
+++ b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs-build2-stdout.txt
@@ -0,0 +1,2 @@
+.*configured with: first
+.*configured again with: second
diff --git a/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.cmake b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.cmake
new file mode 100644
index 0000000..fe69426
--- /dev/null
+++ b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.cmake
@@ -0,0 +1,19 @@
+include("${CMAKE_CURRENT_BINARY_DIR}/data.cmake")
+
+include(ExternalProject)
+ExternalProject_add(external
+  SOURCE_DIR "${CMAKE_CURRENT_LIST_DIR}/ExternalProject"
+  CMAKE_CACHE_ARGS
+    ${cache_args}
+  BUILD_COMMAND ""
+  INSTALL_COMMAND "")
+
+set(cache_args_path "<TMP_DIR>/external-cache-$<CONFIG>.cmake")
+set(cmake_cache_path "<BINARY_DIR>/CMakeCache.txt")
+_ep_replace_location_tags(external cache_args_path cmake_cache_path)
+
+file(GENERATE OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/check-$<LOWER_CASE:$<CONFIG>>.cmake" CONTENT "
+set(check_pairs
+  \"${cmake_cache_path}|${cache_args_path}\"
+)
+")
diff --git a/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.step1.cmake b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.step1.cmake
new file mode 100644
index 0000000..57c7ab7
--- /dev/null
+++ b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.step1.cmake
@@ -0,0 +1,3 @@
+file(WRITE "${RunCMake_TEST_BINARY_DIR}/data.cmake"
+  "set(cache_args -Dcache_arg:STRING=first)
+")
diff --git a/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.step2.cmake b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.step2.cmake
new file mode 100644
index 0000000..cbb79e1
--- /dev/null
+++ b/Tests/RunCMake/BuildDepends/ExternalProjectCacheArgs.step2.cmake
@@ -0,0 +1,3 @@
+file(WRITE "${RunCMake_TEST_BINARY_DIR}/data.cmake"
+  "set(cache_args -Dsecond_cache_arg:STRING=second)
+")
diff --git a/Tests/RunCMake/BuildDepends/RunCMakeTest.cmake b/Tests/RunCMake/BuildDepends/RunCMakeTest.cmake
index 14ae243..e4d7177 100644
--- a/Tests/RunCMake/BuildDepends/RunCMakeTest.cmake
+++ b/Tests/RunCMake/BuildDepends/RunCMakeTest.cmake
@@ -46,6 +46,11 @@
 run_BuildDepends(Custom-Symbolic-and-Byproduct)
 run_BuildDepends(Custom-Always)
 
+set(RunCMake_TEST_OUTPUT_MERGE_save "${RunCMake_TEST_OUTPUT_MERGE}")
+set(RunCMake_TEST_OUTPUT_MERGE 1)
+run_BuildDepends(ExternalProjectCacheArgs)
+set(RunCMake_TEST_OUTPUT_MERGE "${RunCMake_TEST_OUTPUT_MERGE_save}")
+
 # Test header dependencies with a build tree underneath a source tree.
 set(RunCMake_TEST_SOURCE_DIR "${RunCMake_BINARY_DIR}/BuildUnderSource")
 set(RunCMake_TEST_BINARY_DIR "${RunCMake_BINARY_DIR}/BuildUnderSource/build")
diff --git a/Tests/RunCMake/CPack/tests/DEB_DESCRIPTION/VerifyResult.cmake b/Tests/RunCMake/CPack/tests/DEB_DESCRIPTION/VerifyResult.cmake
index bfe2059..70ad48b 100644
--- a/Tests/RunCMake/CPack/tests/DEB_DESCRIPTION/VerifyResult.cmake
+++ b/Tests/RunCMake/CPack/tests/DEB_DESCRIPTION/VerifyResult.cmake
@@ -46,17 +46,7 @@
   .
   See also: https://www.debian.org/doc/debian-policy/ch-controlfields.html#description]])
 
-# ATTENTION The code in `cmCPackGenerator.cxx` to read `CPACK_PACKAGE_DESCRIPTION_FILE`
-# has a BUG: it appends the `\n` character to every line of the
-# input, even if there was no EOL (e.g. at the last line of the file).
-# That is WHY for this sub-test the one more pre-formatted "empty"
-# line required!
-# NOTE For component based installers content of the file gonna read by
-# `CPackDeb` module and the `file(READ...)` command so no the mentioned
-# workaround required!
-if(RunCMake_SUBTEST_SUFFIX STREQUAL "CPACK_PACKAGE_DESCRIPTION_FILE" AND PACKAGING_TYPE STREQUAL "MONOLITHIC")
-  string(APPEND _expected_description "\n  ." )
-elseif(RunCMake_SUBTEST_SUFFIX STREQUAL "CPACK_NO_PACKAGE_DESCRIPTION")
+if(RunCMake_SUBTEST_SUFFIX STREQUAL "CPACK_NO_PACKAGE_DESCRIPTION")
   set(_expected_description [[ Description: This is the summary line]])
 elseif(RunCMake_SUBTEST_SUFFIX STREQUAL "CPACK_COMPONENT_COMP_DESCRIPTION")
   set(_expected_description [[ Description: One line description]])
diff --git a/Tests/RunCMake/FindPkgConfig/FindPkgConfig_IMPORTED_TARGET.cmake b/Tests/RunCMake/FindPkgConfig/FindPkgConfig_IMPORTED_TARGET.cmake
index 62bb5de..d697fc6 100644
--- a/Tests/RunCMake/FindPkgConfig/FindPkgConfig_IMPORTED_TARGET.cmake
+++ b/Tests/RunCMake/FindPkgConfig/FindPkgConfig_IMPORTED_TARGET.cmake
@@ -99,6 +99,7 @@
 Description: Dummy package for FindPkgConfig IMPORTED_TARGET INTERFACE_LINK_OPTIONS test
 Version: 1.2.3
 Libs: -e dummy_main
+Cflags: -I/special -isystem /other -isystem/more -DA-isystem/foo
 ")
 
 set(expected_link_options -e dummy_main)
@@ -109,7 +110,26 @@
 get_target_property(link_options PkgConfig::FakeLinkOptionsPackage INTERFACE_LINK_OPTIONS)
 if (NOT link_options STREQUAL expected_link_options)
   message(FATAL_ERROR
-    "Additional link options not present in INTERFACE_LINK_OPTIONS property"
+    "Additional link options not present in INTERFACE_LINK_OPTIONS property\n"
     "expected: \"${expected_link_options}\", but got \"${link_options}\""
   )
 endif()
+
+get_target_property(inc_dirs PkgConfig::FakeLinkOptionsPackage INTERFACE_INCLUDE_DIRECTORIES)
+set(expected_inc_dirs "/special" "/other" "/more")
+
+if (NOT inc_dirs STREQUAL expected_inc_dirs)
+  message(FATAL_ERROR
+    "Additional include directories not correctly present in INTERFACE_INCLUDE_DIRECTORIES property\n"
+    "expected: \"${expected_inc_dirs}\", got \"${inc_dirs}\""
+  )
+endif ()
+
+get_target_property(c_opts PkgConfig::FakeLinkOptionsPackage INTERFACE_COMPILE_OPTIONS)
+set(expected_c_opts "-DA-isystem/foo") # this is an invalid option, but a good testcase
+if (NOT c_opts STREQUAL expected_c_opts)
+    message(FATAL_ERROR
+      "Additional compile options not present in INTERFACE_COMPILE_OPTIONS property\n"
+      "expected: \"${expected_c_opts}\", got \"${c_opts}\""
+    )
+endif ()
diff --git a/Tests/RunCMake/NinjaMultiConfig/Install-all-install-ninja-check.cmake b/Tests/RunCMake/NinjaMultiConfig/Install-all-install-ninja-check.cmake
new file mode 100644
index 0000000..c588aac
--- /dev/null
+++ b/Tests/RunCMake/NinjaMultiConfig/Install-all-install-ninja-check.cmake
@@ -0,0 +1,39 @@
+check_files("${RunCMake_TEST_BINARY_DIR}"
+  INCLUDE
+    ${TARGET_FILE_exe_Debug}
+    ${TARGET_OBJECT_FILES_exe_Debug}
+
+    ${TARGET_FILE_mylib_Release}
+    ${TARGET_LINKER_FILE_mylib_Debug}
+    ${TARGET_OBJECT_FILES_mylib_Debug}
+
+    ${RunCMake_TEST_BINARY_DIR}/install/bin/Debug/${TARGET_FILE_NAME_exe_Debug}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Debug/${TARGET_FILE_NAME_mylib_Debug}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Debug/${TARGET_LINKER_FILE_NAME_mylib_Debug}
+
+    ${TARGET_FILE_exe_Release}
+    ${TARGET_OBJECT_FILES_exe_Release}
+
+    ${TARGET_FILE_mylib_Release}
+    ${TARGET_LINKER_FILE_mylib_Release}
+    ${TARGET_OBJECT_FILES_mylib_Release}
+
+    ${RunCMake_TEST_BINARY_DIR}/install/bin/Release/${TARGET_FILE_NAME_exe_Release}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Release/${TARGET_FILE_NAME_mylib_Release}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Release/${TARGET_LINKER_FILE_NAME_mylib_Release}
+
+    ${TARGET_FILE_exe_RelWithDebInfo}
+    ${TARGET_OBJECT_FILES_exe_RelWithDebInfo}
+
+    ${TARGET_FILE_mylib_RelWithDebInfo}
+    ${TARGET_LINKER_FILE_mylib_RelWithDebInfo}
+    ${TARGET_OBJECT_FILES_mylib_RelWithDebInfo}
+
+    ${RunCMake_TEST_BINARY_DIR}/install/bin/RelWithDebInfo/${TARGET_FILE_NAME_exe_RelWithDebInfo}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/RelWithDebInfo/${TARGET_FILE_NAME_mylib_RelWithDebInfo}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/RelWithDebInfo/${TARGET_LINKER_FILE_NAME_mylib_RelWithDebInfo}
+
+  EXCLUDE
+    ${TARGET_OBJECT_FILES_exe_MinSizeRel}
+    ${TARGET_OBJECT_FILES_mylib_MinSizeRel}
+  )
diff --git a/Tests/RunCMake/NinjaMultiConfig/Install-default-install-ninja-check.cmake b/Tests/RunCMake/NinjaMultiConfig/Install-default-install-ninja-check.cmake
new file mode 100644
index 0000000..bc15a25
--- /dev/null
+++ b/Tests/RunCMake/NinjaMultiConfig/Install-default-install-ninja-check.cmake
@@ -0,0 +1,31 @@
+check_files("${RunCMake_TEST_BINARY_DIR}"
+  INCLUDE
+    ${TARGET_FILE_exe_Debug}
+    ${TARGET_OBJECT_FILES_exe_Debug}
+
+    ${TARGET_FILE_mylib_Release}
+    ${TARGET_LINKER_FILE_mylib_Debug}
+    ${TARGET_OBJECT_FILES_mylib_Debug}
+
+    ${RunCMake_TEST_BINARY_DIR}/install/bin/Debug/${TARGET_FILE_NAME_exe_Debug}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Debug/${TARGET_FILE_NAME_mylib_Debug}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Debug/${TARGET_LINKER_FILE_NAME_mylib_Debug}
+
+    ${TARGET_FILE_exe_Release}
+    ${TARGET_OBJECT_FILES_exe_Release}
+
+    ${TARGET_FILE_mylib_Release}
+    ${TARGET_LINKER_FILE_mylib_Release}
+    ${TARGET_OBJECT_FILES_mylib_Release}
+
+    ${RunCMake_TEST_BINARY_DIR}/install/bin/Release/${TARGET_FILE_NAME_exe_Release}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Release/${TARGET_FILE_NAME_mylib_Release}
+    ${RunCMake_TEST_BINARY_DIR}/install/lib/Release/${TARGET_LINKER_FILE_NAME_mylib_Release}
+
+  EXCLUDE
+    ${TARGET_OBJECT_FILES_exe_MinSizeRel}
+    ${TARGET_OBJECT_FILES_mylib_MinSizeRel}
+
+    ${TARGET_OBJECT_FILES_exe_RelWithDebInfo}
+    ${TARGET_OBJECT_FILES_mylib_RelWithDebInfo}
+  )
diff --git a/Tests/RunCMake/NinjaMultiConfig/RunCMakeTest.cmake b/Tests/RunCMake/NinjaMultiConfig/RunCMakeTest.cmake
index 6472f46..d4a08a9 100644
--- a/Tests/RunCMake/NinjaMultiConfig/RunCMakeTest.cmake
+++ b/Tests/RunCMake/NinjaMultiConfig/RunCMakeTest.cmake
@@ -263,12 +263,16 @@
 run_ninja(AdditionalCleanFiles all-clean build-Debug.ninja clean:all)
 
 set(RunCMake_TEST_BINARY_DIR ${RunCMake_BINARY_DIR}/Install-build)
-set(RunCMake_TEST_OPTIONS "-DCMAKE_INSTALL_PREFIX=${RunCMake_TEST_BINARY_DIR}/install;-DCMAKE_CROSS_CONFIGS=all")
+set(RunCMake_TEST_OPTIONS "-DCMAKE_INSTALL_PREFIX=${RunCMake_TEST_BINARY_DIR}/install;-DCMAKE_CROSS_CONFIGS=all;-DCMAKE_DEFAULT_CONFIGS=Debug\\;Release")
 run_cmake_configure(Install)
 unset(RunCMake_TEST_OPTIONS)
 include(${RunCMake_TEST_BINARY_DIR}/target_files.cmake)
 run_cmake_build(Install release-install Release install)
 run_ninja(Install debug-in-release-graph-install build-Release.ninja install:Debug)
+file(REMOVE_RECURSE "${RunCMake_TEST_BINARY_DIR}/install")
+run_ninja(Install default-install build.ninja install)
+file(REMOVE_RECURSE "${RunCMake_TEST_BINARY_DIR}/install")
+run_ninja(Install all-install build.ninja install:all)
 
 # FIXME Get this working
 #set(RunCMake_TEST_BINARY_DIR ${RunCMake_BINARY_DIR}/AutoMocExecutable-build)
diff --git a/Tests/RunCMake/PrecompileHeaders/PchInterface.cmake b/Tests/RunCMake/PrecompileHeaders/PchInterface.cmake
index a1e0792..aab20d8 100644
--- a/Tests/RunCMake/PrecompileHeaders/PchInterface.cmake
+++ b/Tests/RunCMake/PrecompileHeaders/PchInterface.cmake
@@ -9,6 +9,9 @@
   <stdio.h>
   \"string.h\"
 )
+if(CMAKE_C_COMPILER_ID STREQUAL "MSVC")
+  set_property(SOURCE foo.c APPEND PROPERTY COMPILE_OPTIONS "-WX-")
+endif()
 
 add_library(bar INTERFACE)
 target_include_directories(bar INTERFACE include)
diff --git a/Tests/RunCMake/ctest_test/RunCMakeTest.cmake b/Tests/RunCMake/ctest_test/RunCMakeTest.cmake
index 84d1d66..d0a6e5f 100644
--- a/Tests/RunCMake/ctest_test/RunCMakeTest.cmake
+++ b/Tests/RunCMake/ctest_test/RunCMakeTest.cmake
@@ -81,17 +81,43 @@
 run_ctest_test(TestRepeatBad1 REPEAT UNKNOWN:3)
 run_ctest_test(TestRepeatBad2 REPEAT UNTIL_FAIL:-1)
 
-function(run_TestRepeat case)
-  set(CASE_CTEST_TEST_ARGS EXCLUDE RunCMakeVersion ${ARGN})
-  string(CONCAT CASE_CMAKELISTS_SUFFIX_CODE [[
+function(run_TestRepeat case return_value )
+  set(CASE_CTEST_TEST_ARGS RETURN_VALUE result EXCLUDE RunCMakeVersion ${ARGN})
+  string(CONCAT suffix_code [[
 add_test(NAME testRepeat
   COMMAND ${CMAKE_COMMAND} -D COUNT_FILE=${CMAKE_CURRENT_BINARY_DIR}/count.cmake
                            -P "]] "${RunCMake_SOURCE_DIR}/TestRepeat${case}" [[.cmake")
 set_property(TEST testRepeat PROPERTY TIMEOUT 5)
   ]])
+  string(APPEND CASE_CMAKELISTS_SUFFIX_CODE "${suffix_code}")
 
   run_ctest(TestRepeat${case})
+
+  #write to end of the test file logic to Verify we get the expected
+  #return code
+  string(REPLACE "RETURN_VALUE:" "" return_value "${return_value}" )
+  file(APPEND "${RunCMake_BINARY_DIR}/TestRepeat${case}/test.cmake"
+"
+
+  set(expected_result ${return_value})
+  message(STATUS \${result})
+  if(NOT result EQUAL expected_result)
+    message(FATAL_ERROR \"expected a return value of: \${expected_result},
+                         instead got: \${result}\")
+  endif()
+"
+  )
 endfunction()
-run_TestRepeat(UntilFail REPEAT UNTIL_FAIL:3)
-run_TestRepeat(UntilPass REPEAT UNTIL_PASS:3)
-run_TestRepeat(AfterTimeout REPEAT AFTER_TIMEOUT:3)
+
+run_TestRepeat(UntilFail RETURN_VALUE:1 REPEAT UNTIL_FAIL:3)
+run_TestRepeat(UntilPass RETURN_VALUE:0 REPEAT UNTIL_PASS:3)
+run_TestRepeat(AfterTimeout RETURN_VALUE:0 REPEAT AFTER_TIMEOUT:3)
+
+# test repeat and not run tests interact correctly
+set(CASE_CMAKELISTS_SUFFIX_CODE [[
+add_test(NAME testNotRun
+  COMMAND ${CMAKE_COMMAND}/doesnt_exist)
+  set_property(TEST testNotRun PROPERTY TIMEOUT 5)
+  ]])
+run_TestRepeat(NotRun RETURN_VALUE:1 REPEAT UNTIL_PASS:3)
+unset(CASE_CMAKELISTS_SUFFIX_CODE)
diff --git a/Tests/RunCMake/ctest_test/TestRepeatNotRun-result.txt b/Tests/RunCMake/ctest_test/TestRepeatNotRun-result.txt
new file mode 100644
index 0000000..b57e2de
--- /dev/null
+++ b/Tests/RunCMake/ctest_test/TestRepeatNotRun-result.txt
@@ -0,0 +1 @@
+(-1|255)
diff --git a/Tests/RunCMake/ctest_test/TestRepeatNotRun-stderr.txt b/Tests/RunCMake/ctest_test/TestRepeatNotRun-stderr.txt
new file mode 100644
index 0000000..a69932d
--- /dev/null
+++ b/Tests/RunCMake/ctest_test/TestRepeatNotRun-stderr.txt
@@ -0,0 +1 @@
+.*Unable to find executable.*
diff --git a/Tests/RunCMake/ctest_test/TestRepeatNotRun-stdout.txt b/Tests/RunCMake/ctest_test/TestRepeatNotRun-stdout.txt
new file mode 100644
index 0000000..72c98bc
--- /dev/null
+++ b/Tests/RunCMake/ctest_test/TestRepeatNotRun-stdout.txt
@@ -0,0 +1,5 @@
+.*
+50% tests passed, 1 tests failed out of 2
+.*
+The following tests FAILED:
+.*testNotRun.*Not Run.*
diff --git a/Tests/RunCMake/ctest_test/TestRepeatNotRun.cmake b/Tests/RunCMake/ctest_test/TestRepeatNotRun.cmake
new file mode 100644
index 0000000..abde4f0
--- /dev/null
+++ b/Tests/RunCMake/ctest_test/TestRepeatNotRun.cmake
@@ -0,0 +1,10 @@
+include("${COUNT_FILE}" OPTIONAL)
+if(NOT COUNT)
+  set(COUNT 0)
+endif()
+math(EXPR COUNT "${COUNT} + 1")
+file(WRITE "${COUNT_FILE}" "set(COUNT ${COUNT})\n")
+if(NOT COUNT EQUAL 2)
+  message("this test times out except on the 2nd run")
+  execute_process(COMMAND ${CMAKE_COMMAND} -E sleep 10)
+endif()
diff --git a/bootstrap b/bootstrap
index d529f3b..03d9ef0 100755
--- a/bootstrap
+++ b/bootstrap
@@ -38,7 +38,7 @@
 
 cmake_toupper()
 {
-    echo "$1" | tr '[:lower:]' '[:upper:]'
+    echo "$1" | tr '[a-z]' '[A-Z]'
 }
 
 # Detect system and directory information.