diff --git a/src/plugins/cmakeprojectmanager/cmakeprojectimporter.cpp b/src/plugins/cmakeprojectmanager/cmakeprojectimporter.cpp index 59f1d3796b0..e4e9ef90598 100644 --- a/src/plugins/cmakeprojectmanager/cmakeprojectimporter.cpp +++ b/src/plugins/cmakeprojectmanager/cmakeprojectimporter.cpp @@ -394,10 +394,7 @@ bool CMakeProjectImporter::matchKit(void *directoryData, const Kit *k) const if (!Utils::contains(allLanguages, [&tcd](const Id& language) {return language == tcd.language;})) continue; ToolChain *tc = ToolChainKitAspect::toolChain(k, tcd.language); - if (!tc - || !Utils::Environment::systemEnvironment() - .isSameExecutable(tc->compilerCommand().toString(), - tcd.compilerPath.toString())) { + if (!tc || !tc->matchesCompilerCommand(tcd.compilerPath)) { return false; } } diff --git a/src/plugins/projectexplorer/gcctoolchain.cpp b/src/plugins/projectexplorer/gcctoolchain.cpp index 168062d154f..355ff2d7fc6 100644 --- a/src/plugins/projectexplorer/gcctoolchain.cpp +++ b/src/plugins/projectexplorer/gcctoolchain.cpp @@ -1580,6 +1580,27 @@ ClangToolChain::~ClangToolChain() QObject::disconnect(m_mingwToolchainAddedConnection); } +bool ClangToolChain::matchesCompilerCommand(const Utils::FilePath &command, + const Utils::Environment &env) const +{ + if (!m_resolvedCompilerCommand) { + m_resolvedCompilerCommand = FilePath(); + if (HostOsInfo::isMacHost() + && compilerCommand().parentDir() == FilePath::fromString("/usr/bin")) { + std::unique_ptr xcrun(new QtcProcess); + xcrun->setCommand({"/usr/bin/xcrun", {"-f", compilerCommand().fileName()}}); + xcrun->runBlocking(); + const FilePath output = FilePath::fromString(xcrun->stdOut().trimmed()); + if (output.isExecutableFile() && output != compilerCommand()) + m_resolvedCompilerCommand = output; + } + } + if (!m_resolvedCompilerCommand->isEmpty() + && env.isSameExecutable(m_resolvedCompilerCommand->toString(), command.toString())) + return true; + return GccToolChain::matchesCompilerCommand(command, env); +} + static FilePath mingwAwareMakeCommand(const Environment &environment) { const QStringList makes diff --git a/src/plugins/projectexplorer/gcctoolchain.h b/src/plugins/projectexplorer/gcctoolchain.h index 7bd83d0a1b2..bad26674e23 100644 --- a/src/plugins/projectexplorer/gcctoolchain.h +++ b/src/plugins/projectexplorer/gcctoolchain.h @@ -33,6 +33,7 @@ #include "headerpath.h" #include +#include #include #include @@ -211,6 +212,10 @@ public: explicit ClangToolChain(Utils::Id typeId); ~ClangToolChain() override; + bool matchesCompilerCommand( + const Utils::FilePath &command, + const Utils::Environment &env = Utils::Environment::systemEnvironment()) const override; + Utils::FilePath makeCommand(const Utils::Environment &environment) const override; Utils::LanguageExtensions languageExtensions(const QStringList &cxxflags) const override; @@ -237,6 +242,9 @@ protected: void syncAutodetectedWithParentToolchains(); private: + // "resolved" on macOS from /usr/bin/clang(++) etc to /usr/bin/clang(++) + // which is used for comparison with matchesCompileCommand + mutable Utils::optional m_resolvedCompilerCommand; QByteArray m_parentToolChainId; QMetaObject::Connection m_mingwToolchainAddedConnection; QMetaObject::Connection m_thisToolchainRemovedConnection; diff --git a/src/plugins/projectexplorer/projectimporter.cpp b/src/plugins/projectexplorer/projectimporter.cpp index 2db6dafa2b6..e51aaa2c968 100644 --- a/src/plugins/projectexplorer/projectimporter.cpp +++ b/src/plugins/projectexplorer/projectimporter.cpp @@ -414,9 +414,7 @@ ProjectImporter::findOrCreateToolChains(const ToolChainDescription &tcd) const { ToolChainData result; result.tcs = ToolChainManager::toolchains([&tcd](const ToolChain *tc) { - return tc->language() == tcd.language && - Utils::Environment::systemEnvironment().isSameExecutable( - tc->compilerCommand().toString(), tcd.compilerPath.toString()); + return tc->language() == tcd.language && tc->matchesCompilerCommand(tcd.compilerPath); }); for (const ToolChain *tc : qAsConst(result.tcs)) { const QByteArray tcId = tc->id(); diff --git a/src/plugins/projectexplorer/toolchain.cpp b/src/plugins/projectexplorer/toolchain.cpp index f36ce9414b6..32d39fc0806 100644 --- a/src/plugins/projectexplorer/toolchain.cpp +++ b/src/plugins/projectexplorer/toolchain.cpp @@ -343,6 +343,11 @@ void ToolChain::setCompilerCommand(const FilePath &command) toolChainUpdated(); } +bool ToolChain::matchesCompilerCommand(const Utils::FilePath &command, const Environment &env) const +{ + return env.isSameExecutable(compilerCommand().toString(), command.toString()); +} + void ToolChain::setCompilerCommandKey(const QString &commandKey) { d->m_compilerCommandKey = commandKey; diff --git a/src/plugins/projectexplorer/toolchain.h b/src/plugins/projectexplorer/toolchain.h index 2e41313f2ec..6a3ced00535 100644 --- a/src/plugins/projectexplorer/toolchain.h +++ b/src/plugins/projectexplorer/toolchain.h @@ -156,6 +156,9 @@ public: virtual Utils::FilePath compilerCommand() const; // FIXME: De-virtualize. void setCompilerCommand(const Utils::FilePath &command); + virtual bool matchesCompilerCommand( + const Utils::FilePath &command, + const Utils::Environment &env = Utils::Environment::systemEnvironment()) const; virtual QList createOutputParsers() const = 0; diff --git a/src/plugins/qmakeprojectmanager/qmakeproject.cpp b/src/plugins/qmakeprojectmanager/qmakeproject.cpp index c77f468ae23..bff8df79024 100644 --- a/src/plugins/qmakeprojectmanager/qmakeproject.cpp +++ b/src/plugins/qmakeprojectmanager/qmakeproject.cpp @@ -1390,7 +1390,7 @@ void QmakeBuildSystem::testToolChain(ToolChain *tc, const FilePath &path) const const Utils::FilePath expected = tc->compilerCommand(); Environment env = buildConfiguration()->environment(); - if (env.isSameExecutable(path.toString(), expected.toString())) + if (tc->matchesCompilerCommand(expected, env)) return; const QPair pair = qMakePair(expected, path); if (m_toolChainWarnings.contains(pair))