From 0656bebeaecb85c2297b3d87634aed6ce8a80f34 Mon Sep 17 00:00:00 2001 From: Duncan Barber <7744-dunquan@users.noreply.gitlab.kitware.com> Date: Sat, 3 Apr 2021 11:49:11 +0100 Subject: Autogen: Rename the variable for UI files with UIC options Monitoring for UI file changes in the target sources will require keeping track of the files without options as well so this will improve clarity. --- Source/cmQtAutoGenInitializer.cxx | 5 +++-- Source/cmQtAutoGenInitializer.h | 2 +- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/Source/cmQtAutoGenInitializer.cxx b/Source/cmQtAutoGenInitializer.cxx index e96ec63..f0c799e 100644 --- a/Source/cmQtAutoGenInitializer.cxx +++ b/Source/cmQtAutoGenInitializer.cxx @@ -936,7 +936,8 @@ bool cmQtAutoGenInitializer::InitScanFiles() // Check if the .ui file has uic options std::string const uicOpts = sf->GetSafeProperty(kw.AUTOUIC_OPTIONS); if (!uicOpts.empty()) { - this->Uic.UiFiles.emplace_back(fullPath, cmExpandedList(uicOpts)); + this->Uic.UiFilesWithOptions.emplace_back(fullPath, + cmExpandedList(uicOpts)); } auto uiHeaderRelativePath = cmSystemTools::RelativePath( @@ -1626,7 +1627,7 @@ bool cmQtAutoGenInitializer::SetupWriteAutogenInfo() uic_skip.insert(this->Uic.SkipUi.begin(), this->Uic.SkipUi.end()); info.SetArray("UIC_SKIP", uic_skip); - info.SetArrayArray("UIC_UI_FILES", this->Uic.UiFiles, + info.SetArrayArray("UIC_UI_FILES", this->Uic.UiFilesWithOptions, [](Json::Value& jval, UicT::UiFileT const& uiFile) { jval.resize(2u); jval[0u] = uiFile.first; diff --git a/Source/cmQtAutoGenInitializer.h b/Source/cmQtAutoGenInitializer.h index fdb65d3..9fe0cf0 100644 --- a/Source/cmQtAutoGenInitializer.h +++ b/Source/cmQtAutoGenInitializer.h @@ -236,7 +236,7 @@ private: : GenVarsT(GenT::UIC){}; std::set SkipUi; - std::vector UiFiles; + std::vector UiFilesWithOptions; ConfigStrings> Options; std::vector SearchPaths; std::vector> -- cgit v0.12 From 087b717aefd5439fc5bc6ae25b9795cbb5563e02 Mon Sep 17 00:00:00 2001 From: Duncan Barber <7744-dunquan@users.noreply.gitlab.kitware.com> Date: Sat, 3 Apr 2021 19:52:53 +0100 Subject: Autogen: Move duplicated executable dependency code into a function --- Source/cmQtAutoGenInitializer.cxx | 23 +++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/Source/cmQtAutoGenInitializer.cxx b/Source/cmQtAutoGenInitializer.cxx index f0c799e..a1602bd 100644 --- a/Source/cmQtAutoGenInitializer.cxx +++ b/Source/cmQtAutoGenInitializer.cxx @@ -294,6 +294,17 @@ bool InfoWriter::Save(std::string const& filename) return fileStream.Close(); } +void AddAutogenExecutableToDependencies( + cmQtAutoGenInitializer::GenVarsT const& genVars, + std::vector& dependencies) +{ + if (genVars.ExecutableTarget != nullptr) { + dependencies.push_back(genVars.ExecutableTarget->Target->GetName()); + } else if (!genVars.Executable.empty()) { + dependencies.push_back(genVars.Executable); + } +} + } // End of unnamed namespace cmQtAutoGenInitializer::cmQtAutoGenInitializer( @@ -1279,16 +1290,8 @@ bool cmQtAutoGenInitializer::InitAutogenTarget() dependencies.clear(); dependencies.push_back(timestampTargetName); - if (this->Moc.ExecutableTarget != nullptr) { - dependencies.push_back(this->Moc.ExecutableTarget->Target->GetName()); - } else if (!this->Moc.Executable.empty()) { - dependencies.push_back(this->Moc.Executable); - } - if (this->Uic.ExecutableTarget != nullptr) { - dependencies.push_back(this->Uic.ExecutableTarget->Target->GetName()); - } else if (!this->Uic.Executable.empty()) { - dependencies.push_back(this->Uic.Executable); - } + AddAutogenExecutableToDependencies(this->Moc, dependencies); + AddAutogenExecutableToDependencies(this->Uic, dependencies); // Create the custom command that outputs the timestamp file. const char timestampFileName[] = "timestamp"; -- cgit v0.12 From 1876f2d03fe3ccc4ea02c27fe345657b3366b48e Mon Sep 17 00:00:00 2001 From: Duncan Barber <7744-dunquan@users.noreply.gitlab.kitware.com> Date: Sat, 10 Apr 2021 15:04:22 +0100 Subject: Autogen: Move duplicated filename generation code into a function --- Source/cmQtAutoGenInitializer.cxx | 47 +++++++++++++++++---------------------- Source/cmQtAutoGenInitializer.h | 2 ++ 2 files changed, 23 insertions(+), 26 deletions(-) diff --git a/Source/cmQtAutoGenInitializer.cxx b/Source/cmQtAutoGenInitializer.cxx index a1602bd..816d7e5 100644 --- a/Source/cmQtAutoGenInitializer.cxx +++ b/Source/cmQtAutoGenInitializer.cxx @@ -430,12 +430,8 @@ bool cmQtAutoGenInitializer::InitCustomTargets() cmSystemTools::ConvertToUnixSlashes(this->Dir.Work); // Include directory - this->ConfigFileNames(this->Dir.Include, - cmStrCat(this->Dir.Build, "/include"), ""); - this->Dir.IncludeGenExp = this->Dir.Include.Default; - if (this->MultiConfig) { - this->Dir.IncludeGenExp += "_$"; - } + this->ConfigFileNamesAndGenex(this->Dir.Include, this->Dir.IncludeGenExp, + cmStrCat(this->Dir.Build, "/include"), ""); } // Moc, Uic and _autogen target settings @@ -586,15 +582,9 @@ bool cmQtAutoGenInitializer::InitMoc() cmStrCat(this->Dir.Build, "/mocs_compilation.cpp"); this->Moc.CompilationFileGenex = this->Moc.CompilationFile.Default; } else { - this->ConfigFileNames(this->Moc.CompilationFile, - cmStrCat(this->Dir.Build, "/mocs_compilation"), - ".cpp"); - if (this->MultiConfig) { - this->Moc.CompilationFileGenex = - cmStrCat(this->Dir.Build, "/mocs_compilation_$.cpp"_s); - } else { - this->Moc.CompilationFileGenex = this->Moc.CompilationFile.Default; - } + this->ConfigFileNamesAndGenex( + this->Moc.CompilationFile, this->Moc.CompilationFileGenex, + cmStrCat(this->Dir.Build, "/mocs_compilation"_s), ".cpp"_s); } // Moc predefs @@ -966,17 +956,10 @@ bool cmQtAutoGenInitializer::InitScanFiles() cmSystemTools::GetFilenameWithoutLastExtension(fullPath), ".h"_s); ConfigString uiHeader; - uiHeader.Default = - cmStrCat(this->Dir.Build, "/include"_s, uiHeaderFilePath); - auto uiHeaderGenex = uiHeader.Default; - if (this->MultiConfig) { - uiHeaderGenex = cmStrCat(this->Dir.Build, "/include_$"_s, - uiHeaderFilePath); - for (std::string const& cfg : this->ConfigsList) { - uiHeader.Config[cfg] = cmStrCat(this->Dir.Build, "/include_"_s, - cfg, uiHeaderFilePath); - } - } + std::string uiHeaderGenex; + this->ConfigFileNamesAndGenex( + uiHeader, uiHeaderGenex, cmStrCat(this->Dir.Build, "/include"_s), + uiHeaderFilePath); this->Uic.UiHeaders.emplace_back( std::make_pair(uiHeader, uiHeaderGenex)); @@ -1790,6 +1773,18 @@ void cmQtAutoGenInitializer::ConfigFileNames(ConfigString& configString, } } +void cmQtAutoGenInitializer::ConfigFileNamesAndGenex( + ConfigString& configString, std::string& genex, cm::string_view const prefix, + cm::string_view const suffix) +{ + this->ConfigFileNames(configString, prefix, suffix); + if (this->MultiConfig) { + genex = cmStrCat(prefix, "_$"_s, suffix); + } else { + genex = configString.Default; + } +} + void cmQtAutoGenInitializer::ConfigFileClean(ConfigString& configString) { this->AddCleanFile(configString.Default); diff --git a/Source/cmQtAutoGenInitializer.h b/Source/cmQtAutoGenInitializer.h index 9fe0cf0..d096315 100644 --- a/Source/cmQtAutoGenInitializer.h +++ b/Source/cmQtAutoGenInitializer.h @@ -141,6 +141,8 @@ private: void ConfigFileNames(ConfigString& configString, cm::string_view prefix, cm::string_view suffix); + void ConfigFileNamesAndGenex(ConfigString& configString, std::string& genex, + cm::string_view prefix, cm::string_view suffix); void ConfigFileClean(ConfigString& configString); std::string GetMocBuildPath(MUFile const& muf); -- cgit v0.12 From a8d879cf4507f0460dd8386a10c3b4ffe79c3566 Mon Sep 17 00:00:00 2001 From: Duncan Barber <7744-dunquan@users.noreply.gitlab.kitware.com> Date: Sat, 3 Apr 2021 11:53:53 +0100 Subject: Autogen: Add detection of UI file changes to the pre-build VS case This is achieved by adding a rule file which carries the UI files as dependencies but performs no meaningful command. Its output path points to a timestamp file which is instead touched by the pre-build command that runs autogen. The rule file therefore triggers the build if any of the files have been changed more recently than the last autogen run. Fixes: #17959 Fixes: #18741 --- Source/cmQtAutoGenInitializer.cxx | 40 ++++++++++++++++++++++++++++++++++++++- Source/cmQtAutoGenInitializer.h | 1 + 2 files changed, 40 insertions(+), 1 deletion(-) diff --git a/Source/cmQtAutoGenInitializer.cxx b/Source/cmQtAutoGenInitializer.cxx index 816d7e5..3adeb1a 100644 --- a/Source/cmQtAutoGenInitializer.cxx +++ b/Source/cmQtAutoGenInitializer.cxx @@ -936,7 +936,9 @@ bool cmQtAutoGenInitializer::InitScanFiles() if (!skipUic) { // Check if the .ui file has uic options std::string const uicOpts = sf->GetSafeProperty(kw.AUTOUIC_OPTIONS); - if (!uicOpts.empty()) { + if (uicOpts.empty()) { + this->Uic.UiFilesNoOptions.emplace_back(fullPath); + } else { this->Uic.UiFilesWithOptions.emplace_back(fullPath, cmExpandedList(uicOpts)); } @@ -1181,6 +1183,42 @@ bool cmQtAutoGenInitializer::InitAutogenTarget() this->Makefile); } + if (!this->Uic.UiFilesNoOptions.empty() || + !this->Uic.UiFilesWithOptions.empty()) { + // Add a generated timestamp file + ConfigString timestampFile; + std::string timestampFileGenex; + ConfigFileNamesAndGenex(timestampFile, timestampFileGenex, + cmStrCat(this->Dir.Build, "/autouic"_s), + ".stamp"_s); + this->AddGeneratedSource(timestampFile, this->Uic); + + // Add a step in the pre-build command to touch the timestamp file + commandLines.push_back( + cmMakeCommandLine({ cmSystemTools::GetCMakeCommand(), "-E", "touch", + timestampFileGenex })); + + // UIC needs to be re-run if any of the known UI files change or the + // executable itself has been updated + auto uicDependencies = this->Uic.UiFilesNoOptions; + for (auto const& uiFile : this->Uic.UiFilesWithOptions) { + uicDependencies.push_back(uiFile.first); + } + AddAutogenExecutableToDependencies(this->Uic, uicDependencies); + + // Add a rule file to cause the target to build if a dependency has + // changed, which will trigger the pre-build command to run autogen + std::string no_main_dependency; + cmCustomCommandLines no_command_lines; + this->LocalGen->AddCustomCommandToOutput( + timestampFileGenex, uicDependencies, no_main_dependency, + no_command_lines, /*comment=*/"", this->Dir.Work.c_str(), + /*cmp0116=*/cmPolicies::NEW, /*replace=*/false, + /*escapeOldStyle=*/false, /*uses_terminal=*/false, + /*command_expand_lists=*/false, /*depfile=*/"", /*job_pool=*/"", + stdPipesUTF8); + } + // Add the pre-build command directly to bypass the OBJECT_LIBRARY // rejection in cmMakefile::AddCustomCommandToTarget because we know // PRE_BUILD will work for an OBJECT_LIBRARY in this specific case. diff --git a/Source/cmQtAutoGenInitializer.h b/Source/cmQtAutoGenInitializer.h index d096315..8a6d8f9 100644 --- a/Source/cmQtAutoGenInitializer.h +++ b/Source/cmQtAutoGenInitializer.h @@ -238,6 +238,7 @@ private: : GenVarsT(GenT::UIC){}; std::set SkipUi; + std::vector UiFilesNoOptions; std::vector UiFilesWithOptions; ConfigStrings> Options; std::vector SearchPaths; -- cgit v0.12