CMake: Parse Generators out of new cmake -E capabilities output

Makes for way more robust (and featureful) generator discovery.

Change-Id: I7df837500e1c3a200960e9d157b5c105dacd4068
Reviewed-by: Tobias Hunger <tobias.hunger@qt.io>
This commit is contained in:
Tobias Hunger
2016-09-28 15:18:29 +02:00
parent b3b6cfb5ef
commit 3ef11019e2
2 changed files with 43 additions and 14 deletions

View File

@@ -31,6 +31,8 @@
#include <utils/qtcassert.h>
#include <QFileInfo>
#include <QJsonDocument>
#include <QJsonObject>
#include <QProcess>
#include <QSet>
#include <QTextDocument>
@@ -110,7 +112,7 @@ bool CMakeTool::isValid() const
return m_didRun;
}
Utils::SynchronousProcessResponse CMakeTool::run(const QString &arg) const
Utils::SynchronousProcessResponse CMakeTool::run(const QStringList &args, bool mayFail) const
{
if (m_didAttemptToRun && !m_didRun) {
Utils::SynchronousProcessResponse response;
@@ -126,9 +128,9 @@ Utils::SynchronousProcessResponse CMakeTool::run(const QString &arg) const
cmake.setProcessEnvironment(env.toProcessEnvironment());
cmake.setTimeOutMessageBoxEnabled(false);
Utils::SynchronousProcessResponse response = cmake.runBlocking(m_executable.toString(), QStringList() << arg);
Utils::SynchronousProcessResponse response = cmake.runBlocking(m_executable.toString(), args);
m_didAttemptToRun = true;
m_didRun = (response.result == Utils::SynchronousProcessResponse::Finished);
m_didRun = mayFail ? true : (response.result == Utils::SynchronousProcessResponse::Finished);
return response;
}
@@ -161,9 +163,12 @@ bool CMakeTool::isAutoRun() const
QList<CMakeTool::Generator> CMakeTool::supportedGenerators() const
{
if (m_generators.isEmpty())
fetchGeneratorsFromCapabilities();
if (m_generators.isEmpty()) {
fetchGeneratorsFromHelp();
}
return m_generators;
}
@@ -171,19 +176,19 @@ TextEditor::Keywords CMakeTool::keywords()
{
if (m_functions.isEmpty()) {
Utils::SynchronousProcessResponse response;
response = run("--help-command-list");
response = run({ "--help-command-list" });
if (response.result == Utils::SynchronousProcessResponse::Finished)
m_functions = response.stdOut().split('\n');
response = run("--help-commands");
response = run({ "--help-commands" });
if (response.result == Utils::SynchronousProcessResponse::Finished)
parseFunctionDetailsOutput(response.stdOut());
response = run("--help-property-list");
response = run({ "--help-property-list" });
if (response.result == Utils::SynchronousProcessResponse::Finished)
m_variables = parseVariableOutput(response.stdOut());
response = run("--help-variable-list");
response = run({ "--help-variable-list" });
if (response.result == Utils::SynchronousProcessResponse::Finished) {
m_variables.append(parseVariableOutput(response.stdOut()));
m_variables = Utils::filteredUnique(m_variables);
@@ -315,7 +320,7 @@ QStringList CMakeTool::parseVariableOutput(const QString &output)
void CMakeTool::fetchGeneratorsFromHelp() const
{
Utils::SynchronousProcessResponse response = run("--help");
Utils::SynchronousProcessResponse response = run({ "--help" });
if (response.result != Utils::SynchronousProcessResponse::Finished)
return;
@@ -361,11 +366,29 @@ void CMakeTool::fetchGeneratorsFromHelp() const
}
// Populate genertor list:
for (auto it = generatorInfo.constBegin(); it != generatorInfo.constEnd(); ++it) {
Generator info;
info.name = it.key();
info.extraGenerators = it.value();
m_generators.append(info);
for (auto it = generatorInfo.constBegin(); it != generatorInfo.constEnd(); ++it)
m_generators.append(Generator(it.key(), it.value()));
}
void CMakeTool::fetchGeneratorsFromCapabilities() const
{
Utils::SynchronousProcessResponse response = run({ "-E", "capabilities" }, true);
if (response.result != Utils::SynchronousProcessResponse::Finished)
return;
auto doc = QJsonDocument::fromJson(response.stdOut().toUtf8());
if (!doc.isObject())
return;
const QVariantMap data = doc.object().toVariantMap();
m_hasServerMode = data.value("serverMode").toBool();
const QVariantList generatorList = data.value("generators").toList();
for (const QVariant &v : generatorList) {
const QVariantMap gen = v.toMap();
m_generators.append(Generator(gen.value("name").toString(),
gen.value("extraGenerators").toStringList(),
gen.value("platformSupport").toBool(),
gen.value("toolsetSupport").toBool()));
}
}

View File

@@ -55,6 +55,10 @@ public:
class Generator
{
public:
Generator(const QString &n, const QStringList &eg, bool pl = true, bool ts = true) :
name(n), extraGenerators(eg), supportsPlatform(pl), supportsToolset(ts)
{ }
QString name;
QStringList extraGenerators;
bool supportsPlatform = true;
@@ -92,11 +96,12 @@ public:
QString mapAllPaths(const ProjectExplorer::Kit *kit, const QString &in) const;
private:
Utils::SynchronousProcessResponse run(const QString &arg) const;
Utils::SynchronousProcessResponse run(const QStringList &args, bool mayFail = false) const;
void parseFunctionDetailsOutput(const QString &output);
QStringList parseVariableOutput(const QString &output);
void fetchGeneratorsFromHelp() const;
void fetchGeneratorsFromCapabilities() const;
Core::Id m_id;
QString m_displayName;
@@ -107,6 +112,7 @@ private:
mutable bool m_didAttemptToRun = false;
mutable bool m_didRun = false;
mutable bool m_hasServerMode = false;
mutable QList<Generator> m_generators;
mutable QMap<QString, QStringList> m_functionArgs;