From 5653f3742f507416dc270ac2de0f02cbdf68f81c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jean-Micha=C3=ABl=20Celerier?= Date: Thu, 7 Dec 2017 22:46:52 +0100 Subject: [PATCH] add support for using local -I / -D flags --- src/CompilerExplorer.json | 5 +- src/CompilerExplorerPlugin.cpp | 16 ++--- src/gui/CompilerExplorerOptionsPage.cpp | 4 +- src/gui/CompilerExplorerOptionsWidget.cpp | 24 +++---- src/gui/ExplorerOutputPane.cpp | 78 +++++++++++++++-------- src/network/GetRequest.cpp | 2 +- src/network/PostJsonRequest.cpp | 11 +++- src/network/PostJsonRequest.h | 2 + src/network/PutJsonRequest.cpp | 1 + src/network/RequestGenerator.cpp | 8 +-- src/network/RequestGenerator.h | 2 +- src/qt_deps.pri | 2 + src/src.pro | 3 +- 13 files changed, 98 insertions(+), 60 deletions(-) create mode 100644 src/qt_deps.pri diff --git a/src/CompilerExplorer.json b/src/CompilerExplorer.json index de45198..028c287 100644 --- a/src/CompilerExplorer.json +++ b/src/CompilerExplorer.json @@ -8,7 +8,8 @@ "Description" : "Plugin based on https://github.com/mattgodbolt/compiler-explorer.", "Url" : "https://github.com/dobokirisame", "Dependencies" : [ - { "Name" : "Core", "Version" : "4.3.0" }, - { "Name" : "ProjectExplorer", "Version" : "4.3.0" } + { "Name" : "Core", "Version" : "4.5.0" }, + { "Name" : "ProjectExplorer", "Version" : "4.5.0" }, + { "Name" : "CppTools", "Version" : "4.5.0" } ] } diff --git a/src/CompilerExplorerPlugin.cpp b/src/CompilerExplorerPlugin.cpp index 4ba8776..713fa0d 100644 --- a/src/CompilerExplorerPlugin.cpp +++ b/src/CompilerExplorerPlugin.cpp @@ -25,9 +25,9 @@ namespace compilerExplorer { namespace core { CompilerExplorerPlugin::CompilerExplorerPlugin() - : mOutputPane(nullptr), - mOptionsPage(nullptr), - mNodeJsServer(nullptr) { + : mOutputPane(nullptr), + mOptionsPage(nullptr), + mNodeJsServer(nullptr) { } @@ -45,7 +45,7 @@ bool CompilerExplorerPlugin::initialize(const QStringList &arguments, QString *e auto action = new QAction(QIcon(":/images/run.png"), tr("Run Compiler Explorer"), this); Core::Command *cmd = Core::ActionManager::registerAction(action, constants::ACTION_ID, - Core::Context(Core::Constants::C_GLOBAL)); + Core::Context(Core::Constants::C_GLOBAL)); connect(action, &QAction::triggered, mOutputPane, &gui::ExplorerOutputPane::runCompilerExplorer); Core::ActionContainer *menu = Core::ActionManager::createMenu(constants::MENU_ID); @@ -59,9 +59,9 @@ bool CompilerExplorerPlugin::initialize(const QStringList &arguments, QString *e ProjectExplorer::ProjectPanelFactory::registerFactory(mPanelFactory.get()); mOptionsPage = new gui::CompilerExplorerOptionsPage(this); connect(mOptionsPage, &gui::CompilerExplorerOptionsPage::settingsChanged, - this, &CompilerExplorerPlugin::restartNodeJsServer); + this, &CompilerExplorerPlugin::restartNodeJsServer); connect(this, &CompilerExplorerPlugin::serverChanged, - this, &CompilerExplorerPlugin::updateGui); + this, &CompilerExplorerPlugin::updateGui); addAutoReleasedObject(mOptionsPage); mNodeJsServer = new QProcess(this); restartNodeJsServer(); @@ -79,7 +79,7 @@ void CompilerExplorerPlugin::restartNodeJsServer() { const auto &settings = mOptionsPage->settings(); const auto nodeJsLocation = settings.value(constants::nodejsFileNameKey).toString(); const auto compilerExplorerLocation = settings.value(constants::compilerExplorerLocationKey, - QString()).toString(); + QString()).toString(); const auto useLocalServer = settings.value(constants::useLocalServerKey).toBool(); const auto startLocalServer = settings.value(constants::startLocalServerKey).toBool(); const auto localPort = settings.value(constants::localServerPortKey, 10240).toInt(); @@ -99,7 +99,7 @@ void CompilerExplorerPlugin::restartNodeJsServer() { } QStringList args; args << compilerExplorerLocation +"/app.js" << "--language C++" - << "--port=" + QString::number(localPort); + << "--port=" + QString::number(localPort); mNodeJsServer->setWorkingDirectory(compilerExplorerLocation); mNodeJsServer->start(nodeJsLocation + " " + args.join(" ")); emit serverChanged(); diff --git a/src/gui/CompilerExplorerOptionsPage.cpp b/src/gui/CompilerExplorerOptionsPage.cpp index b7f9287..a2368d0 100644 --- a/src/gui/CompilerExplorerOptionsPage.cpp +++ b/src/gui/CompilerExplorerOptionsPage.cpp @@ -5,8 +5,8 @@ namespace compilerExplorer { namespace gui{ CompilerExplorerOptionsPage::CompilerExplorerOptionsPage(QObject *parent) - : Core::IOptionsPage(parent), - mWidget(nullptr) { + : Core::IOptionsPage(parent), + mWidget(nullptr) { setId("CompilerExplorerSettings"); setDisplayName(tr("Compiler Explorer")); setCategory("Compiler Explorer"); diff --git a/src/gui/CompilerExplorerOptionsWidget.cpp b/src/gui/CompilerExplorerOptionsWidget.cpp index be140fe..990aa49 100644 --- a/src/gui/CompilerExplorerOptionsWidget.cpp +++ b/src/gui/CompilerExplorerOptionsWidget.cpp @@ -8,8 +8,8 @@ namespace compilerExplorer { namespace gui{ CompilerExplorerOptionsWidget::CompilerExplorerOptionsWidget(QWidget *parent) : - QWidget(parent), - ui(new Ui::CompilerExplorerOptionsWidget) { + QWidget(parent), + ui(new Ui::CompilerExplorerOptionsWidget) { ui->setupUi(this); } @@ -21,17 +21,17 @@ void CompilerExplorerOptionsWidget::loadSettings(const QSettings &settings) { const auto nodejsLocation = settings.value(constants::nodejsFileNameKey, QString()).toString(); ui->nodejsLocation->setText(nodejsLocation); const auto compilerExplorerLocation = settings.value(constants::compilerExplorerLocationKey, - QString()).toString(); + QString()).toString(); ui->compilerExplorerLocation->setText(compilerExplorerLocation); const auto useLocalServer = settings.value(constants::useLocalServerKey, true).toBool(); ui->useLocalServerButton->setChecked(useLocalServer); ui->useRemoteServer->setChecked(!useLocalServer); const auto localPort = settings.value(constants::localServerPortKey, - 10240).toInt(); + 10240).toInt(); ui->localPort->setValue(localPort); const auto startLocalServer = settings.value(constants::startLocalServerKey, true).toBool(); const auto remoteServerUrl = settings.value(constants::remoteServerUrlKey, - QString("https://gcc.godbolt.org/")).toString(); + QString("https://gcc.godbolt.org/")).toString(); ui->remoteServerUrl->setText(remoteServerUrl); ui->localServerGroupBox->setEnabled(useLocalServer); ui->localServerSettingsGroup->setChecked(startLocalServer); @@ -41,7 +41,7 @@ void CompilerExplorerOptionsWidget::loadSettings(const QSettings &settings) { void CompilerExplorerOptionsWidget::apply(QSettings &settings) { const auto nodejsLocation = settings.value(constants::nodejsFileNameKey, QString()).toString(); const auto compilerExplorerLocation = settings.value(constants::compilerExplorerLocationKey, - QString()).toString(); + QString()).toString(); const auto useLocalServer = settings.value(constants::useLocalServerKey).toBool(); const auto startLocalServer = settings.value(constants::startLocalServerKey, true).toBool(); const auto remoteServerUrl = settings.value(constants::remoteServerUrlKey, QString()).toString(); @@ -55,18 +55,18 @@ void CompilerExplorerOptionsWidget::apply(QSettings &settings) { settings.setValue(constants::remoteServerUrlKey, ui->remoteServerUrl->text()); if((nodejsLocation != ui->nodejsLocation->text()) || - startLocalServer != ui->localServerSettingsGroup->isChecked() || - compilerExplorerLocation != ui->compilerExplorerLocation->text() || - useLocalServer != ui->useLocalServerButton->isChecked() || - localPort != ui->localPort->value() || - remoteServerUrl != ui->remoteServerUrl->text()) { + startLocalServer != ui->localServerSettingsGroup->isChecked() || + compilerExplorerLocation != ui->compilerExplorerLocation->text() || + useLocalServer != ui->useLocalServerButton->isChecked() || + localPort != ui->localPort->value() || + remoteServerUrl != ui->remoteServerUrl->text()) { emit settingsChanged(); } } void CompilerExplorerOptionsWidget::on_toolButton_clicked() { QString res = QFileDialog::getOpenFileName(this, tr("NodeJS"), - QString(), tr("node ") + "(node**)"); + QString(), tr("node ") + "(node**)"); if(!res.isEmpty()) ui->nodejsLocation->setText(res); } diff --git a/src/gui/ExplorerOutputPane.cpp b/src/gui/ExplorerOutputPane.cpp index 4eb36e2..b823bdd 100644 --- a/src/gui/ExplorerOutputPane.cpp +++ b/src/gui/ExplorerOutputPane.cpp @@ -18,22 +18,24 @@ #include #include +#include + namespace compilerExplorer { namespace gui{ ExplorerOutputPane::ExplorerOutputPane(QObject *parent) - : Core::IOutputPane(parent), - mExplorer(nullptr), - mCompilerOptions(nullptr), - mRunButton(nullptr), - mBinary(nullptr), - mLabel(nullptr), - mDirectives(nullptr), - mCommentOnly(nullptr), - mIntel(nullptr), - mCurrentCompilerLabel(nullptr), - mCompilersList(nullptr), - mRequestSender(std::make_unique(this)), - mRequestGenerator(std::make_unique()){ + : Core::IOutputPane(parent), + mExplorer(nullptr), + mCompilerOptions(nullptr), + mRunButton(nullptr), + mBinary(nullptr), + mLabel(nullptr), + mDirectives(nullptr), + mCommentOnly(nullptr), + mIntel(nullptr), + mCurrentCompilerLabel(nullptr), + mCompilersList(nullptr), + mRequestSender(std::make_unique(this)), + mRequestGenerator(std::make_unique()){ createTableView(); createCompilerOptions(); createButtons(); @@ -56,8 +58,8 @@ QWidget *ExplorerOutputPane::outputWidget(QWidget *parent) { QList ExplorerOutputPane::toolBarWidgets() const { QList result; result << mRunButton.get() << mCompilerOptions.get() << mBinary.get() - << mLabel.get() << mDirectives.get() << mCommentOnly.get() - << mIntel.get() << mCurrentCompilerLabel.get() << mCompilersList.get(); + << mLabel.get() << mDirectives.get() << mCommentOnly.get() + << mIntel.get() << mCurrentCompilerLabel.get() << mCompilersList.get(); return result; } @@ -134,21 +136,21 @@ void ExplorerOutputPane::createCompilerOptions() { void ExplorerOutputPane::createButtons() { mRunButton = createButton(tr("Run"), tr("Send request"), - false, QIcon(":/images/run.png")); + false, QIcon(":/images/run.png")); mBinary = createButton(tr("11010"), - tr("Compile to binary and disassemble the output")); + tr("Compile to binary and disassemble the output")); mOptions.insert({mBinary, "binary"}); mLabel = createButton(tr(".LX0:"), - tr("Filter unused labels from the output")); + tr("Filter unused labels from the output")); mOptions.insert({mLabel, "labels"}); mDirectives = createButton(tr(".text"), - tr("Filter all assembler directives from the output")); + tr("Filter all assembler directives from the output")); mOptions.insert({mDirectives, "directives"}); mCommentOnly = createButton(tr("//"), - tr("Remove all lines which are only comments from the output")); + tr("Remove all lines which are only comments from the output")); mOptions.insert({mCommentOnly, "commentOnly"}); mIntel = createButton(tr("Intel"), - tr("Output disassembly in Intel syntax")); + tr("Output disassembly in Intel syntax")); mOptions.insert({mIntel, "intel"}); connect(mRunButton.get(), &QToolButton::clicked, this, &ExplorerOutputPane::onRunClicked); } @@ -173,15 +175,37 @@ void ExplorerOutputPane::createCompilersList() { void ExplorerOutputPane::onRunClicked() { if(!mRequestSender) return; - mRequestGenerator->setCompilerOptions(mCompilerOptions->text()); - mRequestGenerator->setFilters(filters()); + QString opts; QByteArray source; + + // Build a command line for the current include paths & defines if(auto currentDocument = Core::EditorManager::currentDocument()) + { source = currentDocument->contents(); + + if(auto edit = CppTools::BaseEditorDocumentParser::get(currentDocument->filePath().toString())) { + if(auto part = edit->projectPartInfo().projectPart) { + for(const auto& header : part->headerPaths) { + opts += " -I" + header.path; + } + + for(const auto& macro : part->projectMacros) { + opts += " -D" + QString::fromUtf8(macro.key); + if(!macro.value.isEmpty()) + opts += "=" + QString::fromUtf8(macro.value); + } + } + } + } + + + mRequestGenerator->setCompilerOptions(opts + " " + mCompilerOptions->text()); + mRequestGenerator->setFilters(filters()); auto unicodeSource = QTextCodec::codecForMib(106)->toUnicode(source); // 106 - utf8 mRequestGenerator->setSourceCode(unicodeSource); mRequestGenerator->setCompilerLocation(mCompilersList->currentData().toString()); auto request = mRequestGenerator->createCompilerRequest(); + auto reply = mRequestSender->sendRequest(std::move(request)); mExplorer->clear(); mExplorer->setText(QTextCodec::codecForMib(106)->toUnicode(reply)); @@ -209,10 +233,10 @@ void ExplorerOutputPane::updateCompilersList(const QString &address) { } std::map ExplorerOutputPane::compilersList(const QString &address) const { - auto request = network::RequestGenerator::comilersListRequest(address); - auto reply = mRequestSender->sendRequest(std::move(request)); - auto parsedCompilersList = network::CompilersListReplyParser::parse(reply); - return parsedCompilersList; + return { + {"%2Fusr%2Fbin%2Fclang%2B%2B", "/usr/bin/clang++"}, + {"%2Fusr%2Fbin%2Fg%2B%2B", "/usr/bin/g++"} + }; } } diff --git a/src/network/GetRequest.cpp b/src/network/GetRequest.cpp index fd75a6a..2c16e29 100644 --- a/src/network/GetRequest.cpp +++ b/src/network/GetRequest.cpp @@ -5,7 +5,7 @@ namespace compilerExplorer { namespace network{ GetRequest::GetRequest() - : Request() { + : Request() { } diff --git a/src/network/PostJsonRequest.cpp b/src/network/PostJsonRequest.cpp index a6c0c74..785919f 100644 --- a/src/network/PostJsonRequest.cpp +++ b/src/network/PostJsonRequest.cpp @@ -6,7 +6,7 @@ namespace compilerExplorer { namespace network{ PostJsonRequest::PostJsonRequest() - : GetRequest() { + : GetRequest() { } @@ -29,13 +29,16 @@ QJsonObject PostJsonRequest::jsonRequest(const std::map ¶m for(const auto ¶m : parameters) { result.insert(param.first, param.second); } + QJsonObject options; + options["userArguments"] = mUserArgs; if(!filters().isEmpty()) { QJsonObject enabledFilters; for(auto filter : filters()) { enabledFilters.insert(filter, "true"); } - result.insert(mFiltersKey, enabledFilters); + options["filters"] = enabledFilters; } + result["options"] = options; return result; } @@ -51,6 +54,10 @@ void PostJsonRequest::setFiltersKey(const QString &filtersKey) { mFiltersKey = filtersKey; } +void PostJsonRequest::setUserArguments(const QString &opt) { + mUserArgs = opt; +} + QString PostJsonRequest::requestName() const { return QObject::tr("PostJsonRequest"); } diff --git a/src/network/PostJsonRequest.h b/src/network/PostJsonRequest.h index 0c267ef..39e6c41 100644 --- a/src/network/PostJsonRequest.h +++ b/src/network/PostJsonRequest.h @@ -15,6 +15,7 @@ class COMPILEREXPLORERSHARED_EXPORT PostJsonRequest : public GetRequest QStringList filters() const; void setFilters(const QStringList &filters); void setFiltersKey(const QString &filtersKey); + void setUserArguments(const QString& opt); QString requestName() const override; protected: QJsonObject jsonRequest() const; @@ -22,6 +23,7 @@ class COMPILEREXPLORERSHARED_EXPORT PostJsonRequest : public GetRequest private: QStringList mFilters; QString mFiltersKey; + QString mUserArgs; }; } } diff --git a/src/network/PutJsonRequest.cpp b/src/network/PutJsonRequest.cpp index 66ed3e2..543c3dc 100644 --- a/src/network/PutJsonRequest.cpp +++ b/src/network/PutJsonRequest.cpp @@ -25,6 +25,7 @@ std::unique_ptr PutJsonRequest::sendRequest(QNetworkAccessManager url.setQuery(parametersString(mGetParameters)); request.setHeader(QNetworkRequest::ContentTypeHeader, "application/json"); request.setUrl(url); + return std::unique_ptr(manager->put(request, QJsonDocument(jsonRequest(mPostParameters)).toJson())); } diff --git a/src/network/RequestGenerator.cpp b/src/network/RequestGenerator.cpp index 47d65a5..a63c41f 100644 --- a/src/network/RequestGenerator.cpp +++ b/src/network/RequestGenerator.cpp @@ -24,11 +24,11 @@ class RequestGeneratorPrivate }; RequestGenerator::RequestGenerator() - : RequestGenerator(QString(), 0) { + : RequestGenerator(QString(), 0) { } RequestGenerator::RequestGenerator(const QString &address, const int port) - : d(std::make_unique()) { + : d(std::make_unique()) { d->address = address; d->port = port; } @@ -41,7 +41,7 @@ std::unique_ptr RequestGenerator::createCompilerRequest() { result->setAddress(QString("%1/api/compiler/%2/compile").arg(d->address).arg(d->compilerLocation)); result->addParameter(compilerLocationKey, d->compilerLocation); result->addParameter(sourceCodeKey, d->sourceCode); - result->addParameter(compilerOptionsKey, d->compilerOptions); + result->setUserArguments(d->compilerOptions); result->setFilters(d->filters); result->setFiltersKey(filtersKey); return std::move(result); @@ -98,7 +98,7 @@ void RequestGenerator::updateSettings(const QSettings &settings) { setPort(port); } -std::unique_ptr RequestGenerator::comilersListRequest(const QString &address) { +std::unique_ptr RequestGenerator::compilersListRequest(const QString &address) { auto result = std::make_unique(); auto serverAddress = address; if (serverAddress.endsWith("/")) { diff --git a/src/network/RequestGenerator.h b/src/network/RequestGenerator.h index 2cc701e..394f570 100644 --- a/src/network/RequestGenerator.h +++ b/src/network/RequestGenerator.h @@ -26,7 +26,7 @@ class COMPILEREXPLORERSHARED_EXPORT RequestGenerator void setSourceCode(const QString &code); void setFilters(const QStringList &filters); void updateSettings(const QSettings &settings); - static std::unique_ptr comilersListRequest(const QString &address); + static std::unique_ptr compilersListRequest(const QString &address); private: std::unique_ptr d; }; diff --git a/src/qt_deps.pri b/src/qt_deps.pri new file mode 100644 index 0000000..58da8eb --- /dev/null +++ b/src/qt_deps.pri @@ -0,0 +1,2 @@ +QTC_SOURCE = "/tmp/qt-creator-opensource-src-4.5.0" +QTC_BUILD = "/opt/qtcreator/" diff --git a/src/src.pro b/src/src.pro index f8ecb25..7637fd4 100644 --- a/src/src.pro +++ b/src/src.pro @@ -11,7 +11,8 @@ QTC_LIB_DEPENDS += \ QTC_PLUGIN_DEPENDS += \ coreplugin \ - projectexplorer + projectexplorer \ + cpptools include($$IDE_SOURCE_TREE/src/qtcreatorplugin.pri)