cmake: Add `cmake -E capabilities` mode
Add `cmake -E capabilities` to report on generators, cmake version and possibly other static capabilities of cmake. Closes: #15462
This commit is contained in:
parent
1d408dc10f
commit
49ad7f9af8
|
@ -180,6 +180,43 @@ CMake provides builtin command-line tools through the signature::
|
||||||
Run ``cmake -E`` or ``cmake -E help`` for a summary of commands.
|
Run ``cmake -E`` or ``cmake -E help`` for a summary of commands.
|
||||||
Available commands are:
|
Available commands are:
|
||||||
|
|
||||||
|
``capabilities``
|
||||||
|
Report cmake capabilities in JSON format. The output is a JSON object
|
||||||
|
with the following keys:
|
||||||
|
|
||||||
|
``version``
|
||||||
|
A JSON object with version information. Keys are:
|
||||||
|
|
||||||
|
``string``
|
||||||
|
The full version string as displayed by cmake ``--version``.
|
||||||
|
``major``
|
||||||
|
The major version number in integer form.
|
||||||
|
``minor``
|
||||||
|
The minor version number in integer form.
|
||||||
|
``patch``
|
||||||
|
The patch level in integer form.
|
||||||
|
``suffix``
|
||||||
|
The cmake version suffix string.
|
||||||
|
``isDirty``
|
||||||
|
A bool that is set if the cmake build is from a dirty tree.
|
||||||
|
|
||||||
|
``generators``
|
||||||
|
A list available generators. Each generator is a JSON object with the
|
||||||
|
following keys:
|
||||||
|
|
||||||
|
``name``
|
||||||
|
A string containing the name of the generator.
|
||||||
|
``toolsetSupport``
|
||||||
|
``true`` if the generator supports toolsets and ``false`` otherwise.
|
||||||
|
``platformSupport``
|
||||||
|
``true`` if the generator supports platforms and ``false`` otherwise.
|
||||||
|
``extraGenerators``
|
||||||
|
A list of strings with all the extra generators compatible with
|
||||||
|
the generator.
|
||||||
|
|
||||||
|
``serverMode``
|
||||||
|
``true`` if cmake supports server-mode and ``false`` otherwise.
|
||||||
|
|
||||||
``chdir <dir> <cmd> [<arg>...]``
|
``chdir <dir> <cmd> [<arg>...]``
|
||||||
Change the current working directory and run a command.
|
Change the current working directory and run a command.
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,6 @@
|
||||||
|
cmake-capabilities
|
||||||
|
------------------
|
||||||
|
|
||||||
|
* :manual:`cmake(1)` gained a ``-E capabilities`` option to provide a
|
||||||
|
machine-readable (JSON) description of the capabilities of the
|
||||||
|
cmake tool (available generators, etc.).
|
|
@ -23,11 +23,15 @@
|
||||||
#include "cmState.h"
|
#include "cmState.h"
|
||||||
#include "cmTest.h"
|
#include "cmTest.h"
|
||||||
#include "cmUtils.hxx"
|
#include "cmUtils.hxx"
|
||||||
|
#include "cmVersionMacros.h"
|
||||||
|
|
||||||
#if defined(CMAKE_BUILD_WITH_CMAKE)
|
#if defined(CMAKE_BUILD_WITH_CMAKE)
|
||||||
#include "cmGraphVizWriter.h"
|
#include "cmGraphVizWriter.h"
|
||||||
#include "cmVariableWatch.h"
|
#include "cmVariableWatch.h"
|
||||||
#include <cmsys/SystemInformation.hxx>
|
#include <cmsys/SystemInformation.hxx>
|
||||||
|
|
||||||
|
#include "cm_jsoncpp_value.h"
|
||||||
|
#include "cm_jsoncpp_writer.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#include <cmsys/FStream.hxx>
|
#include <cmsys/FStream.hxx>
|
||||||
|
@ -110,6 +114,18 @@
|
||||||
|
|
||||||
#include <list>
|
#include <list>
|
||||||
|
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
#if defined(CMAKE_BUILD_WITH_CMAKE)
|
||||||
|
#ifdef CMake_HAVE_CXX_UNORDERED_MAP
|
||||||
|
typedef std::unordered_map<std::string, Json::Value> JsonValueMapType;
|
||||||
|
#else
|
||||||
|
typedef cmsys::hash_map<std::string, Json::Value> JsonValueMapType;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
|
|
||||||
|
} // namespace
|
||||||
|
|
||||||
static bool cmakeCheckStampFile(const char* stampName);
|
static bool cmakeCheckStampFile(const char* stampName);
|
||||||
static bool cmakeCheckStampList(const char* stampName);
|
static bool cmakeCheckStampList(const char* stampName);
|
||||||
|
|
||||||
|
@ -201,6 +217,68 @@ cmake::~cmake()
|
||||||
delete this->FileComparison;
|
delete this->FileComparison;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::string cmake::ReportCapabilities() const
|
||||||
|
{
|
||||||
|
std::string result;
|
||||||
|
#if defined(CMAKE_BUILD_WITH_CMAKE)
|
||||||
|
Json::Value obj = Json::objectValue;
|
||||||
|
// Version information:
|
||||||
|
Json::Value version = Json::objectValue;
|
||||||
|
version["string"] = CMake_VERSION;
|
||||||
|
version["major"] = CMake_VERSION_MAJOR;
|
||||||
|
version["minor"] = CMake_VERSION_MINOR;
|
||||||
|
version["suffix"] = CMake_VERSION_SUFFIX;
|
||||||
|
version["isDirty"] = (CMake_VERSION_IS_DIRTY == 1);
|
||||||
|
version["patch"] = CMake_VERSION_PATCH;
|
||||||
|
|
||||||
|
obj["version"] = version;
|
||||||
|
|
||||||
|
// Generators:
|
||||||
|
std::vector<cmake::GeneratorInfo> generatorInfoList;
|
||||||
|
this->GetRegisteredGenerators(generatorInfoList);
|
||||||
|
|
||||||
|
JsonValueMapType generatorMap;
|
||||||
|
for (std::vector<cmake::GeneratorInfo>::const_iterator i =
|
||||||
|
generatorInfoList.begin();
|
||||||
|
i != generatorInfoList.end(); ++i) {
|
||||||
|
if (i->isAlias) { // skip aliases, they are there for compatibility reasons
|
||||||
|
// only
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (i->extraName.empty()) {
|
||||||
|
Json::Value gen = Json::objectValue;
|
||||||
|
gen["name"] = i->name;
|
||||||
|
gen["toolsetSupport"] = i->supportsToolset;
|
||||||
|
gen["platformSupport"] = i->supportsPlatform;
|
||||||
|
gen["extraGenerators"] = Json::arrayValue;
|
||||||
|
generatorMap[i->name] = gen;
|
||||||
|
} else {
|
||||||
|
Json::Value& gen = generatorMap[i->baseName];
|
||||||
|
gen["extraGenerators"].append(i->extraName);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Json::Value generators = Json::arrayValue;
|
||||||
|
for (JsonValueMapType::const_iterator i = generatorMap.begin();
|
||||||
|
i != generatorMap.end(); ++i) {
|
||||||
|
generators.append(i->second);
|
||||||
|
}
|
||||||
|
obj["generators"] = generators;
|
||||||
|
|
||||||
|
#if defined(HAVE_SERVER_MODE) && HAVE_SERVER_MODE
|
||||||
|
obj["serverMode"] = true;
|
||||||
|
#else
|
||||||
|
obj["serverMode"] = false;
|
||||||
|
#endif
|
||||||
|
Json::FastWriter writer;
|
||||||
|
result = writer.write(obj);
|
||||||
|
#else
|
||||||
|
result = "Not supported";
|
||||||
|
#endif
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
void cmake::CleanupCommandsAndMacros()
|
void cmake::CleanupCommandsAndMacros()
|
||||||
{
|
{
|
||||||
this->CurrentSnapshot = this->State->Reset();
|
this->CurrentSnapshot = this->State->Reset();
|
||||||
|
|
|
@ -117,6 +117,8 @@ public:
|
||||||
/// Destructor
|
/// Destructor
|
||||||
~cmake();
|
~cmake();
|
||||||
|
|
||||||
|
std::string ReportCapabilities() const;
|
||||||
|
|
||||||
static const char* GetCMakeFilesDirectory() { return "/CMakeFiles"; }
|
static const char* GetCMakeFilesDirectory() { return "/CMakeFiles"; }
|
||||||
static const char* GetCMakeFilesDirectoryPostSlash()
|
static const char* GetCMakeFilesDirectoryPostSlash()
|
||||||
{
|
{
|
||||||
|
|
|
@ -60,6 +60,8 @@ void CMakeCommandUsage(const char* program)
|
||||||
errorStream
|
errorStream
|
||||||
<< "Usage: " << program << " -E <command> [arguments...]\n"
|
<< "Usage: " << program << " -E <command> [arguments...]\n"
|
||||||
<< "Available commands: \n"
|
<< "Available commands: \n"
|
||||||
|
<< " capabilities - Report capabilities built into cmake "
|
||||||
|
"in JSON format\n"
|
||||||
<< " chdir dir cmd [args...] - run command in a given directory\n"
|
<< " chdir dir cmd [args...] - run command in a given directory\n"
|
||||||
<< " compare_files file1 file2 - check if file1 is same as file2\n"
|
<< " compare_files file1 file2 - check if file1 is same as file2\n"
|
||||||
<< " copy <file>... destination - copy files to destination "
|
<< " copy <file>... destination - copy files to destination "
|
||||||
|
@ -510,6 +512,16 @@ int cmcmd::ExecuteCMakeCommand(std::vector<std::string>& args)
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
// capabilities
|
||||||
|
else if (args[1] == "capabilities") {
|
||||||
|
if (args.size() > 2) {
|
||||||
|
std::cerr << "-E capabilities accepts no additional arguments\n";
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
cmake cm;
|
||||||
|
std::cout << cm.ReportCapabilities();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
// Sleep command
|
// Sleep command
|
||||||
else if (args[1] == "sleep" && args.size() > 2) {
|
else if (args[1] == "sleep" && args.size() > 2) {
|
||||||
|
|
|
@ -0,0 +1 @@
|
||||||
|
1
|
|
@ -0,0 +1 @@
|
||||||
|
^-E capabilities accepts no additional arguments$
|
|
@ -0,0 +1 @@
|
||||||
|
^{.*}$
|
|
@ -8,6 +8,8 @@ run_cmake_command(lists-no-file ${CMAKE_COMMAND} nosuchsubdir/CMakeLists.txt)
|
||||||
run_cmake_command(D-no-arg ${CMAKE_COMMAND} -D)
|
run_cmake_command(D-no-arg ${CMAKE_COMMAND} -D)
|
||||||
run_cmake_command(U-no-arg ${CMAKE_COMMAND} -U)
|
run_cmake_command(U-no-arg ${CMAKE_COMMAND} -U)
|
||||||
run_cmake_command(E-no-arg ${CMAKE_COMMAND} -E)
|
run_cmake_command(E-no-arg ${CMAKE_COMMAND} -E)
|
||||||
|
run_cmake_command(E_capabilities ${CMAKE_COMMAND} -E capabilities)
|
||||||
|
run_cmake_command(E_capabilities-arg ${CMAKE_COMMAND} -E capabilities --extra-arg)
|
||||||
run_cmake_command(E_echo_append ${CMAKE_COMMAND} -E echo_append)
|
run_cmake_command(E_echo_append ${CMAKE_COMMAND} -E echo_append)
|
||||||
run_cmake_command(E_rename-no-arg ${CMAKE_COMMAND} -E rename)
|
run_cmake_command(E_rename-no-arg ${CMAKE_COMMAND} -E rename)
|
||||||
run_cmake_command(E_touch_nocreate-no-arg ${CMAKE_COMMAND} -E touch_nocreate)
|
run_cmake_command(E_touch_nocreate-no-arg ${CMAKE_COMMAND} -E touch_nocreate)
|
||||||
|
|
Loading…
Reference in New Issue