Selaa lähdekoodia

Display subproject timing summary

Use the '--no-subproject-summary' option to disable timing summary.
Betsy McPhail 8 vuotta sitten
vanhempi
sitoutus
47b3a57c9b

+ 7 - 0
Help/manual/ctest.1.rst

@@ -250,6 +250,13 @@ Options
  label associated with the tests run.  If there are no labels on the
  label associated with the tests run.  If there are no labels on the
  tests, nothing extra is printed.
  tests, nothing extra is printed.
 
 
+ ``--no-subproject-summary``
+ Disable timing summary information for subprojects.
+
+ This option tells ctest not to print summary information for each
+ subproject associated with the tests run.  If there are no subprojects on the
+ tests, nothing extra is printed.
+
 ``--build-and-test <path-to-source> <path-to-build>``
 ``--build-and-test <path-to-source> <path-to-build>``
  Configure, build and run a test.
  Configure, build and run a test.
 
 

+ 84 - 1
Source/CTest/cmCTestTestHandler.cxx

@@ -536,9 +536,14 @@ int cmCTestTestHandler::ProcessHandler()
                  << static_cast<int>(percent + .5f) << "% tests passed, "
                  << static_cast<int>(percent + .5f) << "% tests passed, "
                  << failed.size() << " tests failed out of " << total
                  << failed.size() << " tests failed out of " << total
                  << std::endl);
                  << std::endl);
-    if (this->CTest->GetLabelSummary()) {
+
+    if (!this->CTest->GetLabelsForSubprojects().empty() &&
+        this->CTest->GetSubprojectSummary()) {
+      this->PrintSubprojectSummary();
+    } else if (this->CTest->GetLabelSummary()) {
       this->PrintLabelSummary();
       this->PrintLabelSummary();
     }
     }
+
     char realBuf[1024];
     char realBuf[1024];
     sprintf(realBuf, "%6.2f sec", (double)(clock_finish - clock_start));
     sprintf(realBuf, "%6.2f sec", (double)(clock_finish - clock_start));
     cmCTestOptionalLog(this->CTest, HANDLER_OUTPUT,
     cmCTestOptionalLog(this->CTest, HANDLER_OUTPUT,
@@ -688,6 +693,84 @@ void cmCTestTestHandler::PrintLabelSummary()
   }
   }
 }
 }
 
 
+void cmCTestTestHandler::PrintSubprojectSummary()
+{
+  std::vector<std::string> subprojects =
+    this->CTest->GetLabelsForSubprojects();
+
+  cmCTestTestHandler::ListOfTests::iterator it = this->TestList.begin();
+  std::map<std::string, double> labelTimes;
+  std::map<std::string, int> labelCounts;
+  std::set<std::string> labels;
+  // initialize maps
+  std::string::size_type maxlen = 0;
+  for (; it != this->TestList.end(); ++it) {
+    cmCTestTestProperties& p = *it;
+    for (std::vector<std::string>::iterator l = p.Labels.begin();
+         l != p.Labels.end(); ++l) {
+      std::vector<std::string>::iterator subproject =
+        std::find(subprojects.begin(), subprojects.end(), *l);
+      if (subproject != subprojects.end()) {
+        if ((*l).size() > maxlen) {
+          maxlen = (*l).size();
+        }
+        labels.insert(*l);
+        labelTimes[*l] = 0;
+        labelCounts[*l] = 0;
+      }
+    }
+  }
+  cmCTestTestHandler::TestResultsVector::iterator ri =
+    this->TestResults.begin();
+  // fill maps
+  for (; ri != this->TestResults.end(); ++ri) {
+    cmCTestTestResult& result = *ri;
+    cmCTestTestProperties& p = *result.Properties;
+    for (std::vector<std::string>::iterator l = p.Labels.begin();
+         l != p.Labels.end(); ++l) {
+      std::vector<std::string>::iterator subproject =
+        std::find(subprojects.begin(), subprojects.end(), *l);
+      if (subproject != subprojects.end()) {
+        labelTimes[*l] += result.ExecutionTime;
+        ++labelCounts[*l];
+      }
+    }
+  }
+  // now print times
+  if (!labels.empty()) {
+    cmCTestOptionalLog(this->CTest, HANDLER_OUTPUT,
+                       "\nSubproject Time Summary:", this->Quiet);
+  }
+  for (std::set<std::string>::const_iterator i = labels.begin();
+       i != labels.end(); ++i) {
+    std::string label = *i;
+    label.resize(maxlen + 3, ' ');
+
+    char buf[1024];
+    sprintf(buf, "%6.2f sec", labelTimes[*i]);
+
+    std::ostringstream labelCountStr;
+    labelCountStr << "(" << labelCounts[*i] << " test";
+    if (labelCounts[*i] > 1) {
+      labelCountStr << "s";
+    }
+    labelCountStr << ")";
+
+    cmCTestOptionalLog(this->CTest, HANDLER_OUTPUT, "\n"
+                         << label << " = " << buf << " "
+                         << labelCountStr.str(),
+                       this->Quiet);
+    if (this->LogFile) {
+      *this->LogFile << "\n" << *i << " = " << buf << "\n";
+    }
+  }
+  if (!labels.empty()) {
+    if (this->LogFile) {
+      *this->LogFile << "\n";
+    }
+    cmCTestOptionalLog(this->CTest, HANDLER_OUTPUT, "\n", this->Quiet);
+  }
+}
 void cmCTestTestHandler::CheckLabelFilterInclude(cmCTestTestProperties& it)
 void cmCTestTestHandler::CheckLabelFilterInclude(cmCTestTestProperties& it)
 {
 {
   // if not using Labels to filter then return
   // if not using Labels to filter then return

+ 2 - 0
Source/CTest/cmCTestTestHandler.h

@@ -232,6 +232,8 @@ private:
   virtual void GenerateDartOutput(cmXMLWriter& xml);
   virtual void GenerateDartOutput(cmXMLWriter& xml);
 
 
   void PrintLabelSummary();
   void PrintLabelSummary();
+  void PrintSubprojectSummary();
+
   /**
   /**
    * Run the tests for a directory and any subdirectories
    * Run the tests for a directory and any subdirectories
    */
    */

+ 4 - 0
Source/cmCTest.cxx

@@ -253,6 +253,7 @@ std::string cmCTest::DecodeURL(const std::string& in)
 cmCTest::cmCTest()
 cmCTest::cmCTest()
 {
 {
   this->LabelSummary = true;
   this->LabelSummary = true;
+  this->SubprojectSummary = true;
   this->ParallelLevel = 1;
   this->ParallelLevel = 1;
   this->ParallelLevelSetInCli = false;
   this->ParallelLevelSetInCli = false;
   this->TestLoad = 0;
   this->TestLoad = 0;
@@ -1794,6 +1795,9 @@ bool cmCTest::HandleCommandLineArguments(size_t& i,
   if (this->CheckArgument(arg, "--no-label-summary")) {
   if (this->CheckArgument(arg, "--no-label-summary")) {
     this->LabelSummary = false;
     this->LabelSummary = false;
   }
   }
+  if (this->CheckArgument(arg, "--no-subproject-summary")) {
+    this->SubprojectSummary = false;
+  }
   if (this->CheckArgument(arg, "-Q", "--quiet")) {
   if (this->CheckArgument(arg, "-Q", "--quiet")) {
     this->Quiet = true;
     this->Quiet = true;
   }
   }

+ 3 - 0
Source/cmCTest.h

@@ -438,7 +438,9 @@ public:
     this->StreamErr = err;
     this->StreamErr = err;
   }
   }
   void AddSiteProperties(cmXMLWriter& xml);
   void AddSiteProperties(cmXMLWriter& xml);
+
   bool GetLabelSummary() { return this->LabelSummary; }
   bool GetLabelSummary() { return this->LabelSummary; }
+  bool GetSubprojectSummary() { return this->SubprojectSummary; }
 
 
   std::string GetCostDataFile();
   std::string GetCostDataFile();
 
 
@@ -467,6 +469,7 @@ private:
   bool ExtraVerbose;
   bool ExtraVerbose;
   bool ProduceXML;
   bool ProduceXML;
   bool LabelSummary;
   bool LabelSummary;
+  bool SubprojectSummary;
   bool UseHTTP10;
   bool UseHTTP10;
   bool PrintLabels;
   bool PrintLabels;
   bool Failover;
   bool Failover;

+ 2 - 0
Source/ctest.cxx

@@ -83,6 +83,8 @@ static const char* cmDocumentationOptions[][2] = {
   { "--max-width <width>", "Set the max width for a test name to output" },
   { "--max-width <width>", "Set the max width for a test name to output" },
   { "--interactive-debug-mode [0|1]", "Set the interactive mode to 0 or 1." },
   { "--interactive-debug-mode [0|1]", "Set the interactive mode to 0 or 1." },
   { "--no-label-summary", "Disable timing summary information for labels." },
   { "--no-label-summary", "Disable timing summary information for labels." },
+  { "--no-subproject-summary", "Disable timing summary information for "
+                               "subprojects." },
   { "--build-and-test", "Configure, build and run a test." },
   { "--build-and-test", "Configure, build and run a test." },
   { "--build-target", "Specify a specific target to build." },
   { "--build-target", "Specify a specific target to build." },
   { "--build-nocmake", "Run the build without running cmake first." },
   { "--build-nocmake", "Run the build without running cmake first." },