diff options
Diffstat (limited to 'Source')
-rw-r--r-- | Source/cmQtAutoGen.cxx | 85 | ||||
-rw-r--r-- | Source/cmQtAutoGen.h | 33 | ||||
-rw-r--r-- | Source/cmQtAutoGeneratorInitializer.cxx | 349 | ||||
-rw-r--r-- | Source/cmQtAutoGeneratorInitializer.h | 2 | ||||
-rw-r--r-- | Source/cmQtAutoGenerators.cxx | 88 | ||||
-rw-r--r-- | Source/cmQtAutoGenerators.h | 3 |
6 files changed, 343 insertions, 217 deletions
diff --git a/Source/cmQtAutoGen.cxx b/Source/cmQtAutoGen.cxx index 2bed5b3..5e89978 100644 --- a/Source/cmQtAutoGen.cxx +++ b/Source/cmQtAutoGen.cxx @@ -14,18 +14,22 @@ // - Static variables -const std::string genNameGen = "AutoGen"; -const std::string genNameMoc = "AutoMoc"; -const std::string genNameUic = "AutoUic"; -const std::string genNameRcc = "AutoRcc"; +std::string const genNameGen = "AutoGen"; +std::string const genNameMoc = "AutoMoc"; +std::string const genNameUic = "AutoUic"; +std::string const genNameRcc = "AutoRcc"; + +std::string const mcNameSingle = "SINGLE"; +std::string const mcNameWrap = "WRAP"; +std::string const mcNameFull = "FULL"; // - Static functions /// @brief Merges newOpts into baseOpts /// @arg valueOpts list of options that accept a value void MergeOptions(std::vector<std::string>& baseOpts, - const std::vector<std::string>& newOpts, - const std::vector<std::string>& valueOpts, bool isQt5) + std::vector<std::string> const& newOpts, + std::vector<std::string> const& valueOpts, bool isQt5) { typedef std::vector<std::string>::iterator Iter; typedef std::vector<std::string>::const_iterator CIter; @@ -40,7 +44,7 @@ void MergeOptions(std::vector<std::string>& baseOpts, std::vector<std::string> extraOpts; for (CIter fit = newOpts.begin(), fitEnd = newOpts.end(); fit != fitEnd; ++fit) { - const std::string& newOpt = *fit; + std::string const& newOpt = *fit; Iter existIt = std::find(baseOpts.begin(), baseOpts.end(), newOpt); if (existIt != baseOpts.end()) { if (newOpt.size() >= 2) { @@ -87,7 +91,7 @@ static std::string utilStripCR(std::string const& line) /// @brief Reads the resource files list from from a .qrc file - Qt4 version /// @return True if the .qrc file was successfully parsed -static bool RccListInputsQt4(const std::string& fileName, +static bool RccListInputsQt4(std::string const& fileName, std::vector<std::string>& files, std::string* errorMessage) { @@ -140,8 +144,8 @@ static bool RccListInputsQt4(const std::string& fileName, /// @brief Reads the resource files list from from a .qrc file - Qt5 version /// @return True if the .qrc file was successfully parsed -static bool RccListInputsQt5(const std::string& rccCommand, - const std::string& fileName, +static bool RccListInputsQt5(std::string const& rccCommand, + std::string const& fileName, std::vector<std::string>& files, std::string* errorMessage) { @@ -244,9 +248,9 @@ static bool RccListInputsQt5(const std::string& rccCommand, // - Class definitions -const std::string cmQtAutoGen::listSep = "@LSEP@"; +std::string const cmQtAutoGen::listSep = "@LSEP@"; -const std::string& cmQtAutoGen::GeneratorName(Generator type) +std::string const& cmQtAutoGen::GeneratorName(Generator type) { switch (type) { case Generator::GEN: @@ -266,7 +270,31 @@ std::string cmQtAutoGen::GeneratorNameUpper(Generator genType) return cmSystemTools::UpperCase(cmQtAutoGen::GeneratorName(genType)); } -std::string cmQtAutoGen::Quoted(const std::string& text) +std::string const& cmQtAutoGen::MultiConfigName(MultiConfig config) +{ + switch (config) { + case MultiConfig::SINGLE: + return mcNameSingle; + case MultiConfig::WRAP: + return mcNameWrap; + case MultiConfig::FULL: + return mcNameFull; + } + return mcNameWrap; +} + +cmQtAutoGen::MultiConfig cmQtAutoGen::MultiConfigType(std::string const& name) +{ + if (name == mcNameSingle) { + return MultiConfig::SINGLE; + } + if (name == mcNameFull) { + return MultiConfig::FULL; + } + return MultiConfig::WRAP; +} + +std::string cmQtAutoGen::Quoted(std::string const& text) { static const char* rep[18] = { "\\", "\\\\", "\"", "\\\"", "\a", "\\a", "\b", "\\b", "\f", "\\f", "\n", "\\n", @@ -282,11 +310,28 @@ std::string cmQtAutoGen::Quoted(const std::string& text) return res; } +std::string cmQtAutoGen::AppendFilenameSuffix(std::string const& filename, + std::string const& suffix) +{ + std::string res; + auto pos = filename.rfind('.'); + if (pos != std::string::npos) { + const auto it_dot = filename.begin() + pos; + res.assign(filename.begin(), it_dot); + res.append(suffix); + res.append(it_dot, filename.end()); + } else { + res = filename; + res.append(suffix); + } + return res; +} + void cmQtAutoGen::UicMergeOptions(std::vector<std::string>& baseOpts, - const std::vector<std::string>& newOpts, + std::vector<std::string> const& newOpts, bool isQt5) { - static const std::vector<std::string> valueOpts = { + static std::vector<std::string> const valueOpts = { "tr", "translate", "postfix", "generator", "include", // Since Qt 5.3 "g" @@ -295,18 +340,18 @@ void cmQtAutoGen::UicMergeOptions(std::vector<std::string>& baseOpts, } void cmQtAutoGen::RccMergeOptions(std::vector<std::string>& baseOpts, - const std::vector<std::string>& newOpts, + std::vector<std::string> const& newOpts, bool isQt5) { - static const std::vector<std::string> valueOpts = { "name", "root", + static std::vector<std::string> const valueOpts = { "name", "root", "compress", "threshold" }; MergeOptions(baseOpts, newOpts, valueOpts, isQt5); } -bool cmQtAutoGen::RccListInputs(const std::string& qtMajorVersion, - const std::string& rccCommand, - const std::string& fileName, +bool cmQtAutoGen::RccListInputs(std::string const& qtMajorVersion, + std::string const& rccCommand, + std::string const& fileName, std::vector<std::string>& files, std::string* errorMessage) { diff --git a/Source/cmQtAutoGen.h b/Source/cmQtAutoGen.h index d7807ee..acc092f 100644 --- a/Source/cmQtAutoGen.h +++ b/Source/cmQtAutoGen.h @@ -14,7 +14,7 @@ class cmQtAutoGen { public: - static const std::string listSep; + static std::string const listSep; enum Generator { @@ -24,32 +24,47 @@ public: RCC }; + enum MultiConfig + { + SINGLE, // Single configuration + WRAP, // Multi configuration using wrapper files + FULL // Full multi configuration using per config sources + }; + public: /// @brief Returns the generator name - static const std::string& GeneratorName(Generator genType); + static std::string const& GeneratorName(Generator genType); /// @brief Returns the generator name in upper case static std::string GeneratorNameUpper(Generator genType); + /// @brief Returns the multi configuration name string + static std::string const& MultiConfigName(MultiConfig config); + /// @brief Returns the multi configuration type + static MultiConfig MultiConfigType(std::string const& name); + /// @brief Returns a the string escaped and enclosed in quotes - /// - static std::string Quoted(const std::string& text); + static std::string Quoted(std::string const& text); + + /// @brief Appends the suffix to the filename before the last dot + static std::string AppendFilenameSuffix(std::string const& filename, + std::string const& suffix); /// @brief Merges newOpts into baseOpts static void UicMergeOptions(std::vector<std::string>& baseOpts, - const std::vector<std::string>& newOpts, + std::vector<std::string> const& newOpts, bool isQt5); /// @brief Merges newOpts into baseOpts static void RccMergeOptions(std::vector<std::string>& baseOpts, - const std::vector<std::string>& newOpts, + std::vector<std::string> const& newOpts, bool isQt5); /// @brief Reads the resource files list from from a .qrc file /// @arg fileName Must be the absolute path of the .qrc file /// @return True if the rcc file was successfully parsed - static bool RccListInputs(const std::string& qtMajorVersion, - const std::string& rccCommand, - const std::string& fileName, + static bool RccListInputs(std::string const& qtMajorVersion, + std::string const& rccCommand, + std::string const& fileName, std::vector<std::string>& files, std::string* errorMessage = nullptr); }; diff --git a/Source/cmQtAutoGeneratorInitializer.cxx b/Source/cmQtAutoGeneratorInitializer.cxx index 33c7d45..9befd65 100644 --- a/Source/cmQtAutoGeneratorInitializer.cxx +++ b/Source/cmQtAutoGeneratorInitializer.cxx @@ -48,9 +48,26 @@ inline static std::string GetSafeProperty(cmSourceFile const* sf, return std::string(SafeString(sf->GetProperty(key))); } -inline static bool AutogenMultiConfig(cmGlobalGenerator* globalGen) +static cmQtAutoGen::MultiConfig AutogenMultiConfig( + cmGlobalGenerator* globalGen) { - return globalGen->IsMultiConfig(); + if (!globalGen->IsMultiConfig()) { + return cmQtAutoGen::SINGLE; + } + + // FIXME: Xcode does not support per-config sources, yet. + // (EXCLUDED_SOURCE_FILE_NAMES) + // if (globalGen->GetName().find("Xcode") != std::string::npos) { + // return cmQtAutoGen::FULL; + //} + + // FIXME: Visual Studio does not support per-config sources, yet. + // (EXCLUDED_SOURCE_FILE_NAMES) + // if (globalGen->GetName().find("Visual Studio") != std::string::npos) { + // return cmQtAutoGen::FULL; + //} + + return cmQtAutoGen::WRAP; } static std::string GetAutogenTargetName(cmGeneratorTarget const* target) @@ -100,7 +117,7 @@ std::string cmQtAutoGeneratorInitializer::GetQtMajorVersion( } std::string cmQtAutoGeneratorInitializer::GetQtMinorVersion( - cmGeneratorTarget const* target, const std::string& qtVersionMajor) + cmGeneratorTarget const* target, std::string const& qtVersionMajor) { cmMakefile* makefile = target->Target->GetMakefile(); std::string qtMinor; @@ -119,8 +136,8 @@ std::string cmQtAutoGeneratorInitializer::GetQtMinorVersion( return qtMinor; } -static bool QtVersionGreaterOrEqual(const std::string& major, - const std::string& minor, +static bool QtVersionGreaterOrEqual(std::string const& major, + std::string const& minor, unsigned long requestMajor, unsigned long requestMinor) { @@ -134,40 +151,17 @@ static bool QtVersionGreaterOrEqual(const std::string& major, return false; } -static std::vector<std::string> GetConfigurations( - cmMakefile* makefile, std::string* config = nullptr) -{ - std::vector<std::string> configs; - { - std::string cfg = makefile->GetConfigurations(configs); - if (config != nullptr) { - *config = cfg; - } - } - // Add empty configuration on demand - if (configs.empty()) { - configs.push_back(""); - } - return configs; -} - -static std::vector<std::string> GetConfigurationSuffixes(cmMakefile* makefile) +static void GetConfigs(cmMakefile* makefile, std::string& configDefault, + std::vector<std::string>& configsList) { - std::vector<std::string> suffixes; - if (AutogenMultiConfig(makefile->GetGlobalGenerator())) { - makefile->GetConfigurations(suffixes); - for (std::string& suffix : suffixes) { - suffix.insert(0, "_"); - } + configDefault = makefile->GetConfigurations(configsList); + if (configsList.empty()) { + configsList.push_back(""); } - if (suffixes.empty()) { - suffixes.push_back(""); - } - return suffixes; } static void AddDefinitionEscaped(cmMakefile* makefile, const char* key, - const std::string& value) + std::string const& value) { makefile->AddDefinition(key, cmOutputConverter::EscapeForCMake(value).c_str()); @@ -203,7 +197,7 @@ static void AddDefinitionEscaped( .c_str()); } -static bool AddToSourceGroup(cmMakefile* makefile, const std::string& fileName, +static bool AddToSourceGroup(cmMakefile* makefile, std::string const& fileName, cmQtAutoGen::Generator genType) { cmSourceGroup* sourceGroup = nullptr; @@ -255,25 +249,54 @@ static bool AddToSourceGroup(cmMakefile* makefile, const std::string& fileName, return true; } -static void AddCleanFile(cmMakefile* makefile, const std::string& fileName) +static void AddCleanFile(cmMakefile* makefile, std::string const& fileName) { makefile->AppendProperty("ADDITIONAL_MAKE_CLEAN_FILES", fileName.c_str(), false); } -static void AddGeneratedSource(cmGeneratorTarget* target, - const std::string& filename, - cmQtAutoGen::Generator genType) +static std::vector<std::string> AddGeneratedSource( + cmGeneratorTarget* target, std::string const& filename, + cmQtAutoGen::MultiConfig multiConfig, + const std::vector<std::string>& configsList, cmQtAutoGen::Generator genType) { - cmMakefile* makefile = target->Target->GetMakefile(); + std::vector<std::string> genFiles; + // Register source file in makefile and source group + if (multiConfig != cmQtAutoGen::FULL) { + genFiles.push_back(filename); + } else { + for (std::string const& cfg : configsList) { + genFiles.push_back( + cmQtAutoGen::AppendFilenameSuffix(filename, "_" + cfg)); + } + } { - cmSourceFile* gFile = makefile->GetOrCreateSource(filename, true); - gFile->SetProperty("GENERATED", "1"); - gFile->SetProperty("SKIP_AUTOGEN", "On"); + cmMakefile* makefile = target->Target->GetMakefile(); + for (std::string const& genFile : genFiles) { + { + cmSourceFile* gFile = makefile->GetOrCreateSource(genFile, true); + gFile->SetProperty("GENERATED", "1"); + gFile->SetProperty("SKIP_AUTOGEN", "On"); + } + AddToSourceGroup(makefile, genFile, genType); + } } - target->AddSource(filename); - AddToSourceGroup(makefile, filename, genType); + // Add source file to target + if (multiConfig != cmQtAutoGen::FULL) { + target->AddSource(filename); + } else { + for (std::string const& cfg : configsList) { + std::string src = "$<$<CONFIG:"; + src += cfg; + src += ">:"; + src += cmQtAutoGen::AppendFilenameSuffix(filename, "_" + cfg); + src += ">"; + target->AddSource(src); + } + } + + return genFiles; } struct cmQtAutoGenSetup @@ -295,8 +318,8 @@ static void SetupAcquireSkipFiles(cmQtAutoGenDigest const& digest, digest.Target->Makefile->GetSourceFiles(); for (cmSourceFile* sf : allSources) { // sf->GetExtension() is only valid after sf->GetFullPath() ... - const std::string& fPath = sf->GetFullPath(); - const cmSystemTools::FileFormat fileType = + std::string const& fPath = sf->GetFullPath(); + cmSystemTools::FileFormat const fileType = cmSystemTools::GetFileFormat(sf->GetExtension().c_str()); if (!(fileType == cmSystemTools::CXX_FILE_FORMAT) && !(fileType == cmSystemTools::HEADER_FILE_FORMAT)) { @@ -308,7 +331,7 @@ static void SetupAcquireSkipFiles(cmQtAutoGenDigest const& digest, const bool uicSkip = digest.UicEnabled && (skipAll || sf->GetPropertyAsBool("SKIP_AUTOUIC")); if (mocSkip || uicSkip) { - const std::string absFile = cmSystemTools::GetRealPath(fPath); + std::string const absFile = cmSystemTools::GetRealPath(fPath); if (mocSkip) { setup.MocSkip.insert(absFile); } @@ -320,9 +343,9 @@ static void SetupAcquireSkipFiles(cmQtAutoGenDigest const& digest, } } -static void SetupAutoTargetMoc(const cmQtAutoGenDigest& digest, - std::string const& config, - std::vector<std::string> const& configs, +static void SetupAutoTargetMoc(cmQtAutoGenDigest const& digest, + std::string const& configDefault, + std::vector<std::string> const& configsList, cmQtAutoGenSetup& setup) { cmGeneratorTarget const* target = digest.Target; @@ -348,43 +371,42 @@ static void SetupAutoTargetMoc(const cmQtAutoGenDigest& digest, } // Moc includes and compile definitions { - auto GetCompileDefinitionsAndDirectories = [target, localGen]( - const std::string& cfg, std::string& incs, std::string& defs) { - { - std::vector<std::string> includeDirs; - // Get the include dirs for this target, without stripping the implicit - // include dirs off, see - // https://gitlab.kitware.com/cmake/cmake/issues/13667 - localGen->GetIncludeDirectories(includeDirs, target, "CXX", cfg, - false); - incs = cmJoin(includeDirs, ";"); - } - { - std::set<std::string> defines; - localGen->AddCompileDefinitions(defines, target, cfg, "CXX"); - defs += cmJoin(defines, ";"); - } + auto GetIncludeDirs = [target, + localGen](std::string const& cfg) -> std::string { + // Get the include dirs for this target, without stripping the implicit + // include dirs off, see + // https://gitlab.kitware.com/cmake/cmake/issues/13667 + std::vector<std::string> includeDirs; + localGen->GetIncludeDirectories(includeDirs, target, "CXX", cfg, false); + return cmJoin(includeDirs, ";"); + }; + auto GetCompileDefinitions = + [target, localGen](std::string const& cfg) -> std::string { + std::set<std::string> defines; + localGen->AddCompileDefinitions(defines, target, cfg, "CXX"); + return cmJoin(defines, ";"); }; - // Default settings - std::string incs; - std::string compileDefs; - GetCompileDefinitionsAndDirectories(config, incs, compileDefs); - AddDefinitionEscaped(makefile, "_moc_incs", incs); - AddDefinitionEscaped(makefile, "_moc_compile_defs", compileDefs); - - // Configuration specific settings - for (std::string const& cfg : configs) { - std::string configIncs; - std::string configCompileDefs; - GetCompileDefinitionsAndDirectories(cfg, configIncs, configCompileDefs); - if (configIncs != incs) { - setup.ConfigMocIncludes[cfg] = configIncs; + // Default configuration settings + std::string const includeDirs = GetIncludeDirs(configDefault); + std::string const compileDefs = GetCompileDefinitions(configDefault); + // Other configuration settings + for (std::string const& cfg : configsList) { + { + std::string const configIncludeDirs = GetIncludeDirs(cfg); + if (configIncludeDirs != includeDirs) { + setup.ConfigMocIncludes[cfg] = configIncludeDirs; + } } - if (configCompileDefs != compileDefs) { - setup.ConfigMocDefines[cfg] = configCompileDefs; + { + std::string const configCompileDefs = GetCompileDefinitions(cfg); + if (configCompileDefs != compileDefs) { + setup.ConfigMocDefines[cfg] = configCompileDefs; + } } } + AddDefinitionEscaped(makefile, "_moc_include_dirs", includeDirs); + AddDefinitionEscaped(makefile, "_moc_compile_defs", compileDefs); } // Moc executable @@ -419,7 +441,7 @@ static void SetupAutoTargetMoc(const cmQtAutoGenDigest& digest, } } -static void SetupAutoTargetUic(const cmQtAutoGenDigest& digest, +static void SetupAutoTargetUic(cmQtAutoGenDigest const& digest, std::string const& config, std::vector<std::string> const& configs, cmQtAutoGenSetup& setup) @@ -433,10 +455,10 @@ static void SetupAutoTargetUic(const cmQtAutoGenDigest& digest, { std::vector<std::string> uicSearchPaths; { - const std::string usp = GetSafeProperty(target, "AUTOUIC_SEARCH_PATHS"); + std::string const usp = GetSafeProperty(target, "AUTOUIC_SEARCH_PATHS"); if (!usp.empty()) { cmSystemTools::ExpandListArgument(usp, uicSearchPaths); - const std::string srcDir = makefile->GetCurrentSourceDirectory(); + std::string const srcDir = makefile->GetCurrentSourceDirectory(); for (std::string& path : uicSearchPaths) { path = cmSystemTools::CollapseFullPath(path, srcDir); } @@ -446,19 +468,19 @@ static void SetupAutoTargetUic(const cmQtAutoGenDigest& digest, } // Uic target options { - auto UicGetOpts = [target](const std::string& cfg) -> std::string { + auto UicGetOpts = [target](std::string const& cfg) -> std::string { std::vector<std::string> opts; target->GetAutoUicOptions(opts, cfg); return cmJoin(opts, ";"); }; // Default settings - const std::string uicOpts = UicGetOpts(config); + std::string const uicOpts = UicGetOpts(config); AddDefinitionEscaped(makefile, "_uic_target_options", uicOpts); // Configuration specific settings for (std::string const& cfg : configs) { - const std::string configUicOpts = UicGetOpts(cfg); + std::string const configUicOpts = UicGetOpts(cfg); if (configUicOpts != uicOpts) { setup.ConfigUicOptions[cfg] = configUicOpts; } @@ -469,16 +491,16 @@ static void SetupAutoTargetUic(const cmQtAutoGenDigest& digest, std::vector<std::string> uiFileFiles; std::vector<std::vector<std::string>> uiFileOptions; { - const std::string uiExt = "ui"; + std::string const uiExt = "ui"; const std::vector<cmSourceFile*>& srcFiles = makefile->GetSourceFiles(); for (cmSourceFile* sf : srcFiles) { // sf->GetExtension() is only valid after sf->GetFullPath() ... - const std::string& fPath = sf->GetFullPath(); + std::string const& fPath = sf->GetFullPath(); if (sf->GetExtension() == uiExt) { // Check if the files has uic options - const std::string uicOpts = GetSafeProperty(sf, "AUTOUIC_OPTIONS"); + std::string const uicOpts = GetSafeProperty(sf, "AUTOUIC_OPTIONS"); if (!uicOpts.empty()) { - const std::string absFile = cmSystemTools::GetRealPath(fPath); + std::string const absFile = cmSystemTools::GetRealPath(fPath); // Check if file isn't skipped if (setup.UicSkip.count(absFile) == 0) { uiFileFiles.push_back(absFile); @@ -528,7 +550,7 @@ static void SetupAutoTargetUic(const cmQtAutoGenDigest& digest, } static std::string RccGetExecutable(cmGeneratorTarget const* target, - const std::string& qtMajorVersion) + std::string const& qtMajorVersion) { std::string rccExec; std::string err; @@ -559,7 +581,7 @@ static std::string RccGetExecutable(cmGeneratorTarget const* target, return rccExec; } -static void SetupAutoTargetRcc(const cmQtAutoGenDigest& digest) +static void SetupAutoTargetRcc(cmQtAutoGenDigest const& digest) { std::vector<std::string> rccFiles; std::vector<std::string> rccBuilds; @@ -590,26 +612,36 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( cmLocalGenerator* localGen = target->GetLocalGenerator(); cmGlobalGenerator* globalGen = localGen->GetGlobalGenerator(); - // Create a custom target for running generators at buildtime - const bool multiConfig = AutogenMultiConfig(globalGen); - const std::string autogenTargetName = GetAutogenTargetName(target); - const std::string autogenBuildDir = GetAutogenTargetBuildDir(target); - const std::string workingDirectory = + std::string const autogenTargetName = GetAutogenTargetName(target); + std::string const autogenBuildDir = GetAutogenTargetBuildDir(target); + std::string const workingDirectory = cmSystemTools::CollapseFullPath("", makefile->GetCurrentBinaryDirectory()); - const std::vector<std::string> suffixes = GetConfigurationSuffixes(makefile); + + cmQtAutoGen::MultiConfig const multiConfig = AutogenMultiConfig(globalGen); + std::string configDefault; + std::vector<std::string> configsList; + GetConfigs(makefile, configDefault, configsList); + std::set<std::string> autogenDependFiles; std::set<std::string> autogenDependTargets; std::vector<std::string> autogenProvides; // Remove build directories on cleanup AddCleanFile(makefile, autogenBuildDir); - // Remove old settings on cleanup { std::string base = GetAutogenTargetFilesDir(target); base += "/AutogenOldSettings"; - for (std::string const& suffix : suffixes) { - AddCleanFile(makefile, (base + suffix).append(".cmake")); + if (multiConfig == cmQtAutoGen::SINGLE) { + AddCleanFile(makefile, base.append(".cmake")); + } else { + for (std::string const& cfg : configsList) { + std::string filename = base; + filename += "_"; + filename += cfg; + filename += ".cmake"; + AddCleanFile(makefile, filename); + } } } @@ -653,15 +685,18 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( // Add moc compilation to generated files list if (digest.MocEnabled) { - const std::string mocsComp = autogenBuildDir + "/mocs_compilation.cpp"; - AddGeneratedSource(target, mocsComp, cmQtAutoGen::MOC); - autogenProvides.push_back(mocsComp); + std::string const mocsComp = autogenBuildDir + "/mocs_compilation.cpp"; + auto files = AddGeneratedSource(target, mocsComp, multiConfig, configsList, + cmQtAutoGen::MOC); + for (std::string& file : files) { + autogenProvides.push_back(std::move(file)); + } } // Add autogen includes directory to the origin target INCLUDE_DIRECTORIES if (digest.MocEnabled || digest.UicEnabled) { std::string includeDir = autogenBuildDir + "/include"; - if (multiConfig) { + if (multiConfig != cmQtAutoGen::SINGLE) { includeDir += "_$<CONFIG>"; } target->AddIncludeDirectory(includeDir, true); @@ -671,7 +706,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( std::vector<std::string> generatedSources; std::vector<std::string> generatedHeaders; { - const std::string qrcExt = "qrc"; + std::string const qrcExt = "qrc"; std::vector<cmSourceFile*> srcFiles; target->GetConfigCommonSourceFiles(srcFiles); for (cmSourceFile* sf : srcFiles) { @@ -679,15 +714,15 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( continue; } // sf->GetExtension() is only valid after sf->GetFullPath() ... - const std::string& fPath = sf->GetFullPath(); - const std::string& ext = sf->GetExtension(); + std::string const& fPath = sf->GetFullPath(); + std::string const& ext = sf->GetExtension(); // Register generated files that will be scanned by moc or uic if (digest.MocEnabled || digest.UicEnabled) { - const cmSystemTools::FileFormat fileType = + cmSystemTools::FileFormat const fileType = cmSystemTools::GetFileFormat(ext.c_str()); if ((fileType == cmSystemTools::CXX_FILE_FORMAT) || (fileType == cmSystemTools::HEADER_FILE_FORMAT)) { - const std::string absPath = cmSystemTools::GetRealPath(fPath); + std::string const absPath = cmSystemTools::GetRealPath(fPath); if ((digest.MocEnabled && !sf->GetPropertyAsBool("SKIP_AUTOMOC")) || (digest.UicEnabled && !sf->GetPropertyAsBool("SKIP_AUTOUIC"))) { // Register source @@ -720,7 +755,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( qrcDigest.Generated = sf->GetPropertyAsBool("GENERATED"); // RCC options { - const std::string opts = GetSafeProperty(sf, "AUTORCC_OPTIONS"); + std::string const opts = GetSafeProperty(sf, "AUTORCC_OPTIONS"); if (!opts.empty()) { cmSystemTools::ExpandListArgument(opts, qrcDigest.Options); } @@ -741,7 +776,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( // Check status of policy CMP0071 bool policyAccept = false; bool policyWarn = false; - const cmPolicies::PolicyStatus CMP0071_status = + cmPolicies::PolicyStatus const CMP0071_status = target->Makefile->GetPolicyStatus(cmPolicies::CMP0071); switch (CMP0071_status) { case cmPolicies::WARN: @@ -785,13 +820,13 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( } if (!generatedHeaders.empty()) { msg.append(tools).append(": Ignoring GENERATED header file(s):\n"); - for (const std::string& absFile : generatedHeaders) { + for (std::string const& absFile : generatedHeaders) { msg.append(" ").append(cmQtAutoGen::Quoted(absFile)).append("\n"); } } if (!generatedSources.empty()) { msg.append(tools).append(": Ignoring GENERATED source file(s):\n"); - for (const std::string& absFile : generatedSources) { + for (std::string const& absFile : generatedSources) { msg.append(" ").append(cmQtAutoGen::Quoted(absFile)).append("\n"); } } @@ -806,7 +841,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( // Process qrc files if (!digest.Qrcs.empty()) { const bool QtV5 = (digest.QtVersionMajor == "5"); - const std::string rcc = RccGetExecutable(target, digest.QtVersionMajor); + std::string const rcc = RccGetExecutable(target, digest.QtVersionMajor); // Target rcc options std::vector<std::string> optionsTarget; cmSystemTools::ExpandListArgument( @@ -825,7 +860,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( } // Path checksum { - const cmFilePathChecksum fpathCheckSum(makefile); + cmFilePathChecksum const fpathCheckSum(makefile); for (cmQtAutoGenDigestQrc& qrcDigest : digest.Qrcs) { qrcDigest.PathChecksum = fpathCheckSum.getPart(qrcDigest.QrcFile); // RCC output file name @@ -861,8 +896,13 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( } for (cmQtAutoGenDigestQrc& qrcDigest : digest.Qrcs) { // Register file at target - AddGeneratedSource(target, qrcDigest.RccFile, cmQtAutoGen::RCC); - autogenProvides.push_back(qrcDigest.RccFile); + { + auto files = AddGeneratedSource(target, qrcDigest.RccFile, multiConfig, + configsList, cmQtAutoGen::RCC); + for (std::string& file : files) { + autogenProvides.push_back(std::move(file)); + } + } // Dependencies if (qrcDigest.Generated) { // Add the GENERATED .qrc file to the dependencies @@ -889,7 +929,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( // Add user defined autogen target dependencies { - const std::string deps = GetSafeProperty(target, "AUTOGEN_TARGET_DEPENDS"); + std::string const deps = GetSafeProperty(target, "AUTOGEN_TARGET_DEPENDS"); if (!deps.empty()) { std::vector<std::string> extraDeps; cmSystemTools::ExpandListArgument(deps, extraDeps); @@ -924,7 +964,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( // Create the autogen target/command if (usePRE_BUILD) { // Add additional autogen target dependencies to origin target - for (const std::string& depTarget : autogenDependTargets) { + for (std::string const& depTarget : autogenDependTargets) { target->Target->AddUtility(depTarget, makefile); } @@ -944,7 +984,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( } else { // Add utility target dependencies to the autogen target dependencies - for (const std::string& depTarget : target->Target->GetUtilities()) { + for (std::string const& depTarget : target->Target->GetUtilities()) { autogenDependTargets.insert(depTarget); } // Add link library target dependencies to the autogen target dependencies @@ -967,7 +1007,7 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( new cmGeneratorTarget(autogenTarget, localGen)); // Add additional autogen target dependencies to autogen target - for (const std::string& depTarget : autogenDependTargets) { + for (std::string const& depTarget : autogenDependTargets) { autogenTarget->AddUtility(depTarget, makefile); } @@ -994,45 +1034,51 @@ void cmQtAutoGeneratorInitializer::InitializeAutogenTarget( } void cmQtAutoGeneratorInitializer::SetupAutoGenerateTarget( - const cmQtAutoGenDigest& digest) + cmQtAutoGenDigest const& digest) { cmGeneratorTarget const* target = digest.Target; cmMakefile* makefile = target->Target->GetMakefile(); + cmQtAutoGen::MultiConfig const multiConfig = + AutogenMultiConfig(target->GetGlobalGenerator()); // forget the variables added here afterwards again: cmMakefile::ScopePushPop varScope(makefile); static_cast<void>(varScope); - // Get configurations - std::string config; - const std::vector<std::string> configs(GetConfigurations(makefile, &config)); - - // Configuration suffixes - std::map<std::string, std::string> configSuffix; - if (AutogenMultiConfig(target->GetGlobalGenerator())) { - for (std::string const& cfg : configs) { - configSuffix[cfg] = "_" + cfg; + // Configurations + std::string configDefault; + std::vector<std::string> configsList; + std::map<std::string, std::string> configSuffixes; + { + configDefault = makefile->GetConfigurations(configsList); + if (configsList.empty()) { + configsList.push_back(""); } } + for (std::string const& cfg : configsList) { + configSuffixes[cfg] = "_" + cfg; + } // Configurations settings buffers cmQtAutoGenSetup setup; // Basic setup + AddDefinitionEscaped(makefile, "_multi_config", + cmQtAutoGen::MultiConfigName(multiConfig)); AddDefinitionEscaped(makefile, "_build_dir", GetAutogenTargetBuildDir(target)); - AddDefinitionEscaped(makefile, "_qt_version_major", digest.QtVersionMajor); - AddDefinitionEscaped(makefile, "_qt_version_minor", digest.QtVersionMinor); AddDefinitionEscaped(makefile, "_sources", digest.Sources); AddDefinitionEscaped(makefile, "_headers", digest.Headers); + AddDefinitionEscaped(makefile, "_qt_version_major", digest.QtVersionMajor); + AddDefinitionEscaped(makefile, "_qt_version_minor", digest.QtVersionMinor); { if (digest.MocEnabled || digest.UicEnabled) { SetupAcquireSkipFiles(digest, setup); if (digest.MocEnabled) { - SetupAutoTargetMoc(digest, config, configs, setup); + SetupAutoTargetMoc(digest, configDefault, configsList, setup); } if (digest.UicEnabled) { - SetupAutoTargetUic(digest, config, configs, setup); + SetupAutoTargetUic(digest, configDefault, configsList, setup); } } if (digest.RccEnabled) { @@ -1041,17 +1087,18 @@ void cmQtAutoGeneratorInitializer::SetupAutoGenerateTarget( } // Generate info file - std::string infoFile = GetAutogenTargetFilesDir(target); - infoFile += "/AutogenInfo.cmake"; { - std::string inf = cmSystemTools::GetCMakeRoot(); - inf += "/Modules/AutogenInfo.cmake.in"; - makefile->ConfigureFile(inf.c_str(), infoFile.c_str(), false, true, false); - } + std::string infoFile = GetAutogenTargetFilesDir(target); + infoFile += "/AutogenInfo.cmake"; + { + std::string infoFileIn = cmSystemTools::GetCMakeRoot(); + infoFileIn += "/Modules/AutogenInfo.cmake.in"; + makefile->ConfigureFile(infoFileIn.c_str(), infoFile.c_str(), false, + true, false); + } - // Append custom definitions to info file on demand - if (!configSuffix.empty() || !setup.ConfigMocDefines.empty() || - !setup.ConfigMocIncludes.empty() || !setup.ConfigUicOptions.empty()) { + // Append custom definitions to info file + // -------------------------------------- // Ensure we have write permission in case .in was read-only. mode_t perm = 0; @@ -1069,14 +1116,14 @@ void cmQtAutoGeneratorInitializer::SetupAutoGenerateTarget( cmsys::ofstream ofs(infoFile.c_str(), std::ios::app); if (ofs) { auto OfsWriteMap = [&ofs]( - const char* key, const std::map<std::string, std::string>& map) { + const char* key, std::map<std::string, std::string> const& map) { for (auto const& item : map) { ofs << "set(" << key << "_" << item.first << " " << cmOutputConverter::EscapeForCMake(item.second) << ")\n"; } }; - ofs << "# Configuration specific options\n"; - OfsWriteMap("AM_CONFIG_SUFFIX", configSuffix); + ofs << "# Configurations options\n"; + OfsWriteMap("AM_CONFIG_SUFFIX", configSuffixes); OfsWriteMap("AM_MOC_DEFINITIONS", setup.ConfigMocDefines); OfsWriteMap("AM_MOC_INCLUDES", setup.ConfigMocIncludes); OfsWriteMap("AM_UIC_TARGET_OPTIONS", setup.ConfigUicOptions); diff --git a/Source/cmQtAutoGeneratorInitializer.h b/Source/cmQtAutoGeneratorInitializer.h index 1264ca5..b8a5ae4 100644 --- a/Source/cmQtAutoGeneratorInitializer.h +++ b/Source/cmQtAutoGeneratorInitializer.h @@ -15,7 +15,7 @@ class cmQtAutoGeneratorInitializer public: static std::string GetQtMajorVersion(cmGeneratorTarget const* target); static std::string GetQtMinorVersion(cmGeneratorTarget const* target, - const std::string& qtVersionMajor); + std::string const& qtVersionMajor); static void InitializeAutogenTarget(cmQtAutoGenDigest& digest); static void SetupAutoGenerateTarget(cmQtAutoGenDigest const& digest); diff --git a/Source/cmQtAutoGenerators.cxx b/Source/cmQtAutoGenerators.cxx index 4faa409..bd0fb9a 100644 --- a/Source/cmQtAutoGenerators.cxx +++ b/Source/cmQtAutoGenerators.cxx @@ -131,7 +131,8 @@ static bool ListContains(std::vector<std::string> const& list, // -- Class methods cmQtAutoGenerators::cmQtAutoGenerators() - : IncludeProjectDirsBefore(false) + : MultiConfig(cmQtAutoGen::WRAP) + , IncludeProjectDirsBefore(false) , Verbose(cmSystemTools::HasEnv("VERBOSE")) , ColorOutput(true) , MocSettingsChanged(false) @@ -196,6 +197,9 @@ bool cmQtAutoGenerators::InitInfoFile(cmMakefile* makefile, std::string const& targetDirectory, std::string const& config) { + // -- Meta + this->HeaderExtensions = makefile->GetCMakeInstance()->GetHeaderExtensions(); + // Utility lambdas auto InfoGet = [makefile](const char* key) { return makefile->GetSafeDefinition(key); @@ -239,10 +243,8 @@ bool cmQtAutoGenerators::InitInfoFile(cmMakefile* makefile, const char* valueConf = nullptr; { std::string keyConf = key; - if (!config.empty()) { - keyConf += '_'; - keyConf += config; - } + keyConf += '_'; + keyConf += config; valueConf = makefile->GetDefinition(keyConf); } if (valueConf == nullptr) { @@ -257,10 +259,10 @@ bool cmQtAutoGenerators::InitInfoFile(cmMakefile* makefile, return list; }; + // -- Read info file this->InfoFile = cmSystemTools::CollapseFullPath(targetDirectory); cmSystemTools::ConvertToUnixSlashes(this->InfoFile); this->InfoFile += "/AutogenInfo.cmake"; - if (!makefile->ReadListFile(this->InfoFile.c_str())) { this->LogFileError(cmQtAutoGen::GEN, this->InfoFile, "File processing failed"); @@ -268,16 +270,11 @@ bool cmQtAutoGenerators::InitInfoFile(cmMakefile* makefile, } // -- Meta - this->HeaderExtensions = makefile->GetCMakeInstance()->GetHeaderExtensions(); + this->MultiConfig = cmQtAutoGen::MultiConfigType(InfoGet("AM_MULTI_CONFIG")); this->ConfigSuffix = InfoGetConfig("AM_CONFIG_SUFFIX"); - - // - Old settings file - { - this->SettingsFile = cmSystemTools::CollapseFullPath(targetDirectory); - cmSystemTools::ConvertToUnixSlashes(this->SettingsFile); - this->SettingsFile += "/AutogenOldSettings"; - this->SettingsFile += this->ConfigSuffix; - this->SettingsFile += ".cmake"; + if (this->ConfigSuffix.empty()) { + this->ConfigSuffix = "_"; + this->ConfigSuffix += config; } // - Files and directories @@ -499,19 +496,28 @@ bool cmQtAutoGenerators::InitInfoFile(cmMakefile* makefile, // include directory this->AutogenIncludeDir = "include"; - this->AutogenIncludeDir += this->ConfigSuffix; + if (this->MultiConfig != cmQtAutoGen::SINGLE) { + this->AutogenIncludeDir += this->ConfigSuffix; + } this->AutogenIncludeDir += "/"; + // Moc variables if (this->MocEnabled()) { // Mocs compilation file - this->MocCompFileRel = "mocs_compilation.cpp"; + this->MocCompFileRel = "mocs_compilation"; + if (this->MultiConfig == cmQtAutoGen::FULL) { + this->MocCompFileRel += this->ConfigSuffix; + } + this->MocCompFileRel += ".cpp"; this->MocCompFileAbs = cmSystemTools::CollapseCombinedPath( this->AutogenBuildDir, this->MocCompFileRel); // Moc predefs file if (!this->MocPredefsCmd.empty()) { this->MocPredefsFileRel = "moc_predefs"; - this->MocPredefsFileRel += this->ConfigSuffix; + if (this->MultiConfig != cmQtAutoGen::SINGLE) { + this->MocPredefsFileRel += this->ConfigSuffix; + } this->MocPredefsFileRel += ".h"; this->MocPredefsFileAbs = cmSystemTools::CollapseCombinedPath( this->AutogenBuildDir, this->MocPredefsFileRel); @@ -585,6 +591,17 @@ bool cmQtAutoGenerators::InitInfoFile(cmMakefile* makefile, } } + // - Old settings file + { + this->SettingsFile = cmSystemTools::CollapseFullPath(targetDirectory); + cmSystemTools::ConvertToUnixSlashes(this->SettingsFile); + this->SettingsFile += "/AutogenOldSettings"; + if (this->MultiConfig != cmQtAutoGen::SINGLE) { + this->SettingsFile += this->ConfigSuffix; + } + this->SettingsFile += ".cmake"; + } + return true; } @@ -1299,18 +1316,18 @@ void cmQtAutoGenerators::MocParseHeaderContent(std::string const& absFilename, }); if (fit == this->MocJobsIncluded.cend()) { if (this->MocRequired(contentText)) { - static std::string const prefix = "moc_"; - static std::string const suffix = this->ConfigSuffix + ".cpp"; - auto job = cm::make_unique<MocJobAuto>(); job->SourceFile = absFilename; { std::string& bld = job->BuildFileRel; bld = this->FilePathChecksum.getPart(absFilename); - bld += "/"; - bld += prefix; + bld += '/'; + bld += "moc_"; bld += cmSystemTools::GetFilenameWithoutLastExtension(absFilename); - bld += suffix; + if (this->MultiConfig != cmQtAutoGen::SINGLE) { + bld += this->ConfigSuffix; + } + bld += ".cpp"; } this->MocFindDepends(absFilename, contentText, job->Depends); this->MocJobsAuto.push_back(std::move(job)); @@ -1437,9 +1454,12 @@ bool cmQtAutoGenerators::MocGenerateAll() // Compose mocs compilation file content { - std::string mocs = "/* This file is autogenerated, do not edit*/\n"; + std::string mocs = + "// This file is autogenerated. Changes will be overwritten.\n"; if (this->MocJobsAuto.empty()) { - // Dummy content + // Placeholder content + mocs += + "// No files found that require moc or the moc files are included\n"; mocs += "enum some_compilers { need_more_than_nothing };\n"; } else { // Valid content @@ -1917,14 +1937,11 @@ bool cmQtAutoGenerators::RccGenerateFile(const RccJob& rccJob) bool rccGenerated = false; std::string rccFileAbs; - if (this->ConfigSuffix.empty()) { + if (this->MultiConfig == cmQtAutoGen::SINGLE) { rccFileAbs = rccJob.RccFile; } else { - rccFileAbs = SubDirPrefix(rccJob.RccFile); - rccFileAbs += - cmSystemTools::GetFilenameWithoutLastExtension(rccJob.RccFile); - rccFileAbs += this->ConfigSuffix; - rccFileAbs += cmSystemTools::GetFilenameLastExtension(rccJob.RccFile); + rccFileAbs = + cmQtAutoGen::AppendFilenameSuffix(rccJob.RccFile, this->ConfigSuffix); } std::string const rccFileRel = cmSystemTools::RelativePath( this->AutogenBuildDir.c_str(), rccFileAbs.c_str()); @@ -2064,15 +2081,16 @@ bool cmQtAutoGenerators::RccGenerateFile(const RccJob& rccJob) success = false; } } - // For a multi configuration generator generate a wrapper file - if (success && !this->ConfigSuffix.empty()) { + + // Generate a wrapper source file on demand + if (success && (this->MultiConfig == cmQtAutoGen::WRAP)) { // Wrapper file name std::string const& wrapperFileAbs = rccJob.RccFile; std::string const wrapperFileRel = cmSystemTools::RelativePath( this->AutogenBuildDir.c_str(), wrapperFileAbs.c_str()); // Wrapper file content std::string content = "// This is an autogenerated configuration " - "wrapper file. Do not edit.\n" + "wrapper file. Changes will be overwritten.\n" "#include \""; content += cmSystemTools::GetFilenameName(rccFileRel); content += "\"\n"; diff --git a/Source/cmQtAutoGenerators.h b/Source/cmQtAutoGenerators.h index ad95700..a7bb538 100644 --- a/Source/cmQtAutoGenerators.h +++ b/Source/cmQtAutoGenerators.h @@ -183,8 +183,9 @@ private: std::string& output) const; // -- Meta - std::string ConfigSuffix; std::string InfoFile; + std::string ConfigSuffix; + cmQtAutoGen::MultiConfig MultiConfig; // -- Settings bool IncludeProjectDirsBefore; bool Verbose; |