diff options
Diffstat (limited to 'qmake/generators/win32/msvc_vcproj.cpp')
-rw-r--r-- | qmake/generators/win32/msvc_vcproj.cpp | 94 |
1 files changed, 68 insertions, 26 deletions
diff --git a/qmake/generators/win32/msvc_vcproj.cpp b/qmake/generators/win32/msvc_vcproj.cpp index a8680cf5bd..d6a825af55 100644 --- a/qmake/generators/win32/msvc_vcproj.cpp +++ b/qmake/generators/win32/msvc_vcproj.cpp @@ -40,6 +40,8 @@ #include <qregexp.h> #include <stdlib.h> +#include <tuple> +#include <utility> //#define DEBUG_SOLUTION_GEN @@ -77,6 +79,8 @@ const char _slnHeader141[] = "Microsoft Visual Studio Solution File, Format "\n# Visual Studio 15"; const char _slnHeader142[] = "Microsoft Visual Studio Solution File, Format Version 12.00" "\n# Visual Studio Version 16"; +const char _slnHeader143[] = "Microsoft Visual Studio Solution File, Format Version 12.00" + "\n# Visual Studio Version 17"; // The following UUID _may_ change for later servicepacks... // If so we need to search through the registry at // HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\VisualStudio\7.0\Projects @@ -312,6 +316,8 @@ QString VcprojGenerator::retrievePlatformToolSet() const return QStringLiteral("v141"); case NET2019: return QStringLiteral("v142"); + case NET2022: + return QStringLiteral("v143"); default: return QString(); } @@ -539,6 +545,9 @@ void VcprojGenerator::writeSubDirs(QTextStream &t) } switch (vcProject.Configuration.CompilerVersion) { + case NET2022: + t << _slnHeader143; + break; case NET2019: t << _slnHeader142; break; @@ -814,33 +823,62 @@ void VcprojGenerator::init() } } - // Add all input files for a custom compiler into a map for uniqueness, - // unless the compiler is configure as a combined stage, then use the first one + // Helper function to create a fake file foo.cbt for the project view. + // + // This prevents VS from complaining about a circular dependency from "foo -> foo". + // + // The .cbt file is added as "source" of the Custom Build Tool. This means, in the project + // view, this is the file the Custom Build Tool property page is attached to. + // + // This function returns a pair with + // - the fully resolved output file path + // - the file path of the .cbt file + auto addExtraCompilerSourceWithCustomBuildToolFakeFile + = [this](const QString &compilerOutput, const ProString &extraCompiler, + const QStringList &inputs) -> std::pair<QString, QString> + { + QString realOut = replaceExtraCompilerVariables(compilerOutput, inputs, {}, NoShell); + QString out = realOut + customBuildToolFilterFileSuffix; + createCustomBuildToolFakeFile(out, realOut); + out = Option::fixPathToTargetOS(out, false); + extraCompilerSources[out] += extraCompiler.toQString(); + return { realOut, out }; + }; + + // Add all input files for a custom compiler into a map for uniqueness. + // + // Use .cbt files for the following cases: + // - CONFIG += combine + // - the input has a built-in compiler (e.g. C++ source file) for (const ProString &quc : project->values("QMAKE_EXTRA_COMPILERS")) { const ProStringList &invar = project->values(ProKey(quc + ".input")); const QString compiler_out = project->first(ProKey(quc + ".output")).toQString(); - for (ProStringList::ConstIterator iit = invar.constBegin(); iit != invar.constEnd(); ++iit) { - ProStringList fileList = project->values((*iit).toKey()); - if (!fileList.isEmpty()) { - if (project->values(ProKey(quc + ".CONFIG")).indexOf("combine") != -1) - fileList.erase(fileList.begin() + 1, fileList.end()); - for (ProStringList::ConstIterator fit = fileList.constBegin(); fit != fileList.constEnd(); ++fit) { - QString file = (*fit).toQString(); - if (verifyExtraCompiler(quc, file)) { - if (!hasBuiltinCompiler(file)) { - extraCompilerSources[file] += quc.toQString(); - } else { - // Create a fake file foo.moc.cbt for the project view. - // This prevents VS from complaining about a circular - // dependency from foo.moc -> foo.moc. - QString realOut = replaceExtraCompilerVariables( - compiler_out, file, QString(), NoShell); - QString out = realOut + customBuildToolFilterFileSuffix; - createCustomBuildToolFakeFile(out, realOut); - out = Option::fixPathToTargetOS(out, false); - extraCompilerSources[out] += quc.toQString(); - extraCompilerOutputs[out] = file; - } + + QStringList inputFiles; + for (auto it = invar.begin(); it != invar.end(); ++it) + inputFiles += project->values(it->toKey()).toQStringList(); + + if (project->values(ProKey(quc + ".CONFIG")).contains("combine")) { + // Handle "CONFIG += combine" extra compilers. + QString realOut; + QString out; + std::tie(realOut, out) + = addExtraCompilerSourceWithCustomBuildToolFakeFile(compiler_out, quc, inputFiles); + if (hasBuiltinCompiler(realOut)) + extraCompilerOutputs[out] = realOut; + } else { + // Handle regular 1-to-1 extra compilers. + for (const QString &file : inputFiles) { + if (verifyExtraCompiler(quc, file)) { + if (!hasBuiltinCompiler(file)) { + extraCompilerSources[file] += quc.toQString(); + } else { + QString out; + std::tie(std::ignore, out) + = addExtraCompilerSourceWithCustomBuildToolFakeFile(compiler_out, + quc, + QStringList(file)); + extraCompilerOutputs[out] = file; } } } @@ -892,6 +930,9 @@ void VcprojGenerator::initProject() // Own elements ----------------------------- vcProject.Name = project->first("QMAKE_ORIG_TARGET").toQString(); switch (vcProject.Configuration.CompilerVersion) { + case NET2022: + vcProject.Version = "17.00"; + break; case NET2019: vcProject.Version = "16.00"; break; @@ -1586,9 +1627,10 @@ void VcprojGenerator::initExtraCompilerOutputs() if (!outputs.isEmpty()) tmp_out = outputs.first().toQString(); if (project->values(ProKey(*it + ".CONFIG")).indexOf("combine") != -1) { - // Combined output, only one file result + // Combined output, only one file result. Use .cbt file. extraCompile.addFile(Option::fixPathToTargetOS( - replaceExtraCompilerVariables(tmp_out, QString(), QString(), NoShell), false)); + replaceExtraCompilerVariables(tmp_out + customBuildToolFilterFileSuffix, + QString(), QString(), NoShell), false)); } else if (!inputVars.isEmpty()) { // One output file per input const ProStringList &tmp_in = project->values(inputVars.first().toKey()); |