فهرست منبع

Autogen: Add timestamp file for CMAKE_GLOBAL_AUTORCC_TARGET

When `CMAKE_GLOBAL_AUTORCC_TARGET` is ON and qrc files are not
generated, `<target_name>_arcc_data` is always dirty. So this commit
adds a timestamp file which depens on what `<target_name>_arcc_data`
depends before and ``<target_name>_arcc_data` depends the timestamp
file.

The dependency graph before
(qrcFile, InfoFile) -> _arcc_target

The dependency graph after
(qrcFile, InfoFile) -> global_rcc_timestamp ->_arcc_target

Fixes: #26059
Orkun Tokdemir 1 سال پیش
والد
کامیت
8d99e71b7e
2فایلهای تغییر یافته به همراه53 افزوده شده و 7 حذف شده
  1. 37 7
      Source/cmQtAutoGenInitializer.cxx
  2. 16 0
      Tests/RunCMake/Autogen_5/RunCMakeTest.cmake

+ 37 - 7
Source/cmQtAutoGenInitializer.cxx

@@ -1697,13 +1697,43 @@ bool cmQtAutoGenInitializer::InitRccTargets()
         if (!qrc.Unique) {
           ccName += cmStrCat('_', qrc.QrcPathChecksum);
         }
-
-        cc->SetByproducts(ccOutput);
-        cc->SetDepends(ccDepends);
-        cc->SetEscapeOldStyle(false);
-        cmTarget* autoRccTarget =
-          this->LocalGen->AddUtilityCommand(ccName, true, std::move(cc));
-
+        cmTarget* autoRccTarget = nullptr;
+        // When CMAKE_GLOBAL_AUTORCC_TARGET is ON and qrc is not generated,
+        // Add generate a timestamp file and a custom command to touch it.
+        // This will ensure that the global autorcc target is run only when the
+        // qrc file changes.
+        if (!qrc.Generated && this->Rcc.GlobalTarget) {
+          cm::string_view const timestampFileName = "global_rcc_timestamp";
+          auto const outputFile =
+            cmStrCat(this->Dir.Build, "/", timestampFileName);
+          commandLines.push_back(cmMakeCommandLine(
+            { cmSystemTools::GetCMakeCommand(), "-E", "touch", outputFile }));
+          cc->SetByproducts(ccOutput);
+          cc->SetDepends(ccDepends);
+          cc->SetEscapeOldStyle(false);
+          cc->SetOutputs(outputFile);
+          cc->SetCommandLines(commandLines);
+          this->LocalGen->AddCustomCommandToOutput(std::move(cc));
+          this->AddGeneratedSource(outputFile, this->Rcc);
+          ccDepends.clear();
+          ccDepends.push_back(outputFile);
+
+          auto ccRccTarget = cm::make_unique<cmCustomCommand>();
+          ccRccTarget->SetWorkingDirectory(this->Dir.Work.c_str());
+          ccRccTarget->SetComment(ccComment.c_str());
+          ccRccTarget->SetStdPipesUTF8(true);
+          ccRccTarget->SetDepends(ccDepends);
+          ccRccTarget->SetEscapeOldStyle(false);
+
+          autoRccTarget = this->LocalGen->AddUtilityCommand(
+            ccName, true, std::move(ccRccTarget));
+        } else {
+          cc->SetByproducts(ccOutput);
+          cc->SetDepends(ccDepends);
+          cc->SetEscapeOldStyle(false);
+          autoRccTarget =
+            this->LocalGen->AddUtilityCommand(ccName, true, std::move(cc));
+        }
         // Create autogen generator target
         this->LocalGen->AddGeneratorTarget(
           cm::make_unique<cmGeneratorTarget>(autoRccTarget, this->LocalGen));

+ 16 - 0
Tests/RunCMake/Autogen_5/RunCMakeTest.cmake

@@ -27,5 +27,21 @@ if (DEFINED with_qt_version)
         endblock()
       endforeach()
     endif()
+    if (RunCMake_GENERATOR MATCHES "Ninja")
+      block()
+        set(RunCMake_TEST_BINARY_DIR
+          ${RunCMake_BINARY_DIR}/RccGlobalAutoRcc-build)
+        run_cmake_with_options(RccExample ${RunCMake_TEST_OPTIONS}
+          -DCMAKE_GLOBAL_AUTORCC_TARGET=ON)
+        set(RunCMake_TEST_NO_CLEAN 1)
+        set(RunCMake_TEST_VARIANT_DESCRIPTION "-First-build")
+        run_cmake_command(RccGlobalAutoRcc-build ${CMAKE_COMMAND}
+          --build . --config Debug)
+        set(RunCMake_TEST_VARIANT_DESCRIPTION "-Second-build-nothing-to-do")
+        set(RunCMake_TEST_NOT_EXPECT_stdout "Automatic RCC for data.qrc")
+        run_cmake_command(RccGlobalAutoRcc-build ${CMAKE_COMMAND}
+          --build . --config Debug)
+      endblock()
+    endif()
   endif()
 endif ()