From 0813a08b1e7704da97e857d773ed638672c731c1 Mon Sep 17 00:00:00 2001 From: hjk Date: Thu, 13 Jan 2022 12:42:51 +0100 Subject: [PATCH 01/21] Docker: Re-do auto-detection of Qt This now properly iterates into subdirectories when selecting the "Search in selected directories" option for the auto-detection so it works with Boot2Qt images that don't put Qt in PATH, but somewhere under /opt Change-Id: Ifc337c0169d4b98b4e894a5d7e8286f171e0c569 Reviewed-by: Christian Stenger --- src/plugins/docker/dockerdevice.cpp | 37 +++++++++++++++++------------ 1 file changed, 22 insertions(+), 15 deletions(-) diff --git a/src/plugins/docker/dockerdevice.cpp b/src/plugins/docker/dockerdevice.cpp index 1f6744d3894..9fe4ac081b8 100644 --- a/src/plugins/docker/dockerdevice.cpp +++ b/src/plugins/docker/dockerdevice.cpp @@ -709,20 +709,26 @@ QtVersions KitDetectorPrivate::autoDetectQtVersions() const QtVersions qtVersions; QString error; + + const auto handleQmake = [this, &qtVersions, &error](const FilePath &qmake) { + if (QtVersion *qtVersion = QtVersionFactory::createQtVersionFromQMakePath(qmake, false, m_sharedId, &error)) { + qtVersions.append(qtVersion); + QtVersionManager::addVersion(qtVersion); + emit q->logOutput(tr("Found \"%1\"").arg(qtVersion->qmakeFilePath().toUserOutput())); + } + return true; + }; + + emit q->logOutput(tr("Searching for qmake executables...")); + const QStringList candidates = {"qmake-qt6", "qmake-qt5", "qmake"}; - emit q->logOutput('\n' + tr("Searching Qt installations...")); - for (const QString &candidate : candidates) { - emit q->logOutput(tr("Searching for %1 executable...").arg(candidate)); - const FilePath qmake = m_device->searchExecutable(candidate, m_searchPaths); - if (qmake.isEmpty()) - continue; - QtVersion *qtVersion = QtVersionFactory::createQtVersionFromQMakePath(qmake, false, m_sharedId, &error); - if (!qtVersion) - continue; - qtVersions.append(qtVersion); - QtVersionManager::addVersion(qtVersion); - emit q->logOutput(tr("Found \"%1\"").arg(qtVersion->qmakeFilePath().toUserOutput())); + for (const FilePath &searchPath : m_searchPaths) { + searchPath.iterateDirectory(handleQmake, {candidates, QDir::Files | QDir::Executable, + QDirIterator::Subdirectories}); } + + if (!error.isEmpty()) + emit q->logOutput(tr("Error: %1.").arg(error)); if (qtVersions.isEmpty()) emit q->logOutput(tr("No Qt installation found.")); return qtVersions; @@ -793,19 +799,20 @@ void KitDetectorPrivate::autoDetect() emit q->logOutput(tr("Starting auto-detection. This will take a while...")); - QList toolChains = autoDetectToolChains(); - QtVersions qtVersions = autoDetectQtVersions(); + const Toolchains toolchains = autoDetectToolChains(); + const QtVersions qtVersions = autoDetectQtVersions(); autoDetectCMake(); autoDetectDebugger(); - const auto initializeKit = [this, toolChains, qtVersions](Kit *k) { + const auto initializeKit = [this, toolchains, qtVersions](Kit *k) { k->setAutoDetected(false); k->setAutoDetectionSource(m_sharedId); k->setUnexpandedDisplayName("%{Device:Name}"); DeviceTypeKitAspect::setDeviceTypeId(k, Constants::DOCKER_DEVICE_TYPE); DeviceKitAspect::setDevice(k, m_device); + QtVersion *qt = nullptr; if (!qtVersions.isEmpty()) { qt = qtVersions.at(0); From a386725c6c1fb41516e682314ee65d4b49b4fa9d Mon Sep 17 00:00:00 2001 From: Alessandro Portale Date: Thu, 27 Jan 2022 09:25:03 +0100 Subject: [PATCH 02/21] Utils: Support sorting by QDir::Time in FilePath::dirEntries Amends: f9c97d23c732fdbdcdaa37a6585e384bfc8750d3 Task-number: QTCREATORBUG-26939 Change-Id: I9122d51af102547086687b1b9c6cb1553b609673 Reviewed-by: hjk (cherry picked from commit ec0513bf4b49521bcbee67eae7cc0b0b0df79f41) Reviewed-by: Eike Ziller --- src/libs/utils/filepath.cpp | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/src/libs/utils/filepath.cpp b/src/libs/utils/filepath.cpp index bcf713687a8..4ec1d026f75 100644 --- a/src/libs/utils/filepath.cpp +++ b/src/libs/utils/filepath.cpp @@ -734,8 +734,14 @@ FilePaths FilePath::dirEntries(const FileFilter &filter, QDir::SortFlags sort) c // FIXME: Not all flags supported here. - if ((sort & QDir::SortByMask) == QDir::Name) + const QDir::SortFlags sortBy = (sort & QDir::SortByMask); + if (sortBy == QDir::Name) { Utils::sort(result); + } else if (sortBy == QDir::Time) { + Utils::sort(result, [](const FilePath &path1, const FilePath &path2) { + return path1.lastModified() < path2.lastModified(); + }); + } if (sort & QDir::Reversed) std::reverse(result.begin(), result.end()); From 4e34921451ee7dfc2980aa8b22abf02b8b318fcb Mon Sep 17 00:00:00 2001 From: hjk Date: Thu, 27 Jan 2022 10:55:39 +0100 Subject: [PATCH 03/21] ProjectExplorer: Rename DeviceProcess::error to errorOccured That's what QProcess favors nowadays and QtcProcess uses. Change-Id: Ie9492ae62f23e35a8a70f72196c3d1b6bc50cbdc Reviewed-by: Jarek Kobus --- src/plugins/docker/dockerdevice.cpp | 4 ++-- src/plugins/perfprofiler/perfconfigwidget.cpp | 2 +- src/plugins/perfprofiler/perfprofilerruncontrol.cpp | 2 +- src/plugins/perfprofiler/perftracepointdialog.cpp | 2 +- src/plugins/projectexplorer/applicationlauncher.cpp | 2 +- .../projectexplorer/devicesupport/desktopdeviceprocess.cpp | 2 +- src/plugins/projectexplorer/devicesupport/deviceprocess.h | 2 +- .../devicesupport/deviceusedportsgatherer.cpp | 2 +- .../projectexplorer/devicesupport/sshdeviceprocess.cpp | 6 +++--- src/plugins/qnx/qnxdevice.cpp | 2 +- src/plugins/qnx/slog2inforunner.cpp | 2 +- src/plugins/remotelinux/linuxdevice.cpp | 2 +- src/plugins/remotelinux/remotelinuxenvironmentreader.cpp | 2 +- 13 files changed, 16 insertions(+), 16 deletions(-) diff --git a/src/plugins/docker/dockerdevice.cpp b/src/plugins/docker/dockerdevice.cpp index 9fe4ac081b8..e97d64e3964 100644 --- a/src/plugins/docker/dockerdevice.cpp +++ b/src/plugins/docker/dockerdevice.cpp @@ -154,7 +154,7 @@ void DockerDeviceProcess::start(const Runnable &runnable) m_process.setCommand(command); m_process.setEnvironment(runnable.environment); m_process.setWorkingDirectory(runnable.workingDirectory); - connect(&m_process, &QtcProcess::errorOccurred, this, &DeviceProcess::error); + connect(&m_process, &QtcProcess::errorOccurred, this, &DeviceProcess::errorOccurred); connect(&m_process, &QtcProcess::finished, this, &DeviceProcess::finished); connect(&m_process, &QtcProcess::readyReadStandardOutput, this, &DeviceProcess::readyReadStandardOutput); @@ -569,7 +569,7 @@ DockerDevice::DockerDevice(const DockerDeviceData &data) } proc->deleteLater(); }); - QObject::connect(proc, &DeviceProcess::error, [proc] { + QObject::connect(proc, &DeviceProcess::errorOccurred, [proc] { MessageManager::writeDisrupting(tr("Error starting remote shell.")); proc->deleteLater(); }); diff --git a/src/plugins/perfprofiler/perfconfigwidget.cpp b/src/plugins/perfprofiler/perfconfigwidget.cpp index d201a08ff0d..b58900c5d60 100644 --- a/src/plugins/perfprofiler/perfconfigwidget.cpp +++ b/src/plugins/perfprofiler/perfconfigwidget.cpp @@ -149,7 +149,7 @@ void PerfConfigWidget::setTarget(ProjectExplorer::Target *target) connect(m_process.get(), &ProjectExplorer::DeviceProcess::finished, this, &PerfConfigWidget::handleProcessFinished); - connect(m_process.get(), &ProjectExplorer::DeviceProcess::error, + connect(m_process.get(), &ProjectExplorer::DeviceProcess::errorOccurred, this, &PerfConfigWidget::handleProcessError); useTracePointsButton->setEnabled(true); diff --git a/src/plugins/perfprofiler/perfprofilerruncontrol.cpp b/src/plugins/perfprofiler/perfprofilerruncontrol.cpp index 4bdecd52dbb..684918bb6a8 100644 --- a/src/plugins/perfprofiler/perfprofilerruncontrol.cpp +++ b/src/plugins/perfprofiler/perfprofilerruncontrol.cpp @@ -133,7 +133,7 @@ public: connect(m_process, &DeviceProcess::started, this, &RunWorker::reportStarted); connect(m_process, &DeviceProcess::finished, this, &RunWorker::reportStopped); - connect(m_process, &DeviceProcess::error, [this](QProcess::ProcessError e) { + connect(m_process, &DeviceProcess::errorOccurred, [this](QProcess::ProcessError e) { // The terminate() below will frequently lead to QProcess::Crashed. We're not interested // in that. FailedToStart is the only actual failure. if (e == QProcess::FailedToStart) { diff --git a/src/plugins/perfprofiler/perftracepointdialog.cpp b/src/plugins/perfprofiler/perftracepointdialog.cpp index b439fd7cbe9..3bb2197ea58 100644 --- a/src/plugins/perfprofiler/perftracepointdialog.cpp +++ b/src/plugins/perfprofiler/perftracepointdialog.cpp @@ -113,7 +113,7 @@ void PerfTracePointDialog::runScript() connect(m_process.get(), &DeviceProcess::finished, this, &PerfTracePointDialog::handleProcessFinished); - connect(m_process.get(), &DeviceProcess::error, + connect(m_process.get(), &DeviceProcess::errorOccurred, this, &PerfTracePointDialog::handleProcessError); m_process->start(runnable); diff --git a/src/plugins/projectexplorer/applicationlauncher.cpp b/src/plugins/projectexplorer/applicationlauncher.cpp index 63621eab68c..475622c7038 100644 --- a/src/plugins/projectexplorer/applicationlauncher.cpp +++ b/src/plugins/projectexplorer/applicationlauncher.cpp @@ -424,7 +424,7 @@ void ApplicationLauncherPrivate::start(const Runnable &runnable, const IDevice:: this, &ApplicationLauncherPrivate::handleRemoteStdout); connect(m_deviceProcess, &DeviceProcess::readyReadStandardError, this, &ApplicationLauncherPrivate::handleRemoteStderr); - connect(m_deviceProcess, &DeviceProcess::error, + connect(m_deviceProcess, &DeviceProcess::errorOccurred, this, &ApplicationLauncherPrivate::handleApplicationError); connect(m_deviceProcess, &DeviceProcess::finished, this, &ApplicationLauncherPrivate::handleApplicationFinished); diff --git a/src/plugins/projectexplorer/devicesupport/desktopdeviceprocess.cpp b/src/plugins/projectexplorer/devicesupport/desktopdeviceprocess.cpp index 0bb27f3435d..004eef0af51 100644 --- a/src/plugins/projectexplorer/devicesupport/desktopdeviceprocess.cpp +++ b/src/plugins/projectexplorer/devicesupport/desktopdeviceprocess.cpp @@ -42,7 +42,7 @@ DesktopDeviceProcess::DesktopDeviceProcess(const QSharedPointer & : DeviceProcess(device, parent) , m_process(ProcessMode::Writer) { - connect(&m_process, &QtcProcess::errorOccurred, this, &DeviceProcess::error); + connect(&m_process, &QtcProcess::errorOccurred, this, &DeviceProcess::errorOccurred); connect(&m_process, &QtcProcess::finished, this, &DeviceProcess::finished); connect(&m_process, &QtcProcess::readyReadStandardOutput, this, &DeviceProcess::readyReadStandardOutput); diff --git a/src/plugins/projectexplorer/devicesupport/deviceprocess.h b/src/plugins/projectexplorer/devicesupport/deviceprocess.h index 4aa197666c3..c097bc6d09b 100644 --- a/src/plugins/projectexplorer/devicesupport/deviceprocess.h +++ b/src/plugins/projectexplorer/devicesupport/deviceprocess.h @@ -62,7 +62,7 @@ public: signals: void started(); void finished(); - void error(QProcess::ProcessError error); + void errorOccurred(QProcess::ProcessError error); void readyReadStandardOutput(); void readyReadStandardError(); diff --git a/src/plugins/projectexplorer/devicesupport/deviceusedportsgatherer.cpp b/src/plugins/projectexplorer/devicesupport/deviceusedportsgatherer.cpp index 377be1d5206..d2d3961a015 100644 --- a/src/plugins/projectexplorer/devicesupport/deviceusedportsgatherer.cpp +++ b/src/plugins/projectexplorer/devicesupport/deviceusedportsgatherer.cpp @@ -79,7 +79,7 @@ void DeviceUsedPortsGatherer::start(const IDevice::ConstPtr &device) connect(d->process.data(), &DeviceProcess::finished, this, &DeviceUsedPortsGatherer::handleProcessFinished); - connect(d->process.data(), &DeviceProcess::error, + connect(d->process.data(), &DeviceProcess::errorOccurred, this, &DeviceUsedPortsGatherer::handleProcessError); connect(d->process.data(), &DeviceProcess::readyReadStandardOutput, this, &DeviceUsedPortsGatherer::handleRemoteStdOut); diff --git a/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp b/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp index 3b848b84089..71d7b14cd71 100644 --- a/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp +++ b/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp @@ -194,7 +194,7 @@ void SshDeviceProcess::handleConnected() if (runInTerminal()) { d->process->setUseTerminal(true); connect(&d->consoleProcess, &QtcProcess::errorOccurred, - this, &DeviceProcess::error); + this, &DeviceProcess::errorOccurred); connect(&d->consoleProcess, &QtcProcess::started, this, &SshDeviceProcess::handleProcessStarted); connect(&d->consoleProcess, &QtcProcess::finished, @@ -231,7 +231,7 @@ void SshDeviceProcess::handleDisconnected() switch (oldState) { case SshDeviceProcessPrivate::Connecting: case SshDeviceProcessPrivate::Connected: - emit error(QProcess::FailedToStart); + emit errorOccurred(QProcess::FailedToStart); break; case SshDeviceProcessPrivate::ProcessRunning: d->exitStatus = QProcess::CrashExit; @@ -317,7 +317,7 @@ void SshDeviceProcess::SshDeviceProcessPrivate::doSignal(Signal signal) case SshDeviceProcessPrivate::Connecting: errorMessage = tr("Terminated by request."); setState(SshDeviceProcessPrivate::Inactive); - emit q->error(QProcess::FailedToStart); + emit q->errorOccurred(QProcess::FailedToStart); break; case SshDeviceProcessPrivate::Connected: case SshDeviceProcessPrivate::ProcessRunning: diff --git a/src/plugins/qnx/qnxdevice.cpp b/src/plugins/qnx/qnxdevice.cpp index 37d29516583..4c88743f2ad 100644 --- a/src/plugins/qnx/qnxdevice.cpp +++ b/src/plugins/qnx/qnxdevice.cpp @@ -104,7 +104,7 @@ void QnxDevice::updateVersionNumber() const QEventLoop eventLoop; SshDeviceProcess versionNumberProcess(sharedFromThis()); QObject::connect(&versionNumberProcess, &SshDeviceProcess::finished, &eventLoop, &QEventLoop::quit); - QObject::connect(&versionNumberProcess, &DeviceProcess::error, &eventLoop, &QEventLoop::quit); + QObject::connect(&versionNumberProcess, &DeviceProcess::errorOccurred, &eventLoop, &QEventLoop::quit); Runnable r; r.command = {"uname", {"-r"}}; diff --git a/src/plugins/qnx/slog2inforunner.cpp b/src/plugins/qnx/slog2inforunner.cpp index cd341899ade..c5209fdfe54 100644 --- a/src/plugins/qnx/slog2inforunner.cpp +++ b/src/plugins/qnx/slog2inforunner.cpp @@ -60,7 +60,7 @@ Slog2InfoRunner::Slog2InfoRunner(RunControl *runControl) m_logProcess = new QnxDeviceProcess(device(), this); connect(m_logProcess, &DeviceProcess::readyReadStandardOutput, this, &Slog2InfoRunner::readLogStandardOutput); connect(m_logProcess, &DeviceProcess::readyReadStandardError, this, &Slog2InfoRunner::readLogStandardError); - connect(m_logProcess, &DeviceProcess::error, this, &Slog2InfoRunner::handleLogError); + connect(m_logProcess, &DeviceProcess::errorOccurred, this, &Slog2InfoRunner::handleLogError); } void Slog2InfoRunner::printMissingWarning() diff --git a/src/plugins/remotelinux/linuxdevice.cpp b/src/plugins/remotelinux/linuxdevice.cpp index 9387b46b7cd..171f6d7421f 100644 --- a/src/plugins/remotelinux/linuxdevice.cpp +++ b/src/plugins/remotelinux/linuxdevice.cpp @@ -324,7 +324,7 @@ LinuxDevice::LinuxDevice() } proc->deleteLater(); }); - QObject::connect(proc, &DeviceProcess::error, [proc] { + QObject::connect(proc, &DeviceProcess::errorOccurred, [proc] { Core::MessageManager::writeDisrupting(tr("Error starting remote shell.")); proc->deleteLater(); }); diff --git a/src/plugins/remotelinux/remotelinuxenvironmentreader.cpp b/src/plugins/remotelinux/remotelinuxenvironmentreader.cpp index 6f477bdcce6..fd59e384317 100644 --- a/src/plugins/remotelinux/remotelinuxenvironmentreader.cpp +++ b/src/plugins/remotelinux/remotelinuxenvironmentreader.cpp @@ -54,7 +54,7 @@ void RemoteLinuxEnvironmentReader::start() } m_stop = false; m_deviceProcess = m_device->createProcess(this); - connect(m_deviceProcess, &DeviceProcess::error, + connect(m_deviceProcess, &DeviceProcess::errorOccurred, this, &RemoteLinuxEnvironmentReader::handleError); connect(m_deviceProcess, &DeviceProcess::finished, this, &RemoteLinuxEnvironmentReader::remoteProcessFinished); From 859fa576488cdb999f53a49ef8b09d59866b6cee Mon Sep 17 00:00:00 2001 From: Alessandro Portale Date: Thu, 27 Jan 2022 10:30:09 +0100 Subject: [PATCH 04/21] ProjectExplorer: Sort loaded sessions by time in reverse Fixes: QTCREATORBUG-26939 Change-Id: I2152dbf7c06dbdc511b4db143efe3375cdad04f1 Reviewed-by: Orgad Shaneh --- src/plugins/projectexplorer/session.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/plugins/projectexplorer/session.cpp b/src/plugins/projectexplorer/session.cpp index bd48cc84daf..c03baf88482 100644 --- a/src/plugins/projectexplorer/session.cpp +++ b/src/plugins/projectexplorer/session.cpp @@ -791,7 +791,8 @@ QStringList SessionManager::sessions() { if (d->m_sessions.isEmpty()) { // We are not initialized yet, so do that now - const FilePaths sessionFiles = ICore::userResourcePath().dirEntries({{"*qws"}}, QDir::Time); + const FilePaths sessionFiles = + ICore::userResourcePath().dirEntries({{"*qws"}}, QDir::Time | QDir::Reversed); for (const FilePath &file : sessionFiles) { const QString &name = file.completeBaseName(); d->m_sessionDateTimes.insert(name, file.lastModified()); From 6993bc7382eba79a05999a1ff32d960f90bd89b1 Mon Sep 17 00:00:00 2001 From: Christian Kandeler Date: Wed, 26 Jan 2022 17:01:22 +0100 Subject: [PATCH 05/21] Fix various warnings Change-Id: Iea85f4b890ce7700e8b3632de4656cf848729a36 Reviewed-by: Qt CI Bot Reviewed-by: Eike Ziller --- src/libs/utils/qtcprocess.cpp | 20 ++-- src/libs/utils/terminalprocess.cpp | 112 +++++++++--------- src/plugins/coreplugin/fileutils.cpp | 28 ++--- .../devicesupport/devicemanager.cpp | 10 +- .../components/edit3d/edit3dview.cpp | 2 + .../designercore/model/texttomodelmerger.cpp | 2 +- src/plugins/remotelinux/linuxdevice.cpp | 4 +- src/plugins/remotelinux/linuxdevice.h | 2 +- 8 files changed, 87 insertions(+), 93 deletions(-) diff --git a/src/libs/utils/qtcprocess.cpp b/src/libs/utils/qtcprocess.cpp index 9a6197fae39..dac6947b040 100644 --- a/src/libs/utils/qtcprocess.cpp +++ b/src/libs/utils/qtcprocess.cpp @@ -227,8 +227,8 @@ public: virtual void setWorkingDirectory(const QString &dir) = 0; virtual void start(const QString &program, const QStringList &arguments, const QByteArray &writeData) = 0; - virtual void customStart(const CommandLine &command, const FilePath &workingDirectory, - const Environment &environment) { QTC_CHECK(false); } + virtual void customStart(const CommandLine &, const FilePath &workingDirectory, + const Environment &) { Q_UNUSED(workingDirectory); QTC_CHECK(false); } virtual bool isCustomStart() const { return false; } virtual void terminate() = 0; virtual void kill() = 0; @@ -316,9 +316,9 @@ public: QByteArray readAllStandardOutput() override { QTC_CHECK(false); return {}; } QByteArray readAllStandardError() override { QTC_CHECK(false); return {}; } - void setProcessEnvironment(const QProcessEnvironment &environment) override { QTC_CHECK(false); } - void setWorkingDirectory(const QString &dir) override { QTC_CHECK(false); } - void start(const QString &program, const QStringList &arguments, const QByteArray &writeData) override + void setProcessEnvironment(const QProcessEnvironment &) override { QTC_CHECK(false); } + void setWorkingDirectory(const QString &) override { QTC_CHECK(false); } + void start(const QString &, const QStringList &, const QByteArray &) override { QTC_CHECK(false); } void customStart(const CommandLine &command, const FilePath &workingDirectory, const Environment &environment) override @@ -334,7 +334,7 @@ public: void terminate() override { m_terminal.stopProcess(); } void kill() override { m_terminal.stopProcess(); } void close() override { m_terminal.stopProcess(); } - qint64 write(const QByteArray &data) override { QTC_CHECK(false); return -1; } + qint64 write(const QByteArray &) override { QTC_CHECK(false); return -1; } void setStandardInputFile(const QString &fileName) override { Q_UNUSED(fileName) QTC_CHECK(false); } // intentionally no-op without an assert @@ -347,13 +347,13 @@ public: int exitCode() const override { return m_terminal.exitCode(); } QProcess::ExitStatus exitStatus() const override { return m_terminal.exitStatus(); } QString errorString() const override { return m_terminal.errorString(); } - void setErrorString(const QString &str) override { QTC_CHECK(false); } + void setErrorString(const QString &) override { QTC_CHECK(false); } // intentionally no-op without an assert - bool waitForStarted(int msecs) override { return false; } - bool waitForReadyRead(int msecs) override { QTC_CHECK(false); return false; } + bool waitForStarted(int) override { return false; } + bool waitForReadyRead(int) override { QTC_CHECK(false); return false; } // intentionally no-op without an assert - bool waitForFinished(int msecs) override { return false; } + bool waitForFinished(int) override { return false; } void kickoffProcess() override { m_terminal.kickoffProcess(); } void interruptProcess() override { m_terminal.interruptProcess(); } diff --git a/src/libs/utils/terminalprocess.cpp b/src/libs/utils/terminalprocess.cpp index 1f74153e9f6..a12107e1715 100644 --- a/src/libs/utils/terminalprocess.cpp +++ b/src/libs/utils/terminalprocess.cpp @@ -186,63 +186,6 @@ const CommandLine &TerminalProcess::commandLine() const return d->m_commandLine; } -static QString quoteWinCommand(const QString &program) -{ - const QChar doubleQuote = QLatin1Char('"'); - - // add the program as the first arg ... it works better - QString programName = program; - programName.replace(QLatin1Char('/'), QLatin1Char('\\')); - if (!programName.startsWith(doubleQuote) && !programName.endsWith(doubleQuote) - && programName.contains(QLatin1Char(' '))) { - programName.prepend(doubleQuote); - programName.append(doubleQuote); - } - return programName; -} - -static QString quoteWinArgument(const QString &arg) -{ - if (arg.isEmpty()) - return QString::fromLatin1("\"\""); - - QString ret(arg); - // Quotes are escaped and their preceding backslashes are doubled. - ret.replace(QRegularExpression("(\\\\*)\""), "\\1\\1\\\""); - if (ret.contains(QRegularExpression("\\s"))) { - // The argument must not end with a \ since this would be interpreted - // as escaping the quote -- rather put the \ behind the quote: e.g. - // rather use "foo"\ than "foo\" - int i = ret.length(); - while (i > 0 && ret.at(i - 1) == QLatin1Char('\\')) - --i; - ret.insert(i, QLatin1Char('"')); - ret.prepend(QLatin1Char('"')); - } - return ret; -} - -// Quote a Windows command line correctly for the "CreateProcess" API -static QString createWinCommandline(const QString &program, const QStringList &args) -{ - QString programName = quoteWinCommand(program); - for (const QString &arg : args) { - programName += QLatin1Char(' '); - programName += quoteWinArgument(arg); - } - return programName; -} - -static QString createWinCommandline(const QString &program, const QString &args) -{ - QString programName = quoteWinCommand(program); - if (!args.isEmpty()) { - programName += QLatin1Char(' '); - programName += args; - } - return programName; -} - void TerminalProcess::setAbortOnMetaChars(bool abort) { d->m_abortOnMetaChars = abort; @@ -334,15 +277,66 @@ void TerminalProcess::start() if (!workDir.isEmpty() && !workDir.endsWith(QLatin1Char('\\'))) workDir.append(QLatin1Char('\\')); + // Quote a Windows command line correctly for the "CreateProcess" API + static const auto quoteWinCommand = [](const QString &program) { + const QChar doubleQuote = QLatin1Char('"'); + + // add the program as the first arg ... it works better + QString programName = program; + programName.replace(QLatin1Char('/'), QLatin1Char('\\')); + if (!programName.startsWith(doubleQuote) && !programName.endsWith(doubleQuote) + && programName.contains(QLatin1Char(' '))) { + programName.prepend(doubleQuote); + programName.append(doubleQuote); + } + return programName; + }; + static const auto quoteWinArgument = [](const QString &arg) { + if (arg.isEmpty()) + return QString::fromLatin1("\"\""); + + QString ret(arg); + // Quotes are escaped and their preceding backslashes are doubled. + ret.replace(QRegularExpression("(\\\\*)\""), "\\1\\1\\\""); + if (ret.contains(QRegularExpression("\\s"))) { + // The argument must not end with a \ since this would be interpreted + // as escaping the quote -- rather put the \ behind the quote: e.g. + // rather use "foo"\ than "foo\" + int i = ret.length(); + while (i > 0 && ret.at(i - 1) == QLatin1Char('\\')) + --i; + ret.insert(i, QLatin1Char('"')); + ret.prepend(QLatin1Char('"')); + } + return ret; + }; + static const auto createWinCommandlineMultiArgs = [](const QString &program, const QStringList &args) { + QString programName = quoteWinCommand(program); + for (const QString &arg : args) { + programName += QLatin1Char(' '); + programName += quoteWinArgument(arg); + } + return programName; + }; + static const auto createWinCommandlineSingleArg = [](const QString &program, const QString &args) + { + QString programName = quoteWinCommand(program); + if (!args.isEmpty()) { + programName += QLatin1Char(' '); + programName += args; + } + return programName; + }; + QStringList stubArgs; stubArgs << modeOption(d->m_terminalMode) << d->m_stubServer.fullServerName() << workDir << (d->m_tempFile ? d->m_tempFile->fileName() : QString()) - << createWinCommandline(pcmd, pargs) + << createWinCommandlineSingleArg(pcmd, pargs) << msgPromptToClose(); - const QString cmdLine = createWinCommandline( + const QString cmdLine = createWinCommandlineMultiArgs( QCoreApplication::applicationDirPath() + QLatin1String("/qtcreator_process_stub.exe"), stubArgs); bool success = CreateProcessW(0, (WCHAR*)cmdLine.utf16(), diff --git a/src/plugins/coreplugin/fileutils.cpp b/src/plugins/coreplugin/fileutils.cpp index 538e2120f0c..004d661cafb 100644 --- a/src/plugins/coreplugin/fileutils.cpp +++ b/src/plugins/coreplugin/fileutils.cpp @@ -137,21 +137,6 @@ void FileUtils::showInFileSystemView(const FilePath &path) navWidget->syncWithFilePath(path); } -static QString quoteWinCommand(const QString &program) -{ - const QChar doubleQuote = QLatin1Char('"'); - - // add the program as the first arg ... it works better - QString programName = program; - programName.replace(QLatin1Char('/'), QLatin1Char('\\')); - if (!programName.startsWith(doubleQuote) && !programName.endsWith(doubleQuote) - && programName.contains(QLatin1Char(' '))) { - programName.prepend(doubleQuote); - programName.append(doubleQuote); - } - return programName; -} - static void startTerminalEmulator(const QString &workingDir, const Environment &env) { #ifdef Q_OS_WIN @@ -162,6 +147,19 @@ static void startTerminalEmulator(const QString &workingDir, const Environment & PROCESS_INFORMATION pinfo; ZeroMemory(&pinfo, sizeof(pinfo)); + static const auto quoteWinCommand = [](const QString &program) { + const QChar doubleQuote = QLatin1Char('"'); + + // add the program as the first arg ... it works better + QString programName = program; + programName.replace(QLatin1Char('/'), QLatin1Char('\\')); + if (!programName.startsWith(doubleQuote) && !programName.endsWith(doubleQuote) + && programName.contains(QLatin1Char(' '))) { + programName.prepend(doubleQuote); + programName.append(doubleQuote); + } + return programName; + }; const QString cmdLine = quoteWinCommand(QString::fromLocal8Bit(qgetenv("COMSPEC"))); // cmdLine is assumed to be detached - // https://blogs.msdn.microsoft.com/oldnewthing/20090601-00/?p=18083 diff --git a/src/plugins/projectexplorer/devicesupport/devicemanager.cpp b/src/plugins/projectexplorer/devicesupport/devicemanager.cpp index 32c6add09c1..256b93b6157 100644 --- a/src/plugins/projectexplorer/devicesupport/devicemanager.cpp +++ b/src/plugins/projectexplorer/devicesupport/devicemanager.cpp @@ -112,7 +112,7 @@ void DeviceManager::replaceInstance() const QList newIds = Utils::transform(DeviceManagerPrivate::clonedInstance->d->devices, &IDevice::id); - for (const IDevice::ConstPtr &dev : qAsConst(m_instance->d->devices)) { + for (const IDevice::Ptr &dev : qAsConst(m_instance->d->devices)) { if (!newIds.contains(dev->id())) dev->aboutToBeRemoved(); } @@ -144,7 +144,7 @@ DeviceManager *DeviceManager::cloneInstance() void DeviceManager::copy(const DeviceManager *source, DeviceManager *target, bool deep) { if (deep) { - for (const IDevice::ConstPtr &device : qAsConst(source->d->devices)) + for (const IDevice::Ptr &device : qAsConst(source->d->devices)) target->d->devices << device->clone(); } else { target->d->devices = source->d->devices; @@ -265,7 +265,7 @@ QVariantMap DeviceManager::toMap() const } map.insert(QLatin1String(DefaultDevicesKey), defaultDeviceMap); QVariantList deviceList; - for (const IDevice::ConstPtr &device : qAsConst(d->devices)) + for (const IDevice::Ptr &device : qAsConst(d->devices)) deviceList << device->toMap(); map.insert(QLatin1String(DeviceListKey), deviceList); return map; @@ -276,7 +276,7 @@ void DeviceManager::addDevice(const IDevice::ConstPtr &_device) const IDevice::Ptr device = _device->clone(); QStringList names; - for (const IDevice::ConstPtr &tmp : qAsConst(d->devices)) { + for (const IDevice::Ptr &tmp : qAsConst(d->devices)) { if (tmp->id() != device->id()) names << tmp->displayName(); } @@ -366,7 +366,7 @@ bool DeviceManager::isLoaded() const IDevice::ConstPtr DeviceManager::deviceForPath(const FilePath &path) { const QList devices = instance()->d->deviceList(); - for (const IDevice::ConstPtr &dev : devices) { + for (const IDevice::Ptr &dev : devices) { // TODO: ensure handlesFile is thread safe if (dev->handlesFile(path)) return dev; diff --git a/src/plugins/qmldesigner/components/edit3d/edit3dview.cpp b/src/plugins/qmldesigner/components/edit3d/edit3dview.cpp index 8070cacac02..386f6a1137f 100644 --- a/src/plugins/qmldesigner/components/edit3d/edit3dview.cpp +++ b/src/plugins/qmldesigner/components/edit3d/edit3dview.cpp @@ -92,6 +92,8 @@ Edit3DWidget *Edit3DView::edit3DWidget() const void Edit3DView::selectedNodesChanged(const QList &selectedNodeList, const QList &lastSelectedNodeList) { + Q_UNUSED(selectedNodeList) + Q_UNUSED(lastSelectedNodeList) SelectionContext selectionContext(this); selectionContext.setUpdateMode(SelectionContext::UpdateMode::Fast); if (m_alignCamerasAction) diff --git a/src/plugins/qmldesigner/designercore/model/texttomodelmerger.cpp b/src/plugins/qmldesigner/designercore/model/texttomodelmerger.cpp index 10c2a9cc10c..d9c369e3dd8 100644 --- a/src/plugins/qmldesigner/designercore/model/texttomodelmerger.cpp +++ b/src/plugins/qmldesigner/designercore/model/texttomodelmerger.cpp @@ -1348,7 +1348,7 @@ void TextToModelMerger::syncNode(ModelNode &modelNode, syncExpressionProperty(modelProperty, astValue, astType, differenceHandler); } modelPropertyNames.remove(astName.toUtf8()); - } else if (auto source = AST::cast(member)) { + } else if (AST::cast(member)) { // function et al } else { qWarning() << "Found an unknown QML value."; diff --git a/src/plugins/remotelinux/linuxdevice.cpp b/src/plugins/remotelinux/linuxdevice.cpp index 171f6d7421f..63f7e0ff72c 100644 --- a/src/plugins/remotelinux/linuxdevice.cpp +++ b/src/plugins/remotelinux/linuxdevice.cpp @@ -201,7 +201,7 @@ public: { delete m_shell; m_shell = nullptr; - DEBUG("Failed to connect to " << parameters.host()); + qCDebug(linuxDeviceLog) << "Failed to connect to" << parameters.host(); return false; } @@ -440,7 +440,7 @@ bool LinuxDevice::handlesFile(const FilePath &filePath) const return filePath.scheme() == "ssh" && filePath.host() == userAtHost(); } -void LinuxDevice::runProcess(QtcProcess &process) const +void LinuxDevice::runProcess(QtcProcess &) const { QTC_CHECK(false); // FIXME: Implement } diff --git a/src/plugins/remotelinux/linuxdevice.h b/src/plugins/remotelinux/linuxdevice.h index d2906b230c3..d914e8b223b 100644 --- a/src/plugins/remotelinux/linuxdevice.h +++ b/src/plugins/remotelinux/linuxdevice.h @@ -82,7 +82,7 @@ public: QByteArray fileContents(const Utils::FilePath &filePath, qint64 limit, qint64 offset) const override; bool writeFileContents(const Utils::FilePath &filePath, const QByteArray &data) const override; QDateTime lastModified(const Utils::FilePath &filePath) const override; - void runProcess(Utils::QtcProcess &process) const override; + void runProcess(Utils::QtcProcess &) const override; qint64 fileSize(const Utils::FilePath &filePath) const override; qint64 bytesAvailable(const Utils::FilePath &filePath) const override; QFileDevice::Permissions permissions(const Utils::FilePath &filePath) const override; From 5c1dc40b6c9d4d1024282c740a8208d181bfc7a3 Mon Sep 17 00:00:00 2001 From: Christian Kandeler Date: Thu, 27 Jan 2022 11:16:46 +0100 Subject: [PATCH 06/21] CppEditor: Switch on clangd by default Also change the corresponding settings key to force-enable it with existing settings. Fixes: QTCREATORBUG-22917 Change-Id: I3b5f54bf5d4261c6e4250245f44c4c360a911e5e Reviewed-by: Eike Ziller --- src/plugins/cppeditor/cppcodemodelsettings.cpp | 4 ++-- src/plugins/cppeditor/cppcodemodelsettings.h | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/plugins/cppeditor/cppcodemodelsettings.cpp b/src/plugins/cppeditor/cppcodemodelsettings.cpp index ef5c5fb10ab..9c7f995c064 100644 --- a/src/plugins/cppeditor/cppcodemodelsettings.cpp +++ b/src/plugins/cppeditor/cppcodemodelsettings.cpp @@ -72,7 +72,7 @@ static QString indexerFileSizeLimitKey() { return QLatin1String(Constants::CPPEDITOR_INDEXER_FILE_SIZE_LIMIT); } static QString clangdSettingsKey() { return QLatin1String("ClangdSettings"); } -static QString useClangdKey() { return QLatin1String("UseClangd"); } +static QString useClangdKey() { return QLatin1String("UseClangdV7"); } static QString clangdPathKey() { return QLatin1String("ClangdPath"); } static QString clangdIndexingKey() { return QLatin1String("ClangdIndexing"); } static QString clangdHeaderInsertionKey() { return QLatin1String("ClangdHeaderInsertion"); } @@ -485,7 +485,7 @@ QVariantMap ClangdSettings::Data::toMap() const void ClangdSettings::Data::fromMap(const QVariantMap &map) { - useClangd = map.value(useClangdKey(), false).toBool(); + useClangd = map.value(useClangdKey(), true).toBool(); executableFilePath = FilePath::fromString(map.value(clangdPathKey()).toString()); enableIndexing = map.value(clangdIndexingKey(), true).toBool(); autoIncludeHeaders = map.value(clangdHeaderInsertionKey(), false).toBool(); diff --git a/src/plugins/cppeditor/cppcodemodelsettings.h b/src/plugins/cppeditor/cppcodemodelsettings.h index fc7fd6ee61f..7550c011b2d 100644 --- a/src/plugins/cppeditor/cppcodemodelsettings.h +++ b/src/plugins/cppeditor/cppcodemodelsettings.h @@ -122,7 +122,7 @@ public: Utils::FilePath executableFilePath; QStringList sessionsWithOneClangd; int workerThreadLimit = 0; - bool useClangd = false; + bool useClangd = true; bool enableIndexing = true; bool autoIncludeHeaders = false; int documentUpdateThreshold = 500; From 95595db7d1ce1427d19bae4bafe11d8867ab3849 Mon Sep 17 00:00:00 2001 From: Christian Stenger Date: Thu, 27 Jan 2022 10:10:08 +0100 Subject: [PATCH 07/21] Docker: Drop handling of critical pattern again Drop lately introduced handling of critical pattern and just drop the critical pattern instead for now. Brings back gdb when auto detecting debuggers. Amends 22dd26bc76d and 181e74ebc35. Change-Id: Icde46e9bfa82d5cf1252e46f1e0a84b638927473 Reviewed-by: hjk --- src/plugins/docker/dockerdevice.cpp | 27 +++++++++------------------ 1 file changed, 9 insertions(+), 18 deletions(-) diff --git a/src/plugins/docker/dockerdevice.cpp b/src/plugins/docker/dockerdevice.cpp index e97d64e3964..1de6430b9cc 100644 --- a/src/plugins/docker/dockerdevice.cpp +++ b/src/plugins/docker/dockerdevice.cpp @@ -1502,17 +1502,19 @@ void DockerDevice::iterateWithFind(const FilePath &filePath, const QString nameOption = (filters & QDir::CaseSensitive) ? QString{"-name"} : QString{"-iname"}; - QStringList criticalWildcards; if (!filter.nameFilters.isEmpty()) { const QRegularExpression oneChar("\\[.*?\\]"); - for (int i = 0, len = filter.nameFilters.size(); i < len; ++i) { - if (i > 0) + bool addedFirst = false; + for (const QString ¤t : filter.nameFilters) { + if (current.indexOf(oneChar) != -1) { + LOG("Skipped" << current << "due to presence of [] wildcard"); + continue; + } + + if (addedFirst) filterOptions << "-o"; - QString current = filter.nameFilters.at(i); - if (current.indexOf(oneChar) != -1) - criticalWildcards.append(current); - current.replace(oneChar, "?"); // BAD! but still better than nothing filterOptions << nameOption << current; + addedFirst = true; } } arguments << filterOptions; @@ -1529,17 +1531,6 @@ void DockerDevice::iterateWithFind(const FilePath &filePath, continue; const FilePath fp = FilePath::fromString(entry); - if (!criticalWildcards.isEmpty() && - !Utils::anyOf(criticalWildcards, - [name = fp.fileName()](const QString &pattern) { - const QRegularExpression regex(QRegularExpression::wildcardToRegularExpression(pattern)); - if (regex.match(name).hasMatch()) - return true; - return false; - })) { - continue; - } - if (!callBack(fp.onDevice(filePath))) break; } From 8ace5d38950f18317bf3b021529a19e9ca838eb5 Mon Sep 17 00:00:00 2001 From: Leena Miettinen Date: Wed, 26 Jan 2022 18:42:39 +0100 Subject: [PATCH 08/21] Doc: Update info about ClangFormat options The options are now in a separate tab. Fixes: QTCREATORBUG-26597 Change-Id: If2d337c132f468897cd71e217205c3db29028f34 Reviewed-by: Christian Kandeler --- .../images/qtcreator-clang-format-options.png | Bin 27016 -> 0 bytes .../qtcreator-code-style-clang-format.png | Bin 22397 -> 23281 bytes ...qtcreator-code-style-settings-edit-cpp.png | Bin 23092 -> 18348 bytes .../src/editors/creator-clangformat.qdocinc | 16 +++++++++------- .../src/editors/creator-code-indentation.qdoc | 5 +---- .../creator-only/creator-clang-codemodel.qdoc | 4 ++-- 6 files changed, 12 insertions(+), 13 deletions(-) delete mode 100644 doc/qtcreator/images/qtcreator-clang-format-options.png diff --git a/doc/qtcreator/images/qtcreator-clang-format-options.png b/doc/qtcreator/images/qtcreator-clang-format-options.png deleted file mode 100644 index 57b151ea78bf1321ad362200cf46b5dd4c7933bc..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 27016 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 diff --git a/doc/qtcreator/images/qtcreator-code-style-clang-format.png b/doc/qtcreator/images/qtcreator-code-style-clang-format.png index 8ecce2a960879823b8c2626a952d2c7a28cd401a..5eea378da2115a0a754e21c7954ffdc67deee761 100644 GIT binary patch literal 23281 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 literal 22397 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 literal 23092 zcmeAS@N?(olHy`uVBq!ia0y~yU=CqmV5;C?Vqjo+D`onbfg$p@r;B4q#jUq{{}#tw zuU-B!ep}gp_G;&@s*Rc_6*wnvU=>>AVB#Revfj}v=VV)IbP$KrUfx3=d&*ZY-mt^% zV3yfa4X)f}0v4@BXQw)}i}Kps)bxpyQt^48P@XkMK|k1*)5iMTnUu0@?b)Zaf;SuQ zuiXFr@15=MZs$9E-+O+!-08c|=h=NDDjvtEkVDS_3iXhtYA4uGZo?s7F*YrmaL{GRkb^rVS^X(=6ExO`cb9+-<#6>|K8RAE&u=2p5v3lJhzkg zkG(m*=S*J9biV!HFVFw~XZd^HX#Q76SEMXYyzB6rH~VOA!s%SKTfHgTIjP4vK^}Y7 z@#L@h|F`wxANHR(wCw5o1N?ome-1wQwEyS7`G5ZIuiE=<>q+~ckKX?~`~Lrv_y50K znqT+T{QocczhCVC%eU_TG5^TVbN^3@pMSSUM!CMUMRkwKvVAY@=V|`^viJL>h+v^W zP)~HK0IzS@_>OqptJG`w#8v{~!FX`XODv^ViDz zwx*lb*5-Z>|M$rLf62S}`p5M@XWReSyT8_A`I2zp((F&-8|8yi zwqCm_>kf*L2|PdJi#~g+)X)F<@P_>V{q^6@+E=>EaZj)R^Xpyxua~{`#jhXU|NEK$ z|NHt|FXrsmcw5kB*nYqId}LN=@Uf22rz;mboa$I{%T_EaeywE2sfd-EI$xRXc^EW8q?{!V7!Yezv=CD7Ji=`(M?3f7p}! zPv7Hzp8o&k^7_9Q*W3KK-SSC1fIol5V(sl*4MxEY0s9}E;-TN^xJ}q<{li1EeiGf663x9#Z^{>K6!tt z`Fj2D^>sgP|Nqy1{{Q>=`RksaS2szt?tHD;^NQhj=7!{R6+$=n_!_qrgUbXW{JwDVT;N)?CR{Zn!+Fnli-S_`5 z-v9gZ=Kb^Qe;uCu{a@DK`ro(b^ZfhZ^Yr}tKR@qZKllINY4`s(Z#ndo)|m*Hn1@-~N4RfZo?n>GFS9->m=1umAUBxb*3G?!)`O zbsw4>$E-Z#Yx~sXH))S;m*0?O`I_IH7*J$2=a%@5UjZxso4yLUmsWnqyytcG(%l!# zS4o?{c`auG&Ui1wKWCr%FLZML>5E^D|Nr^_Q~duI`+o-?-nW#DQ2Fy}{(rYEdsx;5 zJ)hF5R-?gv_;2j1AI~;uZQ6O?pRwQl<ffH9ez~eG-p{3smm3q$oj!uoheRO@Wqp9^RkIUtCb+ zV+Iw29$`=3|M>V=rY)^F>)r01N7?89|L4xYz`*dkFXQCO?D9#c?i-)CX+C3`U3dQf zCHr4jHcoE$?~#*}VrF1qxZ&^DQ}^n|hnMk}{Lj|1|9tJ`vTnX*;jiH1cHgh4+p{t- zFl>0=@yE9KQDvaWll9sY&s|NQKl?#38v_Hw-sTgX8eE^QoBouxJKoO2z`#)D@vrT? z>eT(q=hsQi_iq35_i6l}Y`b3!3=AjaKehj1WME+UbUpN^_5W{&+w$l0pMGB0ofJ}b_WTDk^|vn;Y-@not+ZE4V=iiKIh&utHG{w;Ww>)q=$?441cXK`oEzTL6)zzv`0 zjxn1(pXe{D_HQ}!bz8#u`KvRQJ!#$ji)&YI#km(70?!t@B=_8?>9pB!tm7{GspKd8 z3=9lEvvum*`Q`I;>JtTnzMeMP>CkBtX3f;RoGWU%fR?J={LQUr{_SsD+ZrzWt}W#B zRrarDo3cNN%ZY?>>so&aE&l!UO=!n^%h-l{+0bAz{Ks4eAM$veJ2U4K%TOPcq$*`)m+xMxqW_x>$&ddYK;OLi&N2MXIMwb$nM7G3d{ z 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 diff --git a/doc/qtcreator/src/editors/creator-clangformat.qdocinc b/doc/qtcreator/src/editors/creator-clangformat.qdocinc index 9b7ef41d0ad..c7e3e370af9 100644 --- a/doc/qtcreator/src/editors/creator-clangformat.qdocinc +++ b/doc/qtcreator/src/editors/creator-clangformat.qdocinc @@ -1,6 +1,6 @@ /**************************************************************************** ** -** Copyright (C) 2020 The Qt Company Ltd. +** Copyright (C) 2022 The Qt Company Ltd. ** Contact: https://www.qt.io/licensing/ ** ** This file is part of the Qt Creator documentation. @@ -47,11 +47,14 @@ format file recursively from the directory that contains the source file up to the file system root. - To specify settings for automatic formatting and indentation: + To specify global settings for automatic formatting and indentation, you + must copy the built-in settings and edit the copy: \list 1 - \li Select \uicontrol Tools > \uicontrol Options > \uicontrol {C++}. - \image qtcreator-clang-format-options.png "C++ Clang Format options" + \li Select \uicontrol Tools > \uicontrol Options > \uicontrol {C++} > + \uicontrol Edit > \uicontrol {Copy Built-in Code Style} > + \uicontrol {ClangFormat}. + \image qtcreator-code-style-clang-format.png "C++ Clang Format options" \li Select the \uicontrol {Format instead of indenting} check box to use the \key {Ctrl+I} keyboard shortcut to format code instead of indenting it. @@ -72,11 +75,10 @@ To override the \c {.clang-format} file for a project, select \uicontrol Projects > \uicontrol {Project Settings} > - \uicontrol {Code Style} > + \uicontrol {Code Style} > \uicontrol Edit > + \uicontrol {Copy Built-in Code Style} > \uicontrol {ClangFormat} > \uicontrol {Override Clang Format configuration file}. - \image qtcreator-code-style-clang-format.png - You can create \c {.clang-format} files that contain the configuration options of a certain predefined style from the command line. For example, to create a format file for the LLVM style, enter the following command: diff --git a/doc/qtcreator/src/editors/creator-code-indentation.qdoc b/doc/qtcreator/src/editors/creator-code-indentation.qdoc index 09afcca6b5e..e9ef596caf7 100644 --- a/doc/qtcreator/src/editors/creator-code-indentation.qdoc +++ b/doc/qtcreator/src/editors/creator-code-indentation.qdoc @@ -1,6 +1,6 @@ /**************************************************************************** ** -** Copyright (C) 2021 The Qt Company Ltd. +** Copyright (C) 2022 The Qt Company Ltd. ** Contact: https://www.qt.io/licensing/ ** ** This file is part of the Qt Creator documentation. @@ -104,9 +104,6 @@ \list 1 \li Select \uicontrol Tools > \uicontrol Options > \uicontrol {C++}. - \note The settings displayed here depend on which plugins you have - enabled. If the Clang Format plugin is enabled, you'll see the - settings described in \l{Automatic Formatting and Indentation}. \li In the \uicontrol {Current settings} field, select the settings to modify and click \uicontrol Copy. \image qtcreator-options-code-style-cpp.png "C++ Code Style options" diff --git a/doc/qtcreator/src/editors/creator-only/creator-clang-codemodel.qdoc b/doc/qtcreator/src/editors/creator-only/creator-clang-codemodel.qdoc index 34f8cc28ba2..0480cdeed66 100644 --- a/doc/qtcreator/src/editors/creator-only/creator-clang-codemodel.qdoc +++ b/doc/qtcreator/src/editors/creator-only/creator-clang-codemodel.qdoc @@ -1,6 +1,6 @@ /**************************************************************************** ** -** Copyright (C) 2020 The Qt Company Ltd. +** Copyright (C) 2022 The Qt Company Ltd. ** Contact: https://www.qt.io/licensing/ ** ** This file is part of the Qt Creator documentation. @@ -176,7 +176,7 @@ \list 1 \li Select \uicontrol Tools > \uicontrol Options > \uicontrol C++ > - \uicontrol Clang > \uicontrol {Use clangd (EXPERIMENTAL)}. + \uicontrol Clangd > \uicontrol {Use clangd (EXPERIMENTAL)}. \image qtcreator-options-clangd.png "clangd options" \li In \uicontrol {Path to executable}, enter the path to clangd version 13, or later. From 707e7ba41fefeeaf6f42abfc338edc60cf93b3bc Mon Sep 17 00:00:00 2001 From: Orgad Shaneh Date: Thu, 27 Jan 2022 12:26:33 +0200 Subject: [PATCH 09/21] ClangFormat: Suppress warnings from llvm Change-Id: Id79abc3ea87576a681d86a7c1bd3be957acc299f Reviewed-by: Cristian Adam --- src/plugins/clangformat/CMakeLists.txt | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/plugins/clangformat/CMakeLists.txt b/src/plugins/clangformat/CMakeLists.txt index 49eeb53e342..5cc3f6c85ea 100644 --- a/src/plugins/clangformat/CMakeLists.txt +++ b/src/plugins/clangformat/CMakeLists.txt @@ -15,6 +15,10 @@ add_qtc_plugin(ClangFormat clangformatutils.cpp clangformatutils.h ) +if(MSVC AND TARGET ClangFormat) + target_compile_options(ClangFormat PUBLIC /wd4267 /wd4624) +endif() + extend_qtc_plugin(ClangFormat CONDITION UNIX AND NOT APPLE PROPERTIES LINK_FLAGS "-Wl,--exclude-libs,ALL" From 3869487a473b75d0b7c371e892844963fa1070fb Mon Sep 17 00:00:00 2001 From: Alexander Drozdov Date: Thu, 27 Jan 2022 14:13:48 +1000 Subject: [PATCH 10/21] Allow to build ClangFormat plugin with CLANGTOOLING_LINK_CLANG_DYLIB Some Linux distributives provides moders clang without separate libs compiled, like libClangTooling and so on. Just provide libclang.so and libclang-cpp.so. Qt Creator provides way to handle such clang installation by pointing flag CLANGTOOLING_LINK_CLANG_DYLIB=On for CMake. But ClangFormat still keeps from building. Fixed it. Change-Id: Id420f82c47c4205c8cd631aa04be6771628984be Reviewed-by: Eike Ziller --- src/plugins/clangformat/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/plugins/clangformat/CMakeLists.txt b/src/plugins/clangformat/CMakeLists.txt index 5cc3f6c85ea..dbeaed94888 100644 --- a/src/plugins/clangformat/CMakeLists.txt +++ b/src/plugins/clangformat/CMakeLists.txt @@ -1,5 +1,5 @@ add_qtc_plugin(ClangFormat - CONDITION TARGET libclang AND LLVM_PACKAGE_VERSION VERSION_GREATER_EQUAL 10.0.0 AND QTC_CLANG_BUILDMODE_MATCH + CONDITION TARGET libclang AND LLVM_PACKAGE_VERSION VERSION_GREATER_EQUAL 10.0.0 AND (QTC_CLANG_BUILDMODE_MATCH OR CLANGTOOLING_LINK_CLANG_DYLIB) DEPENDS Utils Qt5::Widgets ${CLANG_FORMAT_LIB} INCLUDES "${CLANG_INCLUDE_DIRS}" PLUGIN_DEPENDS Core TextEditor CppEditor ProjectExplorer From 5c1b4d2b48f204055dbe2dc0b2940a0a48576869 Mon Sep 17 00:00:00 2001 From: Christian Stenger Date: Thu, 27 Jan 2022 12:26:29 +0100 Subject: [PATCH 11/21] Debugger: Fix removing auto detected debuggers Do not remove items while iterating over the tree or we may crash when removing more than one. Change-Id: I007672be94a7e6449cf25c965c07ca714049ae97 Reviewed-by: hjk --- src/plugins/debugger/debuggeritemmanager.cpp | 18 +++++++++++------- 1 file changed, 11 insertions(+), 7 deletions(-) diff --git a/src/plugins/debugger/debuggeritemmanager.cpp b/src/plugins/debugger/debuggeritemmanager.cpp index fbe0aeb3fac..93b91c55591 100644 --- a/src/plugins/debugger/debuggeritemmanager.cpp +++ b/src/plugins/debugger/debuggeritemmanager.cpp @@ -1053,19 +1053,23 @@ void DebuggerItemManager::removeDetectedDebuggers(const QString &detectionSource QString *logMessage) { QStringList logMessages{tr("Removing debugger entries...")}; - d->m_model->forItemsAtLevel<2>([detectionSource, &logMessages](DebuggerTreeItem *titem) { + QList toBeRemoved; + + d->m_model->forItemsAtLevel<2>([detectionSource, &toBeRemoved](DebuggerTreeItem *titem) { if (titem->m_item.detectionSource() == detectionSource) { - logMessages.append(tr("Removed \"%1\"").arg(titem->m_item.displayName())); - d->m_model->destroyItem(titem); + toBeRemoved.append(titem); return; } // FIXME: These items appeared in early docker development. Ok to remove for Creator 7.0. FilePath filePath = titem->m_item.command(); - if (filePath.scheme() + ':' + filePath.host() == detectionSource) { - logMessages.append(tr("Removed \"%1\"").arg(titem->m_item.displayName())); - d->m_model->destroyItem(titem); - } + if (filePath.scheme() + ':' + filePath.host() == detectionSource) + toBeRemoved.append(titem); }); + for (DebuggerTreeItem *current : toBeRemoved) { + logMessages.append(tr("Removed \"%1\"").arg(current->m_item.displayName())); + d->m_model->destroyItem(current); + } + if (logMessage) *logMessage = logMessages.join('\n'); } From 5887d13d469f6fba952fb36a7aed7ec0d29f5de0 Mon Sep 17 00:00:00 2001 From: Christian Stenger Date: Thu, 27 Jan 2022 12:27:03 +0100 Subject: [PATCH 12/21] Docker: Fix crash while removing auto detected toolchains Change-Id: Id0cf4346b97f54247ad81ae0d93a42935dca8a0f Reviewed-by: hjk --- src/plugins/docker/dockerdevice.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/plugins/docker/dockerdevice.cpp b/src/plugins/docker/dockerdevice.cpp index 1de6430b9cc..a2284f50a81 100644 --- a/src/plugins/docker/dockerdevice.cpp +++ b/src/plugins/docker/dockerdevice.cpp @@ -628,9 +628,9 @@ void KitDetectorPrivate::undoAutoDetect() const }; emit q->logOutput('\n' + tr("Removing toolchain entries...")); - for (ToolChain *toolChain : ToolChainManager::toolchains()) { - QString detectionSource = toolChain->detectionSource(); - if (toolChain->detectionSource() == m_sharedId) { + const Toolchains toolchains = ToolChainManager::toolchains(); + for (ToolChain *toolChain : toolchains) { + if (toolChain && toolChain->detectionSource() == m_sharedId) { emit q->logOutput(tr("Removed \"%1\"").arg(toolChain->displayName())); ToolChainManager::deregisterToolChain(toolChain); } From 94a17f1e7ec41c5e7bd007d118e44f34087c3ec0 Mon Sep 17 00:00:00 2001 From: Miikka Heikkinen Date: Mon, 24 Jan 2022 15:23:34 +0200 Subject: [PATCH 13/21] QmlDesigner: Fix 3D picking of RuntimeLoader loaded models RuntimeLoader creates the loaded nodes dynamically, similar to Repeater3D and Loader3D, so handle it similarly as well. Fixes: QDS-6053 Change-Id: Iece15254e720cfc0a6796b182ef00c3a773cf35d Reviewed-by: Thomas Hartmann --- .../qmlpuppet/qml2puppet/instances/instances.pri | 4 ++++ .../instances/qt5informationnodeinstanceserver.cpp | 13 +++++++++++++ .../qml2puppet/instances/quick3dnodeinstance.cpp | 13 +++++++++++++ src/tools/qml2puppet/CMakeLists.txt | 9 +++++++++ 4 files changed, 39 insertions(+) diff --git a/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/instances.pri b/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/instances.pri index 59ac62420c9..d3a81cc3705 100644 --- a/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/instances.pri +++ b/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/instances.pri @@ -13,6 +13,10 @@ versionAtLeast(QT_VERSION, 5.15.0) { QT *= quick3dparticles-private DEFINES *= QUICK3D_PARTICLES_MODULE } + qtHaveModule(quick3dassetutils) { + QT *= quick3dassetutils-private + DEFINES *= QUICK3D_ASSET_UTILS_MODULE + } } HEADERS += $$PWD/qt5nodeinstanceserver.h \ diff --git a/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/qt5informationnodeinstanceserver.cpp b/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/qt5informationnodeinstanceserver.cpp index d74bdacf5da..b2a84ff53f3 100644 --- a/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/qt5informationnodeinstanceserver.cpp +++ b/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/qt5informationnodeinstanceserver.cpp @@ -104,6 +104,9 @@ #if QT_VERSION >= QT_VERSION_CHECK(6, 0, 0) #include "../editor3d/qt5compat/qquick3darealight_p.h" #endif +#if defined(QUICK3D_ASSET_UTILS_MODULE) && QT_VERSION > QT_VERSION_CHECK(6, 2, 0) +#include +#endif #endif #ifdef QUICK3D_PARTICLES_MODULE @@ -2317,13 +2320,23 @@ void Qt5InformationNodeInstanceServer::handleInstanceHidden(const ServerNodeInst } else { auto checkRepeater = qobject_cast(checkNode); auto checkLoader = qobject_cast(checkNode); +#if defined(QUICK3D_ASSET_UTILS_MODULE) && QT_VERSION > QT_VERSION_CHECK(6, 2, 0) + auto checkRunLoader = qobject_cast(checkNode); + if (checkRepeater || checkLoader || checkRunLoader) { +#else if (checkRepeater || checkLoader) { +#endif // Repeaters/loaders may not yet have created their children, so we set // _pickTarget on them and connect the notifier. if (checkNode->property("_pickTarget").isNull()) { if (checkRepeater) { QObject::connect(checkRepeater, &QQuick3DRepeater::objectAdded, this, &Qt5InformationNodeInstanceServer::handleDynamicAddObject); +#if defined(QUICK3D_ASSET_UTILS_MODULE) && QT_VERSION > QT_VERSION_CHECK(6, 2, 0) + } else if (checkRunLoader) { + QObject::connect(checkRunLoader, &QQuick3DRuntimeLoader::statusChanged, + this, &Qt5InformationNodeInstanceServer::handleDynamicAddObject); +#endif } else { QObject::connect(checkLoader, &QQuick3DLoader::loaded, this, &Qt5InformationNodeInstanceServer::handleDynamicAddObject); diff --git a/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/quick3dnodeinstance.cpp b/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/quick3dnodeinstance.cpp index 734eeee470e..980da0da791 100644 --- a/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/quick3dnodeinstance.cpp +++ b/share/qtcreator/qml/qmlpuppet/qml2puppet/instances/quick3dnodeinstance.cpp @@ -42,6 +42,9 @@ #include #include #include +#if defined(QUICK3D_ASSET_UTILS_MODULE) && QT_VERSION > QT_VERSION_CHECK(6, 2, 0) +#include +#endif #endif namespace QmlDesigner { @@ -63,11 +66,21 @@ void Quick3DNodeInstance::initialize(const ObjectNodeInstance::Pointer &objectNo QObject *obj = object(); auto repObj = qobject_cast(obj); auto loadObj = qobject_cast(obj); +#if defined(QUICK3D_ASSET_UTILS_MODULE) && QT_VERSION > QT_VERSION_CHECK(6, 2, 0) + auto runLoadObj = qobject_cast(obj); + if (repObj || loadObj || runLoadObj) { +#else if (repObj || loadObj) { +#endif if (auto infoServer = qobject_cast(nodeInstanceServer())) { if (repObj) { QObject::connect(repObj, &QQuick3DRepeater::objectAdded, infoServer, &Qt5InformationNodeInstanceServer::handleDynamicAddObject); +#if defined(QUICK3D_ASSET_UTILS_MODULE) && QT_VERSION > QT_VERSION_CHECK(6, 2, 0) + } else if (runLoadObj) { + QObject::connect(runLoadObj, &QQuick3DRuntimeLoader::statusChanged, + infoServer, &Qt5InformationNodeInstanceServer::handleDynamicAddObject); +#endif } else { QObject::connect(loadObj, &QQuick3DLoader::loaded, infoServer, &Qt5InformationNodeInstanceServer::handleDynamicAddObject); diff --git a/src/tools/qml2puppet/CMakeLists.txt b/src/tools/qml2puppet/CMakeLists.txt index 4a642acbd9a..86d9894edaf 100644 --- a/src/tools/qml2puppet/CMakeLists.txt +++ b/src/tools/qml2puppet/CMakeLists.txt @@ -178,6 +178,15 @@ extend_qtc_executable(qml2puppet DEFINES QUICK3D_PARTICLES_MODULE ) +# Quick3DAssetUtils optionally depends on QuickTimeline, so find also it to make the CI build work +find_package(Qt5 5.15.0 COMPONENTS Quick3DAssetUtils QuickTimeline QUIET) +extend_qtc_executable(qml2puppet + CONDITION TARGET Qt5::Quick3DAssetUtils + FEATURE_INFO "Qt Quick 3D asset utils" + DEPENDS Qt5::Quick3DAssetUtilsPrivate + DEFINES QUICK3D_ASSET_UTILS_MODULE +) + extend_qtc_executable(qml2puppet CONDITION Qt5_VERSION VERSION_GREATER_EQUAL 6.0.0 From 161d25571bbc94b43e923c02da43d683321cb3aa Mon Sep 17 00:00:00 2001 From: Miikka Heikkinen Date: Wed, 26 Jan 2022 17:11:27 +0200 Subject: [PATCH 14/21] QmlDesigner: Change camera id in 3D app template Id "camera" conflicts with property name on View3D. Task-number: QDS-6081 Change-Id: If6a06a9aff75620fc657a8285ac6b2b2a1e8ebc0 Reviewed-by: Reviewed-by: Thomas Hartmann --- .../projects/application-3d/Screen01.ui.qml.tpl | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/share/qtcreator/qmldesigner/studio_templates/projects/application-3d/Screen01.ui.qml.tpl b/share/qtcreator/qmldesigner/studio_templates/projects/application-3d/Screen01.ui.qml.tpl index bc30dce33c4..730906111be 100644 --- a/share/qtcreator/qmldesigner/studio_templates/projects/application-3d/Screen01.ui.qml.tpl +++ b/share/qtcreator/qmldesigner/studio_templates/projects/application-3d/Screen01.ui.qml.tpl @@ -34,7 +34,7 @@ Rectangle { } PerspectiveCamera { - id: camera + id: sceneCamera z: 350 } From 5c53dc5e13396a8e105d77a7110f4fd5978f28e1 Mon Sep 17 00:00:00 2001 From: Alexander Drozdov Date: Thu, 27 Jan 2022 20:14:17 +1000 Subject: [PATCH 15/21] Ssh: fix crash on freed memory access At the cleanup() method we must remove connection from the m_connection list to avoid access to the freed memory from the removeInactiveConnections() that caused Qt Creator crash. Change-Id: I8195f05e903819e3e3b48b2f72fd71047c5a1636 Reviewed-by: Jarek Kobus Reviewed-by: hjk Reviewed-by: --- src/libs/ssh/sshconnectionmanager.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/libs/ssh/sshconnectionmanager.cpp b/src/libs/ssh/sshconnectionmanager.cpp index fff3db499ea..800c4f14f19 100644 --- a/src/libs/ssh/sshconnectionmanager.cpp +++ b/src/libs/ssh/sshconnectionmanager.cpp @@ -151,6 +151,7 @@ private: disconnect(connection, nullptr, this, nullptr); connection->deleteLater(); + m_connections.erase(it); } void removeInactiveConnections() From 1d15a934cde9569835ff6a9470b8dd4e2276637d Mon Sep 17 00:00:00 2001 From: Jarek Kobus Date: Fri, 28 Jan 2022 12:08:09 +0100 Subject: [PATCH 16/21] QtcProcess: Get rid of useTerminal Remove SshRemoteProcessRunner::runInTerminal() method, it wasn't used anywhere (just in test). Remove QtcProcess::useTerminal, as process should be created in TerminalOn mode when there is a need for terminal. Add a parameter to SshRemoteProcess::fullLocalCommandLine(bool inTerminal) as this may still be needed when running application through ssh from terminal (ssh -tt option). Change-Id: I71911082fcca190b82a1106a2ca1ca48dc5d4c79 Reviewed-by: hjk (cherry picked from commit 95a9b22f6fe07f8417ad94722d456d4a5730f068) --- src/libs/ssh/sshremoteprocess.cpp | 4 ++-- src/libs/ssh/sshremoteprocess.h | 2 +- src/libs/ssh/sshremoteprocessrunner.cpp | 10 ---------- src/libs/ssh/sshremoteprocessrunner.h | 1 - src/libs/utils/qtcprocess.cpp | 14 -------------- src/libs/utils/qtcprocess.h | 3 --- .../devicesupport/sshdeviceprocess.cpp | 3 +-- tests/auto/ssh/tst_ssh.cpp | 18 ++++-------------- 8 files changed, 8 insertions(+), 47 deletions(-) diff --git a/src/libs/ssh/sshremoteprocess.cpp b/src/libs/ssh/sshremoteprocess.cpp index 9b748c153a4..bbfec939eba 100644 --- a/src/libs/ssh/sshremoteprocess.cpp +++ b/src/libs/ssh/sshremoteprocess.cpp @@ -89,13 +89,13 @@ void SshRemoteProcess::requestX11Forwarding(const QString &displayName) m_displayName = displayName; } -Utils::CommandLine SshRemoteProcess::fullLocalCommandLine() const +Utils::CommandLine SshRemoteProcess::fullLocalCommandLine(bool inTerminal) const { Utils::CommandLine cmd{SshSettings::sshFilePath()}; if (!m_displayName.isEmpty()) cmd.addArg("-X"); - if (useTerminal()) + if (inTerminal) cmd.addArg("-tt"); cmd.addArg("-q"); diff --git a/src/libs/ssh/sshremoteprocess.h b/src/libs/ssh/sshremoteprocess.h index f8f9bef343b..b5195454b50 100644 --- a/src/libs/ssh/sshremoteprocess.h +++ b/src/libs/ssh/sshremoteprocess.h @@ -43,7 +43,7 @@ public: void requestX11Forwarding(const QString &displayName); void start(); - Utils::CommandLine fullLocalCommandLine() const; + Utils::CommandLine fullLocalCommandLine(bool inTerminal = false) const; signals: void done(const QString &error); diff --git a/src/libs/ssh/sshremoteprocessrunner.cpp b/src/libs/ssh/sshremoteprocessrunner.cpp index 54f40109d95..2d34ab4eae3 100644 --- a/src/libs/ssh/sshremoteprocessrunner.cpp +++ b/src/libs/ssh/sshremoteprocessrunner.cpp @@ -49,7 +49,6 @@ public: SshRemoteProcessPtr m_process; SshConnection *m_connection; - bool m_runInTerminal; QString m_command; QString m_lastConnectionErrorString; QProcess::ExitStatus m_exitStatus; @@ -80,14 +79,6 @@ void SshRemoteProcessRunner::run(const QString &command, const SshConnectionPara { QTC_ASSERT(d->m_state == Inactive, return); - d->m_runInTerminal = false; - runInternal(command, sshParams); -} - -void SshRemoteProcessRunner::runInTerminal(const QString &command, - const SshConnectionParameters &sshParams) -{ - d->m_runInTerminal = true; runInternal(command, sshParams); } @@ -128,7 +119,6 @@ void SshRemoteProcessRunner::handleConnected() this, &SshRemoteProcessRunner::handleStdout); connect(d->m_process.get(), &SshRemoteProcess::readyReadStandardError, this, &SshRemoteProcessRunner::handleStderr); - d->m_process->setUseTerminal(d->m_runInTerminal); d->m_process->start(); } diff --git a/src/libs/ssh/sshremoteprocessrunner.h b/src/libs/ssh/sshremoteprocessrunner.h index 6ad2ac6205a..22ed6613fbf 100644 --- a/src/libs/ssh/sshremoteprocessrunner.h +++ b/src/libs/ssh/sshremoteprocessrunner.h @@ -40,7 +40,6 @@ public: ~SshRemoteProcessRunner(); void run(const QString &command, const SshConnectionParameters &sshParams); - void runInTerminal(const QString &command, const SshConnectionParameters &sshParams); QString command() const; QString lastConnectionErrorString() const; diff --git a/src/libs/utils/qtcprocess.cpp b/src/libs/utils/qtcprocess.cpp index dac6947b040..74fd21f2a85 100644 --- a/src/libs/utils/qtcprocess.cpp +++ b/src/libs/utils/qtcprocess.cpp @@ -260,9 +260,6 @@ public: void setUnixTerminalDisabled() { m_unixTerminalDisabled = true; } bool isUnixTerminalDisabled() const { return m_unixTerminalDisabled; } - void setUseTerminal(bool on) { m_useTerminal = on; } - bool useTerminal() const { return m_useTerminal; } - void setAbortOnMetaChars(bool abort) { m_abortOnMetaChars = abort; } bool isAbortOnMetaChars() const { return m_abortOnMetaChars; } @@ -289,7 +286,6 @@ private: QString m_nativeArguments; bool m_lowPriority = false; bool m_unixTerminalDisabled = false; - bool m_useTerminal = false; bool m_abortOnMetaChars = true; bool m_runAsRoot = false; }; @@ -908,16 +904,6 @@ void QtcProcess::setDisableUnixTerminal() d->m_process->setUnixTerminalDisabled(); } -void QtcProcess::setUseTerminal(bool on) -{ - d->m_process->setUseTerminal(on); -} - -bool QtcProcess::useTerminal() const -{ - return d->m_process->useTerminal(); -} - void QtcProcess::setAbortOnMetaChars(bool abort) { d->m_process->setAbortOnMetaChars(abort); diff --git a/src/libs/utils/qtcprocess.h b/src/libs/utils/qtcprocess.h index d743f7a4373..57783e38ade 100644 --- a/src/libs/utils/qtcprocess.h +++ b/src/libs/utils/qtcprocess.h @@ -115,9 +115,6 @@ public: void setDisableUnixTerminal(); void setRunAsRoot(bool on); - void setUseTerminal(bool on); - bool useTerminal() const; - void setAbortOnMetaChars(bool abort); void start(); diff --git a/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp b/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp index 71d7b14cd71..6456cdacfb3 100644 --- a/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp +++ b/src/plugins/projectexplorer/devicesupport/sshdeviceprocess.cpp @@ -192,7 +192,6 @@ void SshDeviceProcess::handleConnected() if (!display.isEmpty()) d->process->requestX11Forwarding(display); if (runInTerminal()) { - d->process->setUseTerminal(true); connect(&d->consoleProcess, &QtcProcess::errorOccurred, this, &DeviceProcess::errorOccurred); connect(&d->consoleProcess, &QtcProcess::started, @@ -200,7 +199,7 @@ void SshDeviceProcess::handleConnected() connect(&d->consoleProcess, &QtcProcess::finished, this, [this] { handleProcessFinished(d->consoleProcess.errorString()); }); d->consoleProcess.setAbortOnMetaChars(false); - d->consoleProcess.setCommand(d->process->fullLocalCommandLine()); + d->consoleProcess.setCommand(d->process->fullLocalCommandLine(true)); d->consoleProcess.start(); } else { connect(d->process.get(), &QSsh::SshRemoteProcess::started, diff --git a/tests/auto/ssh/tst_ssh.cpp b/tests/auto/ssh/tst_ssh.cpp index 0203d638f86..2c237bfbfa9 100644 --- a/tests/auto/ssh/tst_ssh.cpp +++ b/tests/auto/ssh/tst_ssh.cpp @@ -216,20 +216,14 @@ void tst_Ssh::pristineConnectionObject() void tst_Ssh::remoteProcess_data() { QTest::addColumn("commandLine"); - QTest::addColumn("useTerminal"); QTest::addColumn("isBlocking"); QTest::addColumn("successExpected"); QTest::addColumn("stdoutExpected"); QTest::addColumn("stderrExpected"); - QTest::newRow("normal command") - << QByteArray("ls -a /tmp") << false << false << true << true << false; - QTest::newRow("failing command") - << QByteArray("top -n 1") << false << false << false << false << true; - QTest::newRow("blocking command") - << QByteArray("/bin/sleep 100") << false << true << false << false << false; - QTest::newRow("terminal command") - << QByteArray("top -n 1") << true << false << true << true << false; + QTest::newRow("normal cmd") << QByteArray("ls -a /tmp") << false << true << true << false; + QTest::newRow("failing cmd") << QByteArray("top -n 1") << false << false << false << true; + QTest::newRow("blocking cmd") << QByteArray("sleep 100") << true << false << false << false; } void tst_Ssh::remoteProcess() @@ -238,7 +232,6 @@ void tst_Ssh::remoteProcess() CHECK_PARAMS(params); QFETCH(QByteArray, commandLine); - QFETCH(bool, useTerminal); QFETCH(bool, isBlocking); QFETCH(bool, successExpected); QFETCH(bool, stdoutExpected); @@ -255,10 +248,7 @@ void tst_Ssh::remoteProcess() [&remoteStdout, &runner] { remoteStdout += runner.readAllStandardOutput(); }); connect(&runner, &SshRemoteProcessRunner::readyReadStandardError, [&remoteStderr, &runner] { remoteStderr += runner.readAllStandardError(); }); - if (useTerminal) - runner.runInTerminal(QString::fromUtf8(commandLine), params); - else - runner.run(QString::fromUtf8(commandLine), params); + runner.run(QString::fromUtf8(commandLine), params); QTimer timer; QObject::connect(&timer, &QTimer::timeout, &loop, &QEventLoop::quit); timer.setSingleShot(true); From 3769169b8ee8d0875ed6b08978b63213e8310c01 Mon Sep 17 00:00:00 2001 From: hjk Date: Thu, 27 Jan 2022 17:00:01 +0100 Subject: [PATCH 17/21] Utils: Introduce a struct for QtcProcess ctor arguments We'll need a lot of combinations. Change-Id: Ic92ad6fba1d96c42571be76f7c24b253f210b132 Reviewed-by: Jarek Kobus Reviewed-by: Qt CI Bot --- src/libs/utils/qtcprocess.cpp | 20 +++++++------------- src/libs/utils/qtcprocess.h | 22 +++++++++++++++------- 2 files changed, 22 insertions(+), 20 deletions(-) diff --git a/src/libs/utils/qtcprocess.cpp b/src/libs/utils/qtcprocess.cpp index 74fd21f2a85..04561a5af8b 100644 --- a/src/libs/utils/qtcprocess.cpp +++ b/src/libs/utils/qtcprocess.cpp @@ -748,9 +748,11 @@ static QtcProcess::ProcessImpl defaultProcessImpl() return QtcProcess::ProcessLauncherImpl; } -QtcProcess::QtcProcess(ProcessImpl processImpl, ProcessMode processMode, TerminalMode terminalMode, - QObject *parent) - : QObject(parent), d(new QtcProcessPrivate(this, processImpl, processMode, terminalMode)) +QtcProcess::QtcProcess(const Setup &setup, QObject *parent) + : QObject(parent), + d(new QtcProcessPrivate(this, + setup.processImpl == DefaultImpl ? defaultProcessImpl() : setup.processImpl, + setup.processMode, setup.terminalMode)) { static int qProcessExitStatusMeta = qRegisterMetaType(); static int qProcessProcessErrorMeta = qRegisterMetaType(); @@ -758,17 +760,9 @@ QtcProcess::QtcProcess(ProcessImpl processImpl, ProcessMode processMode, Termina Q_UNUSED(qProcessProcessErrorMeta) } -QtcProcess::QtcProcess(ProcessImpl processImpl, QObject *parent) - : QtcProcess(processImpl, ProcessMode::Reader, TerminalMode::TerminalOff, parent) {} - -QtcProcess::QtcProcess(ProcessMode processMode, QObject *parent) - : QtcProcess(defaultProcessImpl(), processMode, TerminalMode::TerminalOff, parent) {} - -QtcProcess::QtcProcess(TerminalMode terminalMode, QObject *parent) - : QtcProcess(defaultProcessImpl(), ProcessMode::Reader, terminalMode, parent) {} - QtcProcess::QtcProcess(QObject *parent) - : QtcProcess(defaultProcessImpl(), ProcessMode::Reader, TerminalMode::TerminalOff, parent) {} + : QtcProcess({}, parent) +{} QtcProcess::~QtcProcess() { diff --git a/src/libs/utils/qtcprocess.h b/src/libs/utils/qtcprocess.h index 57783e38ade..592830041e1 100644 --- a/src/libs/utils/qtcprocess.h +++ b/src/libs/utils/qtcprocess.h @@ -62,7 +62,8 @@ class QTCREATOR_UTILS_EXPORT QtcProcess : public QObject public: enum ProcessImpl { QProcessImpl, - ProcessLauncherImpl + ProcessLauncherImpl, + DefaultImpl, }; enum TerminalMode { @@ -73,12 +74,19 @@ public: TerminalOn = TerminalRun // default mode for ON }; - QtcProcess(ProcessImpl processImpl, ProcessMode processMode, TerminalMode terminalMode, - QObject *parent = nullptr); - QtcProcess(ProcessImpl processImpl, QObject *parent = nullptr); - QtcProcess(ProcessMode processMode, QObject *parent = nullptr); - QtcProcess(TerminalMode terminalMode, QObject *parent = nullptr); - QtcProcess(QObject *parent = nullptr); + struct Setup { + Setup() {} + Setup(ProcessImpl processImpl) : processImpl(processImpl) {} + Setup(ProcessMode processMode) : processMode(processMode) {} + Setup(TerminalMode terminalMode) : terminalMode(terminalMode) {} + + ProcessImpl processImpl = DefaultImpl; + ProcessMode processMode = ProcessMode::Reader; + TerminalMode terminalMode = TerminalOff; + }; + + QtcProcess(const Setup &setup = {}, QObject *parent = nullptr); + QtcProcess(QObject *parent); ~QtcProcess(); ProcessMode processMode() const; From dd527a389027e65881909ab75f2fd3f662b8b71a Mon Sep 17 00:00:00 2001 From: Jarek Kobus Date: Fri, 28 Jan 2022 12:33:50 +0100 Subject: [PATCH 18/21] SshRemoteProcessRunner: Remove unused command() method Change-Id: If45ea80b892cb683aa3737dd73244fa4b669abc4 Reviewed-by: hjk --- src/libs/ssh/sshremoteprocessrunner.cpp | 1 - src/libs/ssh/sshremoteprocessrunner.h | 1 - 2 files changed, 2 deletions(-) diff --git a/src/libs/ssh/sshremoteprocessrunner.cpp b/src/libs/ssh/sshremoteprocessrunner.cpp index 2d34ab4eae3..edbc7219b17 100644 --- a/src/libs/ssh/sshremoteprocessrunner.cpp +++ b/src/libs/ssh/sshremoteprocessrunner.cpp @@ -185,7 +185,6 @@ void SshRemoteProcessRunner::setState(int newState) } } -QString SshRemoteProcessRunner::command() const { return d->m_command; } QString SshRemoteProcessRunner::lastConnectionErrorString() const { return d->m_lastConnectionErrorString; } diff --git a/src/libs/ssh/sshremoteprocessrunner.h b/src/libs/ssh/sshremoteprocessrunner.h index 22ed6613fbf..5cb188b2e68 100644 --- a/src/libs/ssh/sshremoteprocessrunner.h +++ b/src/libs/ssh/sshremoteprocessrunner.h @@ -40,7 +40,6 @@ public: ~SshRemoteProcessRunner(); void run(const QString &command, const SshConnectionParameters &sshParams); - QString command() const; QString lastConnectionErrorString() const; From abe09bfd763b4e37aa8d76884412a755ef7be5dd Mon Sep 17 00:00:00 2001 From: Christian Kandeler Date: Wed, 26 Jan 2022 12:40:12 +0100 Subject: [PATCH 19/21] ClangCodeModel: Adjust cursor for following destructor symbols ... with clangd. More specifically, for the case where we switch between declaration and definition of a destructor. Since clangd expects the cursor before the "~" character, we move it there. Fixes: QTCREATORBUG-26809 Change-Id: I8ea6a060bea3545c963cb8ebbe2d3ae3a18da2d5 Reviewed-by: Reviewed-by: Christian Stenger --- src/plugins/clangcodemodel/clangdclient.cpp | 7 +++++++ .../cppeditor/followsymbol_switchmethoddecldef_test.cpp | 8 ++++---- 2 files changed, 11 insertions(+), 4 deletions(-) diff --git a/src/plugins/clangcodemodel/clangdclient.cpp b/src/plugins/clangcodemodel/clangdclient.cpp index 7ce3cc243ff..78d3793b502 100644 --- a/src/plugins/clangcodemodel/clangdclient.cpp +++ b/src/plugins/clangcodemodel/clangdclient.cpp @@ -2458,6 +2458,13 @@ QTextCursor ClangdClient::Private::adjustedCursor(const QTextCursor &cursor, } return cursor; } + + // ~My|Class + if (const DestructorNameAST * const destrAst = (*it)->asDestructorName()) { + QTextCursor c = cursor; + c.setPosition(posForToken(destrAst->tilde_token)); + return c; + } } return cursor; } diff --git a/src/plugins/cppeditor/followsymbol_switchmethoddecldef_test.cpp b/src/plugins/cppeditor/followsymbol_switchmethoddecldef_test.cpp index 8cfff10c658..81b410a3cda 100644 --- a/src/plugins/cppeditor/followsymbol_switchmethoddecldef_test.cpp +++ b/src/plugins/cppeditor/followsymbol_switchmethoddecldef_test.cpp @@ -263,10 +263,6 @@ F2TestCase::F2TestCase(CppEditorAction action, QSKIP("fuzzy matching is not supposed to work with clangd"); // TODO: Implement fallback as we do with libclang if (tag == "baseClassFunctionIntroducedByUsingDeclaration") QSKIP("clangd points to the using declaration"); - if (tag == "classDestructor" || tag == "fromDestructorDefinitionSymbol" - || tag == "fromDestructorBody") { - QSKIP("clangd wants the cursor before the ~ character"); - } if (curTestName == "testFollowClassOperatorInOp") QSKIP("clangd goes to operator name first"); } @@ -438,6 +434,10 @@ F2TestCase::F2TestCase(CppEditorAction action, } else { currentTextEditor->convertPosition(targetTestFile->m_targetCursorPosition, &expectedLine, &expectedColumn); + if (useClangd && (tag == "classDestructor" || tag == "fromDestructorDefinitionSymbol" + || tag == "fromDestructorBody")) { + --expectedColumn; // clangd goes before the ~, built-in code model after + } } // qDebug() << "Expected line:" << expectedLine; // qDebug() << "Expected column:" << expectedColumn; From 9e2554b660567d61ee742b2e26234b22eab7c425 Mon Sep 17 00:00:00 2001 From: Alessandro Portale Date: Mon, 20 Dec 2021 00:09:00 +0100 Subject: [PATCH 20/21] Use Utils::Archive instead of java's jar in AndroidSdkDownloader The exctraction of the downloaded commandlinetools zip file via java's jar tool did suddenly not work anymore on Windows. The exit code of jarExtractProc in AndroidSdkDownloader::extractSdk would be != 0. Instead of fixing the jar usage, this change replaces it with the recently added Utils::Archive. That has the advantage that it preserves the file permissions while exctracting, so that we can also get rid of setSdkFilesExecPermission. Another advantage is that the SDK can be extracted even before a jdk has been selected. Change-Id: I99cc2aff8e183108eb11dbf96f06557e5b299d56 Reviewed-by: hjk Reviewed-by: Assam Boudjelthia --- src/plugins/android/androidsdkdownloader.cpp | 64 +++++-------------- src/plugins/android/androidsdkdownloader.h | 5 +- src/plugins/android/androidsettingswidget.cpp | 10 +-- 3 files changed, 19 insertions(+), 60 deletions(-) diff --git a/src/plugins/android/androidsdkdownloader.cpp b/src/plugins/android/androidsdkdownloader.cpp index 28837ca8d4e..c9512b464a9 100644 --- a/src/plugins/android/androidsdkdownloader.cpp +++ b/src/plugins/android/androidsdkdownloader.cpp @@ -24,13 +24,13 @@ ****************************************************************************/ #include "androidsdkdownloader.h" -#include "utils/filepath.h" -#include "utils/qtcprocess.h" + +#include +#include + #include #include -#include -#include #include #include @@ -61,22 +61,7 @@ void AndroidSdkDownloader::sslErrors(const QList &sslErrors) } #endif -static void setSdkFilesExecPermission( const FilePath &sdkExtractPath) -{ - const FilePath filePath = sdkExtractPath / "tools"; - - filePath.iterateDirectory( - [](const FilePath &filePath) { - if (!filePath.fileName().contains('.')) { - QFlags currentPermissions = filePath.permissions(); - filePath.setPermissions(currentPermissions | QFileDevice::ExeOwner); - } - return true; - }, - {{"*"}, QDir::Files, QDirIterator::Subdirectories}); -} - -void AndroidSdkDownloader::downloadAndExtractSdk(const FilePath &jdkPath, const FilePath &sdkExtractPath) +void AndroidSdkDownloader::downloadAndExtractSdk(const FilePath &sdkExtractPath) { if (m_androidConfig.sdkToolsUrl().isEmpty()) { logError(tr("The SDK Tools download URL is empty.")); @@ -103,34 +88,16 @@ void AndroidSdkDownloader::downloadAndExtractSdk(const FilePath &jdkPath, const connect(m_progressDialog, &QProgressDialog::canceled, this, &AndroidSdkDownloader::cancel); - connect(this, &AndroidSdkDownloader::sdkPackageWriteFinished, this, [this, jdkPath, sdkExtractPath]() { - if (extractSdk(jdkPath, sdkExtractPath)) { - setSdkFilesExecPermission(sdkExtractPath); - emit sdkExtracted(); + connect(this, &AndroidSdkDownloader::sdkPackageWriteFinished, this, [this, sdkExtractPath]() { + if (Archive *archive = Archive::unarchive(m_sdkFilename, sdkExtractPath)) { + connect(archive, &Archive::finished, [this, sdkExtractPath](bool success){ + if (success) + emit sdkExtracted(); + }); } }); } -bool AndroidSdkDownloader::extractSdk(const FilePath &jdkPath, const FilePath &sdkExtractPath) -{ - QDir sdkDir = sdkExtractPath.toDir(); - if (!sdkDir.exists()) { - if (!sdkDir.mkpath(".")) { - logError(QString(tr("Could not create the SDK folder %1.")) - .arg(sdkExtractPath.toUserOutput())); - return false; - } - } - - QtcProcess jarExtractProc; - jarExtractProc.setWorkingDirectory(sdkExtractPath); - FilePath jarCmdPath(jdkPath / "/bin/jar"); - jarExtractProc.setCommand({jarCmdPath, {"xf", m_sdkFilename.path()}}); - jarExtractProc.runBlocking(); - - return jarExtractProc.exitCode() ? false : true; -} - bool AndroidSdkDownloader::verifyFileIntegrity() { QFile f(m_sdkFilename.toString()); @@ -170,7 +137,7 @@ void AndroidSdkDownloader::logError(const QString &error) emit sdkDownloaderError(error); } -QString AndroidSdkDownloader::getSaveFilename(const QUrl &url) +FilePath AndroidSdkDownloader::getSaveFilename(const QUrl &url) { QString path = url.path(); QString basename = QFileInfo(path).fileName(); @@ -186,9 +153,8 @@ QString AndroidSdkDownloader::getSaveFilename(const QUrl &url) basename += QString::number(i); } - QString fullPath = QStandardPaths::writableLocation(QStandardPaths::DownloadLocation) - + QDir::separator() + basename; - return fullPath; + return FilePath::fromString(QStandardPaths::writableLocation(QStandardPaths::DownloadLocation)) + / basename; } bool AndroidSdkDownloader::saveToDisk(const FilePath &filename, QIODevice *data) @@ -223,7 +189,7 @@ void AndroidSdkDownloader::downloadFinished(QNetworkReply *reply) if (isHttpRedirect(reply)) { cancelWithError(QString(tr("Download from %1 was redirected.")).arg(url.toString())); } else { - m_sdkFilename = FilePath::fromString(getSaveFilename(url)); + m_sdkFilename = getSaveFilename(url); if (saveToDisk(m_sdkFilename, reply) && verifyFileIntegrity()) emit sdkPackageWriteFinished(); else diff --git a/src/plugins/android/androidsdkdownloader.h b/src/plugins/android/androidsdkdownloader.h index a018d3d10cd..76375132397 100644 --- a/src/plugins/android/androidsdkdownloader.h +++ b/src/plugins/android/androidsdkdownloader.h @@ -43,7 +43,7 @@ class AndroidSdkDownloader : public QObject public: AndroidSdkDownloader(); - void downloadAndExtractSdk(const Utils::FilePath &jdkPath, const Utils::FilePath &sdkExtractPath); + void downloadAndExtractSdk(const Utils::FilePath &sdkExtractPath); static QString dialogTitle(); void cancel(); @@ -54,11 +54,10 @@ signals: void sdkDownloaderError(const QString &error); private: - static QString getSaveFilename(const QUrl &url); + static Utils::FilePath getSaveFilename(const QUrl &url); bool saveToDisk(const Utils::FilePath &filename, QIODevice *data); static bool isHttpRedirect(QNetworkReply *m_reply); - bool extractSdk(const Utils::FilePath &jdkPath, const Utils::FilePath &sdkExtractPath); bool verifyFileIntegrity(); void cancelWithError(const QString &error); void logError(const QString &error); diff --git a/src/plugins/android/androidsettingswidget.cpp b/src/plugins/android/androidsettingswidget.cpp index abbbe2dd871..fda3366a95f 100644 --- a/src/plugins/android/androidsettingswidget.cpp +++ b/src/plugins/android/androidsettingswidget.cpp @@ -712,14 +712,8 @@ void AndroidSettingsWidget::downloadSdk() .arg(m_ui.SDKLocationPathChooser->filePath().cleanPath().toUserOutput()); auto userInput = QMessageBox::information(this, AndroidSdkDownloader::dialogTitle(), message, QMessageBox::Yes | QMessageBox::No); - if (userInput == QMessageBox::Yes) { - if (m_androidSummary->rowsOk({JavaPathExistsAndWritableRow})) { - auto javaPath = m_ui.OpenJDKLocationPathChooser->filePath(); - m_sdkDownloader.downloadAndExtractSdk( - javaPath, - m_ui.SDKLocationPathChooser->filePath().cleanPath()); - } - } + if (userInput == QMessageBox::Yes) + m_sdkDownloader.downloadAndExtractSdk(m_ui.SDKLocationPathChooser->filePath().cleanPath()); } // AndroidSettingsPage From 0923d8676eb6ce7e1af5fc54c83f399eb0ec6648 Mon Sep 17 00:00:00 2001 From: Cristian Adam Date: Mon, 24 Jan 2022 13:41:13 +0100 Subject: [PATCH 21/21] CMakePM: Display CMake kit mismatch values in Settings page updateFromKit() is now called on parsingFinished and the configuration values that differ from the ones in the Kit's CMake configuration will be displayed in red. The "Initial Configuration" page will display the mismatches between kit's CMake configuration and initial parameters. The "Current Configuration" page will display the mismatches between the initial parameters and the current CMake parameters. The Tooltip is displayed with a bit of more space between values for more readability. Change-Id: I6ebfa71951cf979ab08f097befed2d43b74e4d6e Reviewed-by: Reviewed-by: Eike Ziller --- .../cmakebuildconfiguration.cpp | 3 + .../cmakeprojectmanager/configmodel.cpp | 88 +++++++++++++------ src/plugins/cmakeprojectmanager/configmodel.h | 5 +- 3 files changed, 66 insertions(+), 30 deletions(-) diff --git a/src/plugins/cmakeprojectmanager/cmakebuildconfiguration.cpp b/src/plugins/cmakeprojectmanager/cmakebuildconfiguration.cpp index 6facbb8cab7..d7ecacc0668 100644 --- a/src/plugins/cmakeprojectmanager/cmakebuildconfiguration.cpp +++ b/src/plugins/cmakeprojectmanager/cmakebuildconfiguration.cpp @@ -353,6 +353,8 @@ CMakeBuildSettingsWidget::CMakeBuildSettingsWidget(CMakeBuildConfiguration *bc) m_showProgressTimer.start(); }); + m_configModel->setMacroExpander(m_buildConfiguration->macroExpander()); + if (bc->buildSystem()->isParsing()) m_showProgressTimer.start(); else { @@ -368,6 +370,7 @@ CMakeBuildSettingsWidget::CMakeBuildSettingsWidget(CMakeBuildConfiguration *bc) m_configModel->setInitialParametersConfiguration( m_buildConfiguration->initialCMakeConfiguration()); m_buildConfiguration->filterConfigArgumentsFromAdditionalCMakeArguments(); + updateFromKit(); m_configView->expandAll(); m_configView->setEnabled(true); stretcher->stretch(); diff --git a/src/plugins/cmakeprojectmanager/configmodel.cpp b/src/plugins/cmakeprojectmanager/configmodel.cpp index 83e326e530d..aa74f3986b6 100644 --- a/src/plugins/cmakeprojectmanager/configmodel.cpp +++ b/src/plugins/cmakeprojectmanager/configmodel.cpp @@ -26,6 +26,7 @@ #include "configmodel.h" #include +#include #include #include @@ -315,34 +316,37 @@ void ConfigModel::setConfiguration(const QList &c generateTree(); } +Utils::MacroExpander *ConfigModel::macroExpander() const +{ + return m_macroExpander; +} + +void ConfigModel::setMacroExpander(Utils::MacroExpander *newExpander) +{ + m_macroExpander = newExpander; +} + void ConfigModel::generateTree() { + QHash initialHash; + for (const InternalDataItem &di : m_configuration) + if (di.isInitial) + initialHash.insert(di.key, di); + auto root = new Utils::TreeItem; - for (InternalDataItem &di : m_configuration) + for (InternalDataItem &di : m_configuration) { + auto it = initialHash.find(di.key); + if (it != initialHash.end()) + di.initialValue = macroExpander()->expand(it->value); + root->appendChild(new Internal::ConfigModelTreeItem(&di)); + } setRootItem(root); } ConfigModel::InternalDataItem::InternalDataItem(const ConfigModel::DataItem &item) : DataItem(item) { } -QString ConfigModel::InternalDataItem::toolTip() const -{ - QString desc = description; - if (isAdvanced) - desc += QCoreApplication::translate("CMakeProjectManager::ConfigModel", " (ADVANCED)"); - QStringList tooltip(desc); - if (inCMakeCache) { - if (value != newValue) - tooltip << QCoreApplication::translate("CMakeProjectManager", "Current CMake: %1").arg(value); - } else { - tooltip << QCoreApplication::translate("CMakeProjectManager", "Not in CMakeCache.txt").arg(value); - } - if (!kitValue.isEmpty()) - tooltip << QCoreApplication::translate("CMakeProjectManager::ConfigModel", "Current kit: %1").arg(kitValue); - return tooltip.join("
"); -} - QString ConfigModel::InternalDataItem::currentValue() const { if (isUnset) @@ -414,9 +418,15 @@ QVariant ConfigModelTreeItem::data(int column, int role) const font.setStrikeOut((!dataItem->inCMakeCache && !dataItem->isUserNew) || dataItem->isUnset); return font; } - case Qt::ForegroundRole: - return Utils::creatorTheme()->color((!dataItem->kitValue.isNull() && dataItem->kitValue != value) - ? Utils::Theme::TextColorHighlight : Utils::Theme::TextColorNormal); + case Qt::ForegroundRole: { + bool mismatch = false; + if (dataItem->isInitial) + mismatch = !dataItem->kitValue.isEmpty() && dataItem->kitValue != value; + else + mismatch = !dataItem->initialValue.isEmpty() && dataItem->initialValue != value; + return Utils::creatorTheme()->color(mismatch ? Utils::Theme::TextColorHighlight + : Utils::Theme::TextColorNormal); + } case Qt::ToolTipRole: { return toolTip(); } @@ -492,16 +502,36 @@ Qt::ItemFlags ConfigModelTreeItem::flags(int column) const QString ConfigModelTreeItem::toolTip() const { QTC_ASSERT(dataItem, return QString()); - QStringList tooltip(dataItem->description); - if (!dataItem->kitValue.isEmpty()) - tooltip << QCoreApplication::translate("CMakeProjectManager", "Value requested by kit: %1").arg(dataItem->kitValue); - if (dataItem->inCMakeCache) { + QStringList tooltip; + if (!dataItem->description.isEmpty()) + tooltip << dataItem->description; + + if (dataItem->isInitial) { + if (!dataItem->kitValue.isEmpty()) + tooltip << QCoreApplication::translate("CMakeProjectManager", "

Kit: %1

") + .arg(dataItem->kitValue); + if (dataItem->value != dataItem->newValue) - tooltip << QCoreApplication::translate("CMakeProjectManager", "Current CMake: %1").arg(dataItem->value); - } else { - tooltip << QCoreApplication::translate("CMakeProjectManager", "Not in CMakeCache.txt"); + tooltip << QCoreApplication::translate("CMakeProjectManager", + "

Initial Configuration: %1

") + .arg(dataItem->value); + } else { + if (!dataItem->initialValue.isEmpty()) + tooltip << QCoreApplication::translate("CMakeProjectManager", + "

Initial Configuration: %1

") + .arg(dataItem->initialValue); + + if (dataItem->inCMakeCache) { + if (dataItem->value != dataItem->newValue) + tooltip << QCoreApplication::translate("CMakeProjectManager", + "

Current Configuration: %1

") + .arg(dataItem->value); + } else { + tooltip << QCoreApplication::translate("CMakeProjectManager", + "

Not in CMakeCache.txt

"); + } } - return tooltip.join("
"); + return tooltip.join(""); } QString ConfigModelTreeItem::currentValue() const diff --git a/src/plugins/cmakeprojectmanager/configmodel.h b/src/plugins/cmakeprojectmanager/configmodel.h index 03192cad6ff..87f37fcaed6 100644 --- a/src/plugins/cmakeprojectmanager/configmodel.h +++ b/src/plugins/cmakeprojectmanager/configmodel.h @@ -162,6 +162,8 @@ public: QList configurationForCMake() const; + Utils::MacroExpander *macroExpander() const; + void setMacroExpander(Utils::MacroExpander *newExpander); private: class InternalDataItem : public DataItem @@ -170,13 +172,13 @@ private: InternalDataItem(const DataItem &item); InternalDataItem(const InternalDataItem &item) = default; - QString toolTip() const; QString currentValue() const; bool isUserChanged = false; bool isUserNew = false; QString newValue; QString kitValue; + QString initialValue; }; void generateTree(); @@ -184,6 +186,7 @@ private: void setConfiguration(const QList &config); QList m_configuration; KitConfiguration m_kitConfiguration; + Utils::MacroExpander *m_macroExpander = nullptr; friend class Internal::ConfigModelTreeItem; };