소스 검색

CMakePresets.json: Rework how --preset argument is handled

If a path argument with no -S or -B leads to a cache directory,
use that directory as the binary directory. Otherwise, use the
binary directory from the preset.

Fixes: #21311
Kyle Edwards 5 년 전
부모
커밋
b7d7eca66d

+ 2 - 3
Help/manual/cmake-gui.1.rst

@@ -11,7 +11,6 @@ Synopsis
  cmake-gui [<options>]
  cmake-gui [<options>] {<path-to-source> | <path-to-existing-build>}
  cmake-gui [<options>] -S <path-to-source> -B <path-to-build>
- cmake-gui [<options>] -S <path-to-source> --preset=<preset-name>
 
 Description
 ===========
@@ -38,8 +37,8 @@ Options
  If the directory doesn't already exist CMake will make it.
 
 ``--preset=<preset-name>``
- Name of the preset to use from the project's ``CMakePresets.json`` file, if it
- has one.
+ Name of the preset to use from the project's
+ :manual:`presets <cmake-presets(7)>` files, if it has them.
 
 .. include:: OPTIONS_HELP.txt
 

+ 15 - 17
Help/manual/cmake.1.rst

@@ -12,7 +12,6 @@ Synopsis
   cmake [<options>] <path-to-source>
   cmake [<options>] <path-to-existing-build>
   cmake [<options>] -S <path-to-source> -B <path-to-build>
-  cmake [<options>] -S <path-to-source> --preset=<preset-name>
 
  `Build a Project`_
   cmake --build <dir> [<options>] [-- <build-tool-options>]
@@ -149,22 +148,6 @@ source and build trees and generate a buildsystem:
 
     $ cmake -S src -B build
 
-``cmake [<options>] -S <path-to-source> --preset=<preset-name>``
-  Uses ``<path-to-source>`` as the source tree and reads a
-  :manual:`preset <cmake-presets(7)>` from
-  ``<path-to-source>/CMakePresets.json`` and
-  ``<path-to-source>/CMakeUserPresets.json``. The preset specifies the
-  generator and the build directory, and optionally a list of variables and
-  other arguments to pass to CMake. The :manual:`CMake GUI <cmake-gui(1)>` can
-  also recognize ``CMakePresets.json`` and ``CMakeUserPresets.json`` files. For
-  full details on these files, see :manual:`cmake-presets(7)`.
-
-  The presets are read before all other command line options. The options
-  specified by the preset (variables, generator, etc.) can all be overridden by
-  manually specifying them on the command line. For example, if the preset sets
-  a variable called ``MYVAR`` to ``1``, but the user sets it to ``2`` with a
-  ``-D`` argument, the value ``2`` is preferred.
-
 In all cases the ``<options>`` may be zero or more of the `Options`_ below.
 
 After generating a buildsystem one may use the corresponding native
@@ -394,6 +377,21 @@ Options
  about:tracing tab of Google Chrome or using a plugin for a tool like Trace
  Compass.
 
+``--preset=<preset>``
+ Reads a :manual:`preset <cmake-presets(7)>` from
+ ``<path-to-source>/CMakePresets.json`` and
+ ``<path-to-source>/CMakeUserPresets.json``. The preset specifies the
+ generator and the build directory, and optionally a list of variables and
+ other arguments to pass to CMake. The :manual:`CMake GUI <cmake-gui(1)>` can
+ also recognize ``CMakePresets.json`` and ``CMakeUserPresets.json`` files. For
+ full details on these files, see :manual:`cmake-presets(7)`.
+
+ The presets are read before all other command line options. The options
+ specified by the preset (variables, generator, etc.) can all be overridden by
+ manually specifying them on the command line. For example, if the preset sets
+ a variable called ``MYVAR`` to ``1``, but the user sets it to ``2`` with a
+ ``-D`` argument, the value ``2`` is preferred.
+
 .. _`Build Tool Mode`:
 
 Build a Project

+ 1 - 2
Source/QtDialog/CMakeSetup.cxx

@@ -32,8 +32,7 @@ static const char* cmDocumentationUsage[][2] = {
     "  cmake-gui [options]\n"
     "  cmake-gui [options] <path-to-source>\n"
     "  cmake-gui [options] <path-to-existing-build>\n"
-    "  cmake-gui [options] -S <path-to-source> -B <path-to-build>\n"
-    "  cmake-gui [options] -S <path-to-source> --preset=<preset-name>\n" },
+    "  cmake-gui [options] -S <path-to-source> -B <path-to-build>\n" },
   { nullptr, nullptr }
 };
 

+ 1 - 0
Source/cmCacheManager.cxx

@@ -162,6 +162,7 @@ bool cmCacheManager::LoadCache(const std::string& path, bool internal,
       cmSystemTools::Error(message.str());
     }
   }
+  this->CacheLoaded = true;
   return true;
 }
 

+ 4 - 0
Source/cmCacheManager.h

@@ -66,6 +66,9 @@ public:
   //! Print the cache to a stream
   void PrintCache(std::ostream&) const;
 
+  //! Get whether or not cache is loaded
+  bool IsCacheLoaded() const { return this->CacheLoaded; }
+
   //! Get a value from the cache given a key
   cmProp GetInitializedCacheValue(const std::string& key) const;
 
@@ -204,6 +207,7 @@ private:
                             const CacheEntry& e, cmMessenger* messenger) const;
 
   std::map<std::string, CacheEntry> Cache;
+  bool CacheLoaded = false;
 
   // Cache version info
   unsigned int CacheMajorVersion = 0;

+ 5 - 0
Source/cmState.cxx

@@ -135,6 +135,11 @@ bool cmState::DeleteCache(const std::string& path)
   return this->CacheManager->DeleteCache(path);
 }
 
+bool cmState::IsCacheLoaded() const
+{
+  return this->CacheManager->IsCacheLoaded();
+}
+
 std::vector<std::string> cmState::GetCacheEntryKeys() const
 {
   return this->CacheManager->GetCacheEntryKeys();

+ 2 - 0
Source/cmState.h

@@ -87,6 +87,8 @@ public:
 
   bool DeleteCache(const std::string& path);
 
+  bool IsCacheLoaded() const;
+
   std::vector<std::string> GetCacheEntryKeys() const;
   cmProp GetCacheEntryValue(std::string const& key) const;
   std::string GetSafeCacheEntryValue(std::string const& key) const;

+ 3 - 1
Source/cmake.cxx

@@ -727,6 +727,7 @@ void cmake::SetArgs(const std::vector<std::string>& args)
 {
   bool haveToolset = false;
   bool havePlatform = false;
+  bool haveBArg = false;
 #if !defined(CMAKE_BOOTSTRAP)
   std::string profilingFormat;
   std::string profilingOutput;
@@ -775,6 +776,7 @@ void cmake::SetArgs(const std::vector<std::string>& args)
       path = cmSystemTools::CollapseFullPath(path);
       cmSystemTools::ConvertToUnixSlashes(path);
       this->SetHomeOutputDirectory(path);
+      haveBArg = true;
     } else if ((i < args.size() - 2) &&
                cmHasLiteralPrefix(arg, "--check-build-system")) {
       this->CheckBuildSystemArgument = args[++i];
@@ -1057,7 +1059,7 @@ void cmake::SetArgs(const std::vector<std::string>& args)
       return;
     }
 
-    if (!haveBinaryDir) {
+    if (!this->State->IsCacheLoaded() && !haveBArg) {
       this->SetHomeOutputDirectory(expandedPreset->BinaryDir);
     }
     if (!this->GlobalGenerator) {

+ 1 - 2
Source/cmakemain.cxx

@@ -49,8 +49,7 @@ const char* cmDocumentationUsage[][2] = {
   { nullptr,
     "  cmake [options] <path-to-source>\n"
     "  cmake [options] <path-to-existing-build>\n"
-    "  cmake [options] -S <path-to-source> -B <path-to-build>\n"
-    "  cmake [options] -S <path-to-source> --preset=<preset-name>" },
+    "  cmake [options] -S <path-to-source> -B <path-to-build>" },
   { nullptr,
     "Specify a source directory to (re-)generate a build system for "
     "it in the current working directory.  Specify an existing build "

+ 10 - 0
Tests/RunCMake/CMakePresets/CMakePresets.json.in

@@ -159,6 +159,16 @@
       "generator": "@RunCMake_GENERATOR@",
       "binaryDir": "${sourceDir}/build"
     },
+    {
+      "name": "GoodNoSCachePrep",
+      "generator": "@RunCMake_GENERATOR@",
+      "binaryDir": "${sourceParentDir}/GoodNoSCachePrep-build"
+    },
+    {
+      "name": "GoodNoSCache",
+      "generator": "@RunCMake_GENERATOR@",
+      "binaryDir": "${sourceDir}/build"
+    },
     {
       "name": "GoodInheritanceParentBase",
       "hidden": true,

+ 1 - 2
Tests/RunCMake/CMakePresets/GoodNoS.cmake

@@ -1,4 +1,3 @@
 include(${CMAKE_CURRENT_LIST_DIR}/TestVariable.cmake)
 
-get_filename_component(_parent "${CMAKE_SOURCE_DIR}" DIRECTORY)
-test_variable(CMAKE_BINARY_DIR "" "${_parent}/GoodNoS-build")
+test_variable(CMAKE_BINARY_DIR "" "${CMAKE_SOURCE_DIR}/build")

+ 4 - 0
Tests/RunCMake/CMakePresets/GoodNoSCache.cmake

@@ -0,0 +1,4 @@
+include(${CMAKE_CURRENT_LIST_DIR}/TestVariable.cmake)
+
+get_filename_component(_parent "${CMAKE_SOURCE_DIR}" DIRECTORY)
+test_variable(CMAKE_BINARY_DIR "" "${_parent}/GoodNoSCachePrep-build")

+ 4 - 0
Tests/RunCMake/CMakePresets/GoodNoSCachePrep.cmake

@@ -0,0 +1,4 @@
+include(${CMAKE_CURRENT_LIST_DIR}/TestVariable.cmake)
+
+get_filename_component(_parent "${CMAKE_SOURCE_DIR}" DIRECTORY)
+test_variable(CMAKE_BINARY_DIR "" "${_parent}/GoodNoSCachePrep-build")

+ 12 - 4
Tests/RunCMake/CMakePresets/RunCMakeTest.cmake

@@ -28,8 +28,8 @@ endfunction()
 function(run_cmake_presets name)
   set(RunCMake_TEST_SOURCE_DIR "${RunCMake_BINARY_DIR}/${name}")
   set(_source_arg "${RunCMake_TEST_SOURCE_DIR}")
-  if(CMakePresets_RELATIVE_SOURCE)
-    set(_source_arg "../${name}")
+  if(CMakePresets_SOURCE_ARG)
+    set(_source_arg "${CMakePresets_SOURCE_ARG}")
   endif()
   file(REMOVE_RECURSE "${RunCMake_TEST_SOURCE_DIR}")
   file(MAKE_DIRECTORY "${RunCMake_TEST_SOURCE_DIR}")
@@ -154,9 +154,9 @@ unset(ENV{TEST_ENV_REF_PENV})
 run_cmake_presets(GoodNoArgs)
 file(REMOVE_RECURSE ${RunCMake_BINARY_DIR}/GoodBinaryUp-build)
 run_cmake_presets(GoodBinaryUp)
-set(CMakePresets_RELATIVE_SOURCE TRUE)
+set(CMakePresets_SOURCE_ARG "../GoodBinaryRelative")
 run_cmake_presets(GoodBinaryRelative)
-unset(CMakePresets_RELATIVE_SOURCE)
+unset(CMakePresets_SOURCE_ARG)
 run_cmake_presets(GoodSpaces "--preset=Good Spaces")
 if(WIN32)
   run_cmake_presets(GoodWindowsBackslash)
@@ -170,6 +170,14 @@ run_cmake_presets(GoodGeneratorCmdLine -G ${RunCMake_GENERATOR})
 run_cmake_presets(InvalidGeneratorCmdLine -G "Invalid Generator")
 set(CMakePresets_NO_S_ARG TRUE)
 run_cmake_presets(GoodNoS)
+set(RunCMake_TEST_BINARY_DIR "${RunCMake_BINARY_DIR}/GoodNoSCachePrep-build")
+run_cmake_presets(GoodNoSCachePrep)
+set(CMakePresets_SOURCE_ARG ".")
+set(RunCMake_TEST_NO_CLEAN 1)
+run_cmake_presets(GoodNoSCache)
+unset(RunCMake_TEST_NO_CLEAN)
+unset(CMakePresets_SOURCE_ARG)
+unset(RunCMake_TEST_BINARY_DIR)
 unset(CMakePresets_NO_S_ARG)
 run_cmake_presets(GoodInheritanceParent)
 run_cmake_presets(GoodInheritanceChild)

+ 0 - 1
Tests/RunCMake/CommandLine/NoArgs-stdout.txt

@@ -3,7 +3,6 @@
   cmake \[options\] <path-to-source>
   cmake \[options\] <path-to-existing-build>
   cmake \[options\] -S <path-to-source> -B <path-to-build>
-  cmake \[options\] -S <path-to-source> --preset=<preset-name>
 
 Specify a source directory to \(re-\)generate a build system for it in the
 current working directory.  Specify an existing build directory to