1
0
Эх сурвалжийг харах

Merge topic 'feat/cmake-project-module'

b37b912e8f CMAKE_PROJECT_INCLUDE: Allow to run module files

Acked-by: Kitware Robot <[email protected]>
Acked-by: buildbot <[email protected]>
Merge-request: !8894
Brad King 2 жил өмнө
parent
commit
78bfcf47c8

+ 3 - 1
Help/release/dev/project-include-multiple.rst

@@ -6,4 +6,6 @@ project-include-multiple
   :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE`, and
   :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE_BEFORE` variables learned
   to support a :ref:`semicolon-separated list <CMake Language Lists>` of
-  CMake language files to be included sequentially.
+  CMake language files to be included sequentially. These variables can also
+  reference module names to be found in :variable:`CMAKE_MODULE_PATH` or
+  builtin to CMake.

+ 2 - 1
Help/variable/CMAKE_PROJECT_INCLUDE.rst

@@ -11,7 +11,8 @@ for a more detailed discussion of files potentially included during a
 
 .. versionadded:: 3.29
   This variable can be a :ref:`semicolon-separated list <CMake Language Lists>`
-  of CMake language files to be included sequentially.
+  of CMake language files to be included sequentially. It can also now refer to
+  module names to be found in :variable:`CMAKE_MODULE_PATH` or builtin to CMake.
 
 See also the :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE`,
 :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE_BEFORE`,

+ 2 - 1
Help/variable/CMAKE_PROJECT_INCLUDE_BEFORE.rst

@@ -11,7 +11,8 @@ for a more detailed discussion of files potentially included during a
 
 .. versionadded:: 3.29
   This variable can be a :ref:`semicolon-separated list <CMake Language Lists>`
-  of CMake language files to be included sequentially.
+  of CMake language files to be included sequentially. It can also now refer to
+  module names to be found in :variable:`CMAKE_MODULE_PATH` or builtin to CMake.
 
 See also the :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE`,
 :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE_BEFORE`,

+ 2 - 1
Help/variable/CMAKE_PROJECT_PROJECT-NAME_INCLUDE.rst

@@ -9,7 +9,8 @@ discussion of files potentially included during a :command:`project` call.
 
 .. versionadded:: 3.29
   This variable can be a :ref:`semicolon-separated list <CMake Language Lists>`
-  of CMake language files to be included sequentially.
+  of CMake language files to be included sequentially. It can also now refer to
+  module names to be found in :variable:`CMAKE_MODULE_PATH` or builtin to CMake.
 
 See also the :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE_BEFORE`,
 :variable:`CMAKE_PROJECT_INCLUDE`, :variable:`CMAKE_PROJECT_INCLUDE_BEFORE`,

+ 2 - 1
Help/variable/CMAKE_PROJECT_PROJECT-NAME_INCLUDE_BEFORE.rst

@@ -11,7 +11,8 @@ discussion of files potentially included during a :command:`project` call.
 
 .. versionadded:: 3.29
   This variable can be a :ref:`semicolon-separated list <CMake Language Lists>`
-  of CMake language files to be included sequentially.
+  of CMake language files to be included sequentially. It can also now refer to
+  module names to be found in :variable:`CMAKE_MODULE_PATH` or builtin to CMake.
 
 See also the :variable:`CMAKE_PROJECT_<PROJECT-NAME>_INCLUDE`,
 :variable:`CMAKE_PROJECT_INCLUDE`, :variable:`CMAKE_PROJECT_INCLUDE_BEFORE`,

+ 4 - 0
Help/variable/CMAKE_PROJECT_TOP_LEVEL_INCLUDES.rst

@@ -12,6 +12,10 @@ including things like :variable:`CMAKE_<LANG>_COMPILER`, might not be set.
 See :ref:`Code Injection` for a more detailed discussion of files potentially
 included during a :command:`project` call.
 
+.. versionadded:: 3.29
+  This variable can also now refer to module names to be found in
+  :variable:`CMAKE_MODULE_PATH` or builtin to CMake.
+
 This variable is intended for specifying files that perform one-time setup
 for the build. It provides an injection point for things like configuring
 package managers, adding logic the user shares between projects (e.g. defining

+ 16 - 1
Source/cmGlobalGenerator.cxx

@@ -694,7 +694,22 @@ void cmGlobalGenerator::EnableLanguage(
     std::string includes =
       mf->GetSafeDefinition("CMAKE_PROJECT_TOP_LEVEL_INCLUDES");
     cmList includesList{ includes };
-    for (std::string const& setupFile : includesList) {
+    for (std::string setupFile : includesList) {
+      // Any relative path without a .cmake extension is checked for valid
+      // cmake modules. This logic should be consistent with CMake's include()
+      // command. Otherwise default to checking relative path w.r.t. source
+      // directory
+      if (!cmSystemTools::FileIsFullPath(setupFile) &&
+          !cmHasLiteralSuffix(setupFile, ".cmake")) {
+        std::string mfile = mf->GetModulesFile(cmStrCat(setupFile, ".cmake"));
+        if (mfile.empty()) {
+          cmSystemTools::Error(cmStrCat(
+            "CMAKE_PROJECT_TOP_LEVEL_INCLUDES module:\n  ", setupFile));
+          mf->GetState()->SetInTopLevelIncludes(false);
+          return;
+        }
+        setupFile = mfile;
+      }
       std::string absSetupFile = cmSystemTools::CollapseFullPath(
         setupFile, mf->GetCurrentSourceDirectory());
       if (!cmSystemTools::FileExists(absSetupFile)) {

+ 15 - 1
Source/cmProjectCommand.cxx

@@ -375,7 +375,21 @@ static bool IncludeByVariable(cmExecutionStatus& status,
   cmList includeFiles{ *include };
 
   bool failed = false;
-  for (auto const& filePath : includeFiles) {
+  for (auto filePath : includeFiles) {
+    // Any relative path without a .cmake extension is checked for valid cmake
+    // modules. This logic should be consistent with CMake's include() command.
+    // Otherwise default to checking relative path w.r.t. source directory
+    if (!cmSystemTools::FileIsFullPath(filePath) &&
+        !cmHasLiteralSuffix(filePath, ".cmake")) {
+      std::string mfile = mf.GetModulesFile(cmStrCat(filePath, ".cmake"));
+      if (mfile.empty()) {
+        status.SetError(
+          cmStrCat("could not find requested module:\n  ", filePath));
+        failed = true;
+        continue;
+      }
+      filePath = mfile;
+    }
     std::string includeFile = cmSystemTools::CollapseFullPath(
       filePath, mf.GetCurrentSourceDirectory());
     if (!cmSystemTools::FileExists(includeFile)) {

+ 28 - 0
Tests/RunCMake/project/CodeInjection/initial_cache_3.cmake

@@ -0,0 +1,28 @@
+set(CMAKE_MODULE_PATH "${CMAKE_CURRENT_LIST_DIR}" CACHE STRING "")
+set(CMAKE_TOOLCHAIN_FILE
+  "${CMAKE_CURRENT_LIST_DIR}/passthrough_toolchain_file.cmake" CACHE FILEPATH "")
+set(CMAKE_PROJECT_INCLUDE
+  "${CMAKE_CURRENT_LIST_DIR}/cmake_project_includes_1.cmake"
+  "cmake_project_includes_2"
+  CACHE STRING ""
+)
+set(CMAKE_PROJECT_INCLUDE_BEFORE
+  "${CMAKE_CURRENT_LIST_DIR}/cmake_project_includes_before_1.cmake"
+  "cmake_project_includes_before_2"
+  CACHE STRING ""
+)
+set(CMAKE_PROJECT_SubProj_INCLUDE
+  "${CMAKE_CURRENT_LIST_DIR}/cmake_project_subproj_includes_1.cmake"
+  "cmake_project_subproj_includes_2"
+  CACHE STRING ""
+)
+set(CMAKE_PROJECT_SubProj_INCLUDE_BEFORE
+  "${CMAKE_CURRENT_LIST_DIR}/cmake_project_subproj_includes_before_1.cmake"
+  "cmake_project_subproj_includes_before_2"
+  CACHE STRING ""
+)
+set(CMAKE_PROJECT_TOP_LEVEL_INCLUDES
+  "${CMAKE_CURRENT_LIST_DIR}/cmake_project_top_level_includes_1.cmake"
+  "cmake_project_top_level_includes_2"
+  CACHE STRING ""
+)

+ 16 - 0
Tests/RunCMake/project/CodeInjection3-stdout.txt

@@ -0,0 +1,16 @@
+(-- )?Included CMAKE_PROJECT_INCLUDE_BEFORE first file
+(-- )?Included CMAKE_PROJECT_INCLUDE_BEFORE second file
+(-- )?Included CMAKE_TOOLCHAIN_FILE
+.*Included CMAKE_PROJECT_TOP_LEVEL_INCLUDES first file
+(-- )?Included CMAKE_PROJECT_TOP_LEVEL_INCLUDES second file
+(-- )?Included CMAKE_PROJECT_INCLUDE first file
+(-- )?Included CMAKE_PROJECT_INCLUDE second file
+(-- )?Calling sub-project
+(-- )?Included CMAKE_PROJECT_INCLUDE_BEFORE first file
+(-- )?Included CMAKE_PROJECT_INCLUDE_BEFORE second file
+(-- )?Included CMAKE_PROJECT_SubProj_INCLUDE_BEFORE first file
+(-- )?Included CMAKE_PROJECT_SubProj_INCLUDE_BEFORE second file
+(-- )?Included CMAKE_PROJECT_INCLUDE first file
+(-- )?Included CMAKE_PROJECT_INCLUDE second file
+(-- )?Included CMAKE_PROJECT_SubProj_INCLUDE first file
+(-- )?Included CMAKE_PROJECT_SubProj_INCLUDE second file

+ 1 - 0
Tests/RunCMake/project/CodeInjection3.cmake

@@ -0,0 +1 @@
+add_subdirectory(CodeInjection)

+ 4 - 0
Tests/RunCMake/project/RunCMakeTest.cmake

@@ -12,6 +12,10 @@ run_cmake_with_options(CodeInjection1
 run_cmake_with_options(CodeInjection2
         -C "${CMAKE_CURRENT_LIST_DIR}/CodeInjection/initial_cache_2.cmake"
 )
+# This checks that module names are also allowed.
+run_cmake_with_options(CodeInjection3
+        -C "${CMAKE_CURRENT_LIST_DIR}/CodeInjection/initial_cache_3.cmake"
+)
 
 if(CMake_TEST_RESOURCES)
   run_cmake(ExplicitRC)