|  | @@ -32,6 +32,22 @@
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  #define SAFEDIV(x,y) (((y)!=0)?((x)/(y)):(0))
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | +//----------------------------------------------------------------------
 | 
	
		
			
				|  |  | +//**********************************************************************
 | 
	
		
			
				|  |  | +class cmCTestCoverageHandlerContainer
 | 
	
		
			
				|  |  | +{
 | 
	
		
			
				|  |  | +public:
 | 
	
		
			
				|  |  | +  int Error;
 | 
	
		
			
				|  |  | +  std::string SourceDir;
 | 
	
		
			
				|  |  | +  std::string BinaryDir;
 | 
	
		
			
				|  |  | +  typedef std::vector<int> SingleFileCoverageVector;
 | 
	
		
			
				|  |  | +  typedef std::map<std::string, SingleFileCoverageVector> TotalCoverageMap;
 | 
	
		
			
				|  |  | +  TotalCoverageMap TotalCoverage;
 | 
	
		
			
				|  |  | +  std::ostream* OFS;
 | 
	
		
			
				|  |  | +};
 | 
	
		
			
				|  |  | +//**********************************************************************
 | 
	
		
			
				|  |  | +//----------------------------------------------------------------------
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |  //----------------------------------------------------------------------
 | 
	
		
			
				|  |  |  cmCTestCoverageHandler::cmCTestCoverageHandler()
 | 
	
		
			
				|  |  |  {
 | 
	
	
		
			
				|  | @@ -186,12 +202,12 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |      return error;
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  |    
 | 
	
		
			
				|  |  | +  std::string coverage_start_time = this->CTest->CurrentTime();
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |    std::string sourceDir
 | 
	
		
			
				|  |  |      = this->CTest->GetCTestConfiguration("SourceDirectory");
 | 
	
		
			
				|  |  |    std::string binaryDir
 | 
	
		
			
				|  |  |      = this->CTest->GetCTestConfiguration("BuildDirectory");
 | 
	
		
			
				|  |  | -  std::string gcovCommand
 | 
	
		
			
				|  |  | -    = this->CTest->GetCTestConfiguration("CoverageCommand");
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |    cmGeneratedFileStream ofs;
 | 
	
		
			
				|  |  |    double elapsed_time_start = cmSystemTools::GetTime();
 | 
	
	
		
			
				|  | @@ -209,191 +225,474 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |    std::string asfGlob = sourceDir + "/*";
 | 
	
		
			
				|  |  |    std::string abfGlob = binaryDir + "/*";
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  // Style 1
 | 
	
		
			
				|  |  | -  std::string st1gcovOutputRex1
 | 
	
		
			
				|  |  | -    = "[0-9]+\\.[0-9]+% of [0-9]+ (source |)lines executed in file (.*)$";
 | 
	
		
			
				|  |  | -  std::string st1gcovOutputRex2 = "^Creating (.*\\.gcov)\\.";
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st1re1(st1gcovOutputRex1.c_str());
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st1re2(st1gcovOutputRex2.c_str());
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  // Style 2
 | 
	
		
			
				|  |  | -  std::string st2gcovOutputRex1 = "^File *[`'](.*)'$";
 | 
	
		
			
				|  |  | -  std::string st2gcovOutputRex2
 | 
	
		
			
				|  |  | -    = "Lines executed: *[0-9]+\\.[0-9]+% of [0-9]+$";
 | 
	
		
			
				|  |  | -  std::string st2gcovOutputRex3 = "^(.*):creating [`'](.*\\.gcov)'";
 | 
	
		
			
				|  |  | -  std::string st2gcovOutputRex4 = "^(.*):unexpected EOF *$";
 | 
	
		
			
				|  |  | -  std::string st2gcovOutputRex5 = "^(.*):cannot open source file*$";
 | 
	
		
			
				|  |  | -  std::string st2gcovOutputRex6
 | 
	
		
			
				|  |  | -    = "^(.*):source file is newer than graph file `(.*)'$";
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st2re1(st2gcovOutputRex1.c_str());
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st2re2(st2gcovOutputRex2.c_str());
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st2re3(st2gcovOutputRex3.c_str());
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st2re4(st2gcovOutputRex4.c_str());
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st2re5(st2gcovOutputRex5.c_str());
 | 
	
		
			
				|  |  | -  cmsys::RegularExpression st2re6(st2gcovOutputRex6.c_str());
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  |    cmCTestLog(this->CTest, HANDLER_OUTPUT, "Performing coverage" << std::endl);
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  std::string coverage_start_time = this->CTest->CurrentTime();
 | 
	
		
			
				|  |  | +  cmCTestCoverageHandlerContainer cont;
 | 
	
		
			
				|  |  | +  cont.Error = error;
 | 
	
		
			
				|  |  | +  cont.SourceDir = sourceDir;
 | 
	
		
			
				|  |  | +  cont.BinaryDir = binaryDir;
 | 
	
		
			
				|  |  | +  cont.OFS = &ofs;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  std::string testingDir = this->CTest->GetBinaryDir() + "/Testing";
 | 
	
		
			
				|  |  | -  std::string tempDir = testingDir + "/CoverageInfo";
 | 
	
		
			
				|  |  | -  std::string currentDirectory = cmSystemTools::GetCurrentWorkingDirectory();
 | 
	
		
			
				|  |  | -  cmSystemTools::MakeDirectory(tempDir.c_str());
 | 
	
		
			
				|  |  | -  cmSystemTools::ChangeDirectory(tempDir.c_str());
 | 
	
		
			
				|  |  | +  int file_count = 0;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  cmsys::Glob gl;
 | 
	
		
			
				|  |  | -  gl.RecurseOn();
 | 
	
		
			
				|  |  | -  std::string daGlob = binaryDir + "/*.da";
 | 
	
		
			
				|  |  | -  gl.FindFiles(daGlob);
 | 
	
		
			
				|  |  | -  std::vector<std::string> files = gl.GetFiles();
 | 
	
		
			
				|  |  | -  daGlob = binaryDir + "/*.gcda";
 | 
	
		
			
				|  |  | -  gl.FindFiles(daGlob);
 | 
	
		
			
				|  |  | -  std::vector<std::string>& moreFiles = gl.GetFiles();
 | 
	
		
			
				|  |  | -  files.insert(files.end(), moreFiles.begin(), moreFiles.end());
 | 
	
		
			
				|  |  | -  std::vector<std::string>::iterator it;
 | 
	
		
			
				|  |  | +  file_count += this->HandleGCovCoverage(&cont);
 | 
	
		
			
				|  |  | +  if ( file_count < 0 )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    return error;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  file_count += this->HandleTracePyCoverage(&cont);
 | 
	
		
			
				|  |  | +  if ( file_count < 0 )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    return error;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  error = cont.Error;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  if ( files.size() == 0 )
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  if ( file_count == 0 )
 | 
	
		
			
				|  |  |      {
 | 
	
		
			
				|  |  |      cmCTestLog(this->CTest, WARNING,
 | 
	
		
			
				|  |  |        " Cannot find any coverage files. Ignoring Coverage request."
 | 
	
		
			
				|  |  |        << std::endl);
 | 
	
		
			
				|  |  | -    // No coverage files is a valid thing, so the exit code is 0 
 | 
	
		
			
				|  |  | -    cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | -    return 0;
 | 
	
		
			
				|  |  | +    return error;
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  | +  cmGeneratedFileStream covSumFile;
 | 
	
		
			
				|  |  | +  cmGeneratedFileStream covLogFile;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  this->CustomCoverageExcludeRegex.empty();
 | 
	
		
			
				|  |  | -  std::vector<cmStdString>::iterator rexIt;
 | 
	
		
			
				|  |  | -  for ( rexIt = this->CustomCoverageExclude.begin();
 | 
	
		
			
				|  |  | -    rexIt != this->CustomCoverageExclude.end();
 | 
	
		
			
				|  |  | -    ++ rexIt )
 | 
	
		
			
				|  |  | +  if (!this->StartResultingXML("Coverage", covSumFile))
 | 
	
		
			
				|  |  |      {
 | 
	
		
			
				|  |  | -    this->CustomCoverageExcludeRegex.push_back(
 | 
	
		
			
				|  |  | -      cmsys::RegularExpression(rexIt->c_str()));
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +      "Cannot open coverage summary file." << std::endl);
 | 
	
		
			
				|  |  | +    return -1;
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  typedef std::vector<int> singleFileCoverageVector;
 | 
	
		
			
				|  |  | -  typedef std::map<std::string, singleFileCoverageVector> totalCoverageMap;
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  totalCoverageMap totalCoverage;
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  int gcovStyle = 0;
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  std::set<std::string> missingFiles;
 | 
	
		
			
				|  |  | +  this->CTest->StartXML(covSumFile);
 | 
	
		
			
				|  |  | +  // Produce output xml files
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  std::string actualSourceFile = "";
 | 
	
		
			
				|  |  | +  covSumFile << "<Coverage>" << std::endl
 | 
	
		
			
				|  |  | +    << "\t<StartDateTime>" << coverage_start_time << "</StartDateTime>"
 | 
	
		
			
				|  |  | +    << std::endl;
 | 
	
		
			
				|  |  | +  int logFileCount = 0;
 | 
	
		
			
				|  |  | +  if ( !this->StartCoverageLogFile(covLogFile, logFileCount) )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    return -1;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  cmCTestCoverageHandlerContainer::TotalCoverageMap::iterator fileIterator;
 | 
	
		
			
				|  |  | +  int cnt = 0;
 | 
	
		
			
				|  |  | +  long total_tested = 0;
 | 
	
		
			
				|  |  | +  long total_untested = 0;
 | 
	
		
			
				|  |  | +  //std::string fullSourceDir = sourceDir + "/";
 | 
	
		
			
				|  |  | +  //std::string fullBinaryDir = binaryDir + "/";
 | 
	
		
			
				|  |  | +  cmCTestLog(this->CTest, HANDLER_OUTPUT, std::endl);
 | 
	
		
			
				|  |  |    cmCTestLog(this->CTest, HANDLER_OUTPUT,
 | 
	
		
			
				|  |  | -    "   Processing coverage (each . represents one file):" << std::endl);
 | 
	
		
			
				|  |  | +    "   Acumulating results (each . represents one file):" << std::endl);
 | 
	
		
			
				|  |  |    cmCTestLog(this->CTest, HANDLER_OUTPUT, "    ");
 | 
	
		
			
				|  |  | -  int file_count = 0;
 | 
	
		
			
				|  |  | -  for ( it = files.begin(); it != files.end(); ++ it )
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  std::vector<std::string> errorsWhileAccumulating;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  file_count = 0;
 | 
	
		
			
				|  |  | +  for ( fileIterator = cont.TotalCoverage.begin();
 | 
	
		
			
				|  |  | +    fileIterator != cont.TotalCoverage.end();
 | 
	
		
			
				|  |  | +    ++fileIterator )
 | 
	
		
			
				|  |  |      {
 | 
	
		
			
				|  |  |      cmCTestLog(this->CTest, HANDLER_OUTPUT, "." << std::flush);
 | 
	
		
			
				|  |  | -    std::string fileDir = cmSystemTools::GetFilenamePath(it->c_str());
 | 
	
		
			
				|  |  | -    std::string command = "\"" + gcovCommand + "\" -l -o \"" + fileDir
 | 
	
		
			
				|  |  | -      + "\" \"" + *it + "\"";
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, command.c_str()
 | 
	
		
			
				|  |  | -      << std::endl);
 | 
	
		
			
				|  |  | -    std::string output = "";
 | 
	
		
			
				|  |  | -    std::string errors = "";
 | 
	
		
			
				|  |  | -    int retVal = 0;
 | 
	
		
			
				|  |  | -    ofs << "* Run coverage for: " << fileDir.c_str() << std::endl;
 | 
	
		
			
				|  |  | -    ofs << "  Command: " << command.c_str() << std::endl;
 | 
	
		
			
				|  |  | -    int res = this->CTest->RunCommand(command.c_str(), &output, &errors,
 | 
	
		
			
				|  |  | -      &retVal, tempDir.c_str(), 0 /*this->TimeOut*/);
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -    ofs << "  Output: " << output.c_str() << std::endl;
 | 
	
		
			
				|  |  | -    ofs << "  Errors: " << errors.c_str() << std::endl;
 | 
	
		
			
				|  |  | -    if ( ! res )
 | 
	
		
			
				|  |  | +    file_count ++;
 | 
	
		
			
				|  |  | +    if ( file_count % 50 == 0 )
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | -        "Problem running coverage on file: " << it->c_str() << std::endl);
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | -        "Command produced error: " << errors << std::endl);
 | 
	
		
			
				|  |  | -      error ++;
 | 
	
		
			
				|  |  | -      continue;
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, HANDLER_OUTPUT, " processed: " << file_count
 | 
	
		
			
				|  |  | +        << " out of "
 | 
	
		
			
				|  |  | +        << cont.TotalCoverage.size() << std::endl);
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, HANDLER_OUTPUT, "    ");
 | 
	
		
			
				|  |  |        }
 | 
	
		
			
				|  |  | -    if ( retVal != 0 )
 | 
	
		
			
				|  |  | +    if ( cnt % 100 == 0 )
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, ERROR_MESSAGE, "Coverage command returned: "
 | 
	
		
			
				|  |  | -        << retVal << " while processing: " << it->c_str() << std::endl);
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | -        "Command produced error: " << error << std::endl);
 | 
	
		
			
				|  |  | +      this->EndCoverageLogFile(covLogFile, logFileCount);
 | 
	
		
			
				|  |  | +      logFileCount ++;
 | 
	
		
			
				|  |  | +      if ( !this->StartCoverageLogFile(covLogFile, logFileCount) )
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +        return -1;
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  |        }
 | 
	
		
			
				|  |  | +    const std::string fullFileName = fileIterator->first;
 | 
	
		
			
				|  |  | +    const std::string fileName
 | 
	
		
			
				|  |  | +      = cmSystemTools::GetFilenameName(fullFileName.c_str());
 | 
	
		
			
				|  |  | +    std::string fullFilePath
 | 
	
		
			
				|  |  | +      = cmSystemTools::GetFilenamePath(fullFileName.c_str());
 | 
	
		
			
				|  |  |      cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | -      "--------------------------------------------------------------"
 | 
	
		
			
				|  |  | -      << std::endl
 | 
	
		
			
				|  |  | -      << output << std::endl
 | 
	
		
			
				|  |  | -      << "--------------------------------------------------------------"
 | 
	
		
			
				|  |  | -      << std::endl);
 | 
	
		
			
				|  |  | -    std::vector<cmStdString> lines;
 | 
	
		
			
				|  |  | -    std::vector<cmStdString>::iterator line;
 | 
	
		
			
				|  |  | +      "Process file: " << fullFileName << std::endl);
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | +    cmSystemTools::ConvertToUnixSlashes(fullFilePath);
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    // Globals for storing current source file and current gcov file;
 | 
	
		
			
				|  |  | -    cmSystemTools::Split(output.c_str(), lines);
 | 
	
		
			
				|  |  | -    for ( line = lines.begin(); line != lines.end(); ++line)
 | 
	
		
			
				|  |  | +    if ( !cmSystemTools::FileExists(fullFileName.c_str()) )
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  | -      std::string sourceFile;
 | 
	
		
			
				|  |  | -      std::string gcovFile;
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, DEBUG, "Line: [" << line->c_str() << "]"
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE, "Cannot find file: "
 | 
	
		
			
				|  |  | +        << fullFileName.c_str() << std::endl);
 | 
	
		
			
				|  |  | +      continue;
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    bool shouldIDoCoverage
 | 
	
		
			
				|  |  | +      = this->ShouldIDoCoverage(fullFileName.c_str(),
 | 
	
		
			
				|  |  | +        sourceDir.c_str(), binaryDir.c_str());
 | 
	
		
			
				|  |  | +    if ( !shouldIDoCoverage )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +        ".NoDartCoverage found, so skip coverage check for: "
 | 
	
		
			
				|  |  | +        << fullFileName.c_str()
 | 
	
		
			
				|  |  |          << std::endl);
 | 
	
		
			
				|  |  | -      if ( line->size() == 0 )
 | 
	
		
			
				|  |  | +      continue;
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    const cmCTestCoverageHandlerContainer::SingleFileCoverageVector& fcov
 | 
	
		
			
				|  |  | +      = fileIterator->second;
 | 
	
		
			
				|  |  | +    covLogFile << "\t<File Name=\""
 | 
	
		
			
				|  |  | +      << this->CTest->MakeXMLSafe(fileName.c_str())
 | 
	
		
			
				|  |  | +      << "\" FullPath=\"" << this->CTest->MakeXMLSafe(
 | 
	
		
			
				|  |  | +        this->CTest->GetShortPathToFile(
 | 
	
		
			
				|  |  | +          fileIterator->first.c_str())) << "\">" << std::endl
 | 
	
		
			
				|  |  | +      << "\t\t<Report>" << std::endl;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    std::ifstream ifs(fullFileName.c_str());
 | 
	
		
			
				|  |  | +    if ( !ifs)
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cmOStringStream ostr;
 | 
	
		
			
				|  |  | +      ostr <<  "Cannot open source file: " << fullFileName.c_str();
 | 
	
		
			
				|  |  | +      errorsWhileAccumulating.push_back(ostr.str());
 | 
	
		
			
				|  |  | +      error ++;
 | 
	
		
			
				|  |  | +      continue;
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    int tested = 0;
 | 
	
		
			
				|  |  | +    int untested = 0;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    cmCTestCoverageHandlerContainer::SingleFileCoverageVector::size_type cc;
 | 
	
		
			
				|  |  | +    std::string line;
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +      "Actually perfoming coverage for: " << fullFileName << std::endl);
 | 
	
		
			
				|  |  | +    for ( cc= 0; cc < fcov.size(); cc ++ )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      if ( !cmSystemTools::GetLineFromStream(ifs, line) &&
 | 
	
		
			
				|  |  | +        cc != fcov.size() -1 )
 | 
	
		
			
				|  |  |          {
 | 
	
		
			
				|  |  | -        // Ignore empty line; probably style 2
 | 
	
		
			
				|  |  | +        cmOStringStream ostr;
 | 
	
		
			
				|  |  | +        ostr << "Problem reading source file: " << fullFileName.c_str()
 | 
	
		
			
				|  |  | +          << " line:" << cc;
 | 
	
		
			
				|  |  | +        errorsWhileAccumulating.push_back(ostr.str());
 | 
	
		
			
				|  |  | +        error ++;
 | 
	
		
			
				|  |  | +        break;
 | 
	
		
			
				|  |  |          }
 | 
	
		
			
				|  |  | -      else if ( st1re1.find(line->c_str()) )
 | 
	
		
			
				|  |  | +      covLogFile << "\t\t<Line Number=\"" << cc << "\" Count=\"" << fcov[cc]
 | 
	
		
			
				|  |  | +        << "\">"
 | 
	
		
			
				|  |  | +        << this->CTest->MakeXMLSafe(line.c_str()) << "</Line>" << std::endl;
 | 
	
		
			
				|  |  | +      if ( fcov[cc] == 0 )
 | 
	
		
			
				|  |  |          {
 | 
	
		
			
				|  |  | -        if ( gcovStyle != 0 )
 | 
	
		
			
				|  |  | -          {
 | 
	
		
			
				|  |  | -          if ( gcovStyle != 1 )
 | 
	
		
			
				|  |  | -            {
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  | -              << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | -            break;
 | 
	
		
			
				|  |  | -            }
 | 
	
		
			
				|  |  | -          gcovStyle = 1;
 | 
	
		
			
				|  |  | -          }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -        actualSourceFile = "";
 | 
	
		
			
				|  |  | -        sourceFile = st1re1.match(2);
 | 
	
		
			
				|  |  | +        untested ++;
 | 
	
		
			
				|  |  |          }
 | 
	
		
			
				|  |  | -      else if ( st1re2.find(line->c_str() ) )
 | 
	
		
			
				|  |  | +      else if ( fcov[cc] > 0 )
 | 
	
		
			
				|  |  |          {
 | 
	
		
			
				|  |  | -        if ( gcovStyle != 0 )
 | 
	
		
			
				|  |  | -          {
 | 
	
		
			
				|  |  | -          if ( gcovStyle != 1 )
 | 
	
		
			
				|  |  | -            {
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  | -              << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | -            break;
 | 
	
		
			
				|  |  | -            }
 | 
	
		
			
				|  |  | -          gcovStyle = 1;
 | 
	
		
			
				|  |  | -          }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -        gcovFile = st1re2.match(1);
 | 
	
		
			
				|  |  | +        tested ++;
 | 
	
		
			
				|  |  |          }
 | 
	
		
			
				|  |  | -      else if ( st2re1.find(line->c_str() ) )
 | 
	
		
			
				|  |  | -        {
 | 
	
		
			
				|  |  | -        if ( gcovStyle != 0 )
 | 
	
		
			
				|  |  | -          {
 | 
	
		
			
				|  |  | -          if ( gcovStyle != 2 )
 | 
	
		
			
				|  |  | -            {
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  | -              << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | -            break;
 | 
	
		
			
				|  |  | -            }
 | 
	
		
			
				|  |  | -          gcovStyle = 2;
 | 
	
		
			
				|  |  | -          }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -        actualSourceFile = "";
 | 
	
		
			
				|  |  | -        sourceFile = st2re1.match(1);
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    if ( cmSystemTools::GetLineFromStream(ifs, line) )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cmOStringStream ostr;
 | 
	
		
			
				|  |  | +      ostr <<  "Looks like there are more lines in the file: " << line;
 | 
	
		
			
				|  |  | +      errorsWhileAccumulating.push_back(ostr.str());
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    float cper = 0;
 | 
	
		
			
				|  |  | +    float cmet = 0;
 | 
	
		
			
				|  |  | +    if ( tested + untested > 0 )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cper = (100 * SAFEDIV(static_cast<float>(tested),
 | 
	
		
			
				|  |  | +          static_cast<float>(tested + untested)));
 | 
	
		
			
				|  |  | +      cmet = ( SAFEDIV(static_cast<float>(tested + 10),
 | 
	
		
			
				|  |  | +          static_cast<float>(tested + untested + 10)));
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    total_tested += tested;
 | 
	
		
			
				|  |  | +    total_untested += untested;
 | 
	
		
			
				|  |  | +    covLogFile << "\t\t</Report>" << std::endl
 | 
	
		
			
				|  |  | +      << "\t</File>" << std::endl;
 | 
	
		
			
				|  |  | +    covSumFile << "\t<File Name=\"" << this->CTest->MakeXMLSafe(fileName)
 | 
	
		
			
				|  |  | +      << "\" FullPath=\"" << this->CTest->MakeXMLSafe(
 | 
	
		
			
				|  |  | +        this->CTest->GetShortPathToFile(fullFileName.c_str()))
 | 
	
		
			
				|  |  | +      << "\" Covered=\"" << (cmet>0?"true":"false") << "\">\n"
 | 
	
		
			
				|  |  | +      << "\t\t<LOCTested>" << tested << "</LOCTested>\n"
 | 
	
		
			
				|  |  | +      << "\t\t<LOCUnTested>" << untested << "</LOCUnTested>\n"
 | 
	
		
			
				|  |  | +      << "\t\t<PercentCoverage>";
 | 
	
		
			
				|  |  | +    covSumFile.setf(std::ios::fixed, std::ios::floatfield);
 | 
	
		
			
				|  |  | +    covSumFile.precision(2);
 | 
	
		
			
				|  |  | +    covSumFile << (cper) << "</PercentCoverage>\n"
 | 
	
		
			
				|  |  | +      << "\t\t<CoverageMetric>";
 | 
	
		
			
				|  |  | +    covSumFile.setf(std::ios::fixed, std::ios::floatfield);
 | 
	
		
			
				|  |  | +    covSumFile.precision(2);
 | 
	
		
			
				|  |  | +    covSumFile << (cmet) << "</CoverageMetric>\n"
 | 
	
		
			
				|  |  | +      << "\t</File>" << std::endl;
 | 
	
		
			
				|  |  | +    cnt ++;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  this->EndCoverageLogFile(covLogFile, logFileCount);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  if ( errorsWhileAccumulating.size() > 0 )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, ERROR_MESSAGE, std::endl);
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +      "Error(s) while acumulating results:" << std::endl);
 | 
	
		
			
				|  |  | +    std::vector<std::string>::iterator erIt;
 | 
	
		
			
				|  |  | +    for ( erIt = errorsWhileAccumulating.begin();
 | 
	
		
			
				|  |  | +      erIt != errorsWhileAccumulating.end();
 | 
	
		
			
				|  |  | +      ++ erIt )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +        "  " << erIt->c_str() << std::endl);
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  int total_lines = total_tested + total_untested;
 | 
	
		
			
				|  |  | +  float percent_coverage = 100 * SAFEDIV(static_cast<float>(total_tested),
 | 
	
		
			
				|  |  | +    static_cast<float>(total_lines));
 | 
	
		
			
				|  |  | +  if ( total_lines == 0 )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    percent_coverage = 0;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  std::string end_time = this->CTest->CurrentTime();
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  covSumFile << "\t<LOCTested>" << total_tested << "</LOCTested>\n"
 | 
	
		
			
				|  |  | +    << "\t<LOCUntested>" << total_untested << "</LOCUntested>\n"
 | 
	
		
			
				|  |  | +    << "\t<LOC>" << total_lines << "</LOC>\n"
 | 
	
		
			
				|  |  | +    << "\t<PercentCoverage>";
 | 
	
		
			
				|  |  | +  covSumFile.setf(std::ios::fixed, std::ios::floatfield);
 | 
	
		
			
				|  |  | +  covSumFile.precision(2);
 | 
	
		
			
				|  |  | +  covSumFile << (percent_coverage)<< "</PercentCoverage>\n"
 | 
	
		
			
				|  |  | +    << "\t<EndDateTime>" << end_time << "</EndDateTime>\n";
 | 
	
		
			
				|  |  | +  covSumFile << "<ElapsedMinutes>" <<
 | 
	
		
			
				|  |  | +    static_cast<int>((cmSystemTools::GetTime() - elapsed_time_start)/6)/10.0
 | 
	
		
			
				|  |  | +    << "</ElapsedMinutes>"
 | 
	
		
			
				|  |  | +    << "</Coverage>" << std::endl;
 | 
	
		
			
				|  |  | +  this->CTest->EndXML(covSumFile);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  cmCTestLog(this->CTest, HANDLER_OUTPUT, "" << std::endl
 | 
	
		
			
				|  |  | +    << "\tCovered LOC:         "
 | 
	
		
			
				|  |  | +    << total_tested << std::endl
 | 
	
		
			
				|  |  | +    << "\tNot covered LOC:     " << total_untested << std::endl
 | 
	
		
			
				|  |  | +    << "\tTotal LOC:           " << total_lines << std::endl
 | 
	
		
			
				|  |  | +    << "\tPercentage Coverage: "
 | 
	
		
			
				|  |  | +    << std::setiosflags(std::ios::fixed)
 | 
	
		
			
				|  |  | +    << std::setprecision(2)
 | 
	
		
			
				|  |  | +    << (percent_coverage) << "%" << std::endl);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  ofs << "\tCovered LOC:         " << total_tested << std::endl
 | 
	
		
			
				|  |  | +    << "\tNot covered LOC:     " << total_untested << std::endl
 | 
	
		
			
				|  |  | +    << "\tTotal LOC:           " << total_lines << std::endl
 | 
	
		
			
				|  |  | +    << "\tPercentage Coverage: "
 | 
	
		
			
				|  |  | +    << std::setiosflags(std::ios::fixed)
 | 
	
		
			
				|  |  | +    << std::setprecision(2)
 | 
	
		
			
				|  |  | +    << (percent_coverage) << "%" << std::endl;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  if ( error )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    return -1;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  return 0;
 | 
	
		
			
				|  |  | +}
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +//----------------------------------------------------------------------
 | 
	
		
			
				|  |  | +void cmCTestCoverageHandler::PopulateCustomVectors(cmMakefile *mf)
 | 
	
		
			
				|  |  | +{
 | 
	
		
			
				|  |  | +  cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +    " Add coverage exclude regular expressions." << std::endl);
 | 
	
		
			
				|  |  | +  this->CTest->PopulateCustomVector(mf, "CTEST_CUSTOM_COVERAGE_EXCLUDE",
 | 
	
		
			
				|  |  | +                                this->CustomCoverageExclude);
 | 
	
		
			
				|  |  | +  std::vector<cmStdString>::iterator it;
 | 
	
		
			
				|  |  | +  for ( it = this->CustomCoverageExclude.begin();
 | 
	
		
			
				|  |  | +    it != this->CustomCoverageExclude.end();
 | 
	
		
			
				|  |  | +    ++ it )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, " Add coverage exclude: "
 | 
	
		
			
				|  |  | +      << it->c_str() << std::endl);
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +}
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +//----------------------------------------------------------------------
 | 
	
		
			
				|  |  | +int cmCTestCoverageHandler::HandleGCovCoverage(
 | 
	
		
			
				|  |  | +  cmCTestCoverageHandlerContainer* cont)
 | 
	
		
			
				|  |  | +{
 | 
	
		
			
				|  |  | +  std::string gcovCommand
 | 
	
		
			
				|  |  | +    = this->CTest->GetCTestConfiguration("CoverageCommand");
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  // Style 1
 | 
	
		
			
				|  |  | +  std::string st1gcovOutputRex1
 | 
	
		
			
				|  |  | +    = "[0-9]+\\.[0-9]+% of [0-9]+ (source |)lines executed in file (.*)$";
 | 
	
		
			
				|  |  | +  std::string st1gcovOutputRex2 = "^Creating (.*\\.gcov)\\.";
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st1re1(st1gcovOutputRex1.c_str());
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st1re2(st1gcovOutputRex2.c_str());
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  // Style 2
 | 
	
		
			
				|  |  | +  std::string st2gcovOutputRex1 = "^File *[`'](.*)'$";
 | 
	
		
			
				|  |  | +  std::string st2gcovOutputRex2
 | 
	
		
			
				|  |  | +    = "Lines executed: *[0-9]+\\.[0-9]+% of [0-9]+$";
 | 
	
		
			
				|  |  | +  std::string st2gcovOutputRex3 = "^(.*):creating [`'](.*\\.gcov)'";
 | 
	
		
			
				|  |  | +  std::string st2gcovOutputRex4 = "^(.*):unexpected EOF *$";
 | 
	
		
			
				|  |  | +  std::string st2gcovOutputRex5 = "^(.*):cannot open source file*$";
 | 
	
		
			
				|  |  | +  std::string st2gcovOutputRex6
 | 
	
		
			
				|  |  | +    = "^(.*):source file is newer than graph file `(.*)'$";
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st2re1(st2gcovOutputRex1.c_str());
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st2re2(st2gcovOutputRex2.c_str());
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st2re3(st2gcovOutputRex3.c_str());
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st2re4(st2gcovOutputRex4.c_str());
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st2re5(st2gcovOutputRex5.c_str());
 | 
	
		
			
				|  |  | +  cmsys::RegularExpression st2re6(st2gcovOutputRex6.c_str());
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  cmsys::Glob gl;
 | 
	
		
			
				|  |  | +  gl.RecurseOn();
 | 
	
		
			
				|  |  | +  std::string daGlob = cont->BinaryDir + "/*.da";
 | 
	
		
			
				|  |  | +  gl.FindFiles(daGlob);
 | 
	
		
			
				|  |  | +  std::vector<std::string> files = gl.GetFiles();
 | 
	
		
			
				|  |  | +  daGlob = cont->BinaryDir + "/*.gcda";
 | 
	
		
			
				|  |  | +  gl.FindFiles(daGlob);
 | 
	
		
			
				|  |  | +  std::vector<std::string>& moreFiles = gl.GetFiles();
 | 
	
		
			
				|  |  | +  files.insert(files.end(), moreFiles.begin(), moreFiles.end());
 | 
	
		
			
				|  |  | +  std::vector<std::string>::iterator it;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  if ( files.size() == 0 )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +      " Cannot find any GCov coverage files."
 | 
	
		
			
				|  |  | +      << std::endl);
 | 
	
		
			
				|  |  | +    // No coverage files is a valid thing, so the exit code is 0 
 | 
	
		
			
				|  |  | +    return 0;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  std::string testingDir = this->CTest->GetBinaryDir() + "/Testing";
 | 
	
		
			
				|  |  | +  std::string tempDir = testingDir + "/CoverageInfo";
 | 
	
		
			
				|  |  | +  std::string currentDirectory = cmSystemTools::GetCurrentWorkingDirectory();
 | 
	
		
			
				|  |  | +  cmSystemTools::MakeDirectory(tempDir.c_str());
 | 
	
		
			
				|  |  | +  cmSystemTools::ChangeDirectory(tempDir.c_str());
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  this->CustomCoverageExcludeRegex.empty();
 | 
	
		
			
				|  |  | +  std::vector<cmStdString>::iterator rexIt;
 | 
	
		
			
				|  |  | +  for ( rexIt = this->CustomCoverageExclude.begin();
 | 
	
		
			
				|  |  | +    rexIt != this->CustomCoverageExclude.end();
 | 
	
		
			
				|  |  | +    ++ rexIt )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    this->CustomCoverageExcludeRegex.push_back(
 | 
	
		
			
				|  |  | +      cmsys::RegularExpression(rexIt->c_str()));
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  int gcovStyle = 0;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  std::set<std::string> missingFiles;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +  std::string actualSourceFile = "";
 | 
	
		
			
				|  |  | +  cmCTestLog(this->CTest, HANDLER_OUTPUT,
 | 
	
		
			
				|  |  | +    "   Processing coverage (each . represents one file):" << std::endl);
 | 
	
		
			
				|  |  | +  cmCTestLog(this->CTest, HANDLER_OUTPUT, "    ");
 | 
	
		
			
				|  |  | +  int file_count = 0;
 | 
	
		
			
				|  |  | +  for ( it = files.begin(); it != files.end(); ++ it )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_OUTPUT, "." << std::flush);
 | 
	
		
			
				|  |  | +    std::string fileDir = cmSystemTools::GetFilenamePath(it->c_str());
 | 
	
		
			
				|  |  | +    std::string command = "\"" + gcovCommand + "\" -l -o \"" + fileDir
 | 
	
		
			
				|  |  | +      + "\" \"" + *it + "\"";
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, command.c_str()
 | 
	
		
			
				|  |  | +      << std::endl);
 | 
	
		
			
				|  |  | +    std::string output = "";
 | 
	
		
			
				|  |  | +    std::string errors = "";
 | 
	
		
			
				|  |  | +    int retVal = 0;
 | 
	
		
			
				|  |  | +    *cont->OFS << "* Run coverage for: " << fileDir.c_str() << std::endl;
 | 
	
		
			
				|  |  | +    *cont->OFS << "  Command: " << command.c_str() << std::endl;
 | 
	
		
			
				|  |  | +    int res = this->CTest->RunCommand(command.c_str(), &output, &errors,
 | 
	
		
			
				|  |  | +      &retVal, tempDir.c_str(), 0 /*this->TimeOut*/);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    *cont->OFS << "  Output: " << output.c_str() << std::endl;
 | 
	
		
			
				|  |  | +    *cont->OFS << "  Errors: " << errors.c_str() << std::endl;
 | 
	
		
			
				|  |  | +    if ( ! res )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +        "Problem running coverage on file: " << it->c_str() << std::endl);
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +        "Command produced error: " << errors << std::endl);
 | 
	
		
			
				|  |  | +      cont->Error ++;
 | 
	
		
			
				|  |  | +      continue;
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    if ( retVal != 0 )
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE, "Coverage command returned: "
 | 
	
		
			
				|  |  | +        << retVal << " while processing: " << it->c_str() << std::endl);
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +        "Command produced error: " << cont->Error << std::endl);
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +      "--------------------------------------------------------------"
 | 
	
		
			
				|  |  | +      << std::endl
 | 
	
		
			
				|  |  | +      << output << std::endl
 | 
	
		
			
				|  |  | +      << "--------------------------------------------------------------"
 | 
	
		
			
				|  |  | +      << std::endl);
 | 
	
		
			
				|  |  | +    std::vector<cmStdString> lines;
 | 
	
		
			
				|  |  | +    std::vector<cmStdString>::iterator line;
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    // Globals for storing current source file and current gcov file;
 | 
	
		
			
				|  |  | +    cmSystemTools::Split(output.c_str(), lines);
 | 
	
		
			
				|  |  | +    for ( line = lines.begin(); line != lines.end(); ++line)
 | 
	
		
			
				|  |  | +      {
 | 
	
		
			
				|  |  | +      std::string sourceFile;
 | 
	
		
			
				|  |  | +      std::string gcovFile;
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, DEBUG, "Line: [" << line->c_str() << "]"
 | 
	
		
			
				|  |  | +        << std::endl);
 | 
	
		
			
				|  |  | +      if ( line->size() == 0 )
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +        // Ignore empty line; probably style 2
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +      else if ( st1re1.find(line->c_str()) )
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +        if ( gcovStyle != 0 )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          if ( gcovStyle != 1 )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  | +              << std::endl);
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  | +            break;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          gcovStyle = 1;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +        actualSourceFile = "";
 | 
	
		
			
				|  |  | +        sourceFile = st1re1.match(2);
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +      else if ( st1re2.find(line->c_str() ) )
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +        if ( gcovStyle != 0 )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          if ( gcovStyle != 1 )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  | +              << std::endl);
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  | +            break;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          gcovStyle = 1;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +        gcovFile = st1re2.match(1);
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +      else if ( st2re1.find(line->c_str() ) )
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +        if ( gcovStyle != 0 )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          if ( gcovStyle != 2 )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  | +              << std::endl);
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  | +            break;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          gcovStyle = 2;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +        actualSourceFile = "";
 | 
	
		
			
				|  |  | +        sourceFile = st2re1.match(1);
 | 
	
		
			
				|  |  |          }
 | 
	
		
			
				|  |  |        else if ( st2re2.find(line->c_str() ) )
 | 
	
		
			
				|  |  |          {
 | 
	
	
		
			
				|  | @@ -403,7 +702,7 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |              {
 | 
	
		
			
				|  |  |              cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  |                << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  |              break;
 | 
	
		
			
				|  |  |              }
 | 
	
		
			
				|  |  |            gcovStyle = 2;
 | 
	
	
		
			
				|  | @@ -417,7 +716,7 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |              {
 | 
	
		
			
				|  |  |              cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  |                << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  |              break;
 | 
	
		
			
				|  |  |              }
 | 
	
		
			
				|  |  |            gcovStyle = 2;
 | 
	
	
		
			
				|  | @@ -433,7 +732,7 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |              {
 | 
	
		
			
				|  |  |              cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  |                << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  |              break;
 | 
	
		
			
				|  |  |              }
 | 
	
		
			
				|  |  |            gcovStyle = 2;
 | 
	
	
		
			
				|  | @@ -450,7 +749,7 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |              {
 | 
	
		
			
				|  |  |              cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  |                << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  |              break;
 | 
	
		
			
				|  |  |              }
 | 
	
		
			
				|  |  |            gcovStyle = 2;
 | 
	
	
		
			
				|  | @@ -467,7 +766,7 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |              {
 | 
	
		
			
				|  |  |              cmCTestLog(this->CTest, ERROR_MESSAGE, "Unknown gcov output style"
 | 
	
		
			
				|  |  |                << std::endl);
 | 
	
		
			
				|  |  | -            error ++;
 | 
	
		
			
				|  |  | +            cont->Error ++;
 | 
	
		
			
				|  |  |              break;
 | 
	
		
			
				|  |  |              }
 | 
	
		
			
				|  |  |            gcovStyle = 2;
 | 
	
	
		
			
				|  | @@ -480,12 +779,13 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |          {
 | 
	
		
			
				|  |  |          cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  |            "Unknown line: [" << line->c_str() << "]" << std::endl);
 | 
	
		
			
				|  |  | -        error ++;
 | 
	
		
			
				|  |  | +        cont->Error ++;
 | 
	
		
			
				|  |  |          //abort();
 | 
	
		
			
				|  |  |          }
 | 
	
		
			
				|  |  |        if ( !gcovFile.empty() && actualSourceFile.size() )
 | 
	
		
			
				|  |  |          {
 | 
	
		
			
				|  |  | -        singleFileCoverageVector* vec = &totalCoverage[actualSourceFile];
 | 
	
		
			
				|  |  | +        cmCTestCoverageHandlerContainer::SingleFileCoverageVector* vec
 | 
	
		
			
				|  |  | +          = &cont->TotalCoverage[actualSourceFile];
 | 
	
		
			
				|  |  |          cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "   in file: "
 | 
	
		
			
				|  |  |            << gcovFile << std::endl);
 | 
	
		
			
				|  |  |          std::ifstream ifile(gcovFile.c_str());
 | 
	
	
		
			
				|  | @@ -527,7 +827,7 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |              if ( lineIdx >= 0 )
 | 
	
		
			
				|  |  |                {
 | 
	
		
			
				|  |  |                while ( vec->size() <=
 | 
	
		
			
				|  |  | -                static_cast<singleFileCoverageVector::size_type>(lineIdx) )
 | 
	
		
			
				|  |  | +                static_cast<size_t>(lineIdx) )
 | 
	
		
			
				|  |  |                  {
 | 
	
		
			
				|  |  |                  vec->push_back(-1);
 | 
	
		
			
				|  |  |                  }
 | 
	
	
		
			
				|  | @@ -550,311 +850,212 @@ int cmCTestCoverageHandler::ProcessHandler()
 | 
	
		
			
				|  |  |          {
 | 
	
		
			
				|  |  |          gcovFile = "";
 | 
	
		
			
				|  |  |          // Is it in the source dir?
 | 
	
		
			
				|  |  | -        if ( sourceFile.size() > sourceDir.size() &&
 | 
	
		
			
				|  |  | -          sourceFile.substr(0, sourceDir.size()) == sourceDir &&
 | 
	
		
			
				|  |  | -          sourceFile[sourceDir.size()] == '/' )
 | 
	
		
			
				|  |  | +        if ( sourceFile.size() > cont->SourceDir.size() &&
 | 
	
		
			
				|  |  | +          sourceFile.substr(0, cont->SourceDir.size()) == cont->SourceDir &&
 | 
	
		
			
				|  |  | +          sourceFile[cont->SourceDir.size()] == '/' )
 | 
	
		
			
				|  |  |            {
 | 
	
		
			
				|  |  |            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "   produced s: "
 | 
	
		
			
				|  |  |              << sourceFile.c_str() << std::endl);
 | 
	
		
			
				|  |  | -          ofs << "  produced in source dir: " << sourceFile.c_str()
 | 
	
		
			
				|  |  | +          *cont->OFS << "  produced in source dir: " << sourceFile.c_str()
 | 
	
		
			
				|  |  |              << std::endl;
 | 
	
		
			
				|  |  |            actualSourceFile
 | 
	
		
			
				|  |  |              = cmSystemTools::CollapseFullPath(sourceFile.c_str());
 | 
	
		
			
				|  |  |            }
 | 
	
		
			
				|  |  |          // Binary dir?
 | 
	
		
			
				|  |  | -        if ( sourceFile.size() > binaryDir.size() &&
 | 
	
		
			
				|  |  | -          sourceFile.substr(0, binaryDir.size()) == binaryDir &&
 | 
	
		
			
				|  |  | -          sourceFile[binaryDir.size()] == '/' )
 | 
	
		
			
				|  |  | -          {
 | 
	
		
			
				|  |  | -          cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "   produced b: "
 | 
	
		
			
				|  |  | -            << sourceFile.c_str() << std::endl);
 | 
	
		
			
				|  |  | -          ofs << "  produced in binary dir: " << sourceFile.c_str()
 | 
	
		
			
				|  |  | -            << std::endl;
 | 
	
		
			
				|  |  | -          actualSourceFile
 | 
	
		
			
				|  |  | -            = cmSystemTools::CollapseFullPath(sourceFile.c_str());
 | 
	
		
			
				|  |  | -          }
 | 
	
		
			
				|  |  | -        if ( actualSourceFile.empty() )
 | 
	
		
			
				|  |  | -          {
 | 
	
		
			
				|  |  | -          if ( missingFiles.find(actualSourceFile) == missingFiles.end() )
 | 
	
		
			
				|  |  | -            {
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | -              "Something went wrong" << std::endl);
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "File: ["
 | 
	
		
			
				|  |  | -              << sourceFile.c_str() << "]" << std::endl);
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "s: ["
 | 
	
		
			
				|  |  | -              << sourceFile.substr(0, sourceDir.size()) << "]" << std::endl);
 | 
	
		
			
				|  |  | -            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "b: ["
 | 
	
		
			
				|  |  | -              << sourceFile.substr(0, binaryDir.size()) << "]" << std::endl);
 | 
	
		
			
				|  |  | -            ofs << "  Something went wrong. Cannot find: "
 | 
	
		
			
				|  |  | -              << sourceFile.c_str()
 | 
	
		
			
				|  |  | -              << " in source dir: " << sourceDir.c_str()
 | 
	
		
			
				|  |  | -              << " or binary dir: " << binaryDir.c_str() << std::endl;
 | 
	
		
			
				|  |  | -            missingFiles.insert(actualSourceFile);
 | 
	
		
			
				|  |  | -            }
 | 
	
		
			
				|  |  | -          }
 | 
	
		
			
				|  |  | -        }
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | -    file_count ++;
 | 
	
		
			
				|  |  | -    if ( file_count % 50 == 0 )
 | 
	
		
			
				|  |  | -      {
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, HANDLER_OUTPUT, " processed: " << file_count
 | 
	
		
			
				|  |  | -        << " out of " << files.size() << std::endl);
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, HANDLER_OUTPUT, "    ");
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | -    }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  cmGeneratedFileStream covSumFile;
 | 
	
		
			
				|  |  | -  cmGeneratedFileStream covLogFile;
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  if (!this->StartResultingXML("Coverage", covSumFile))
 | 
	
		
			
				|  |  | -    {
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | -      "Cannot open coverage summary file." << std::endl);
 | 
	
		
			
				|  |  | -    cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | -    return -1;
 | 
	
		
			
				|  |  | -    }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  this->CTest->StartXML(covSumFile);
 | 
	
		
			
				|  |  | -  // Produce output xml files
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  covSumFile << "<Coverage>" << std::endl
 | 
	
		
			
				|  |  | -    << "\t<StartDateTime>" << coverage_start_time << "</StartDateTime>"
 | 
	
		
			
				|  |  | -    << std::endl;
 | 
	
		
			
				|  |  | -  int logFileCount = 0;
 | 
	
		
			
				|  |  | -  if ( !this->StartCoverageLogFile(covLogFile, logFileCount) )
 | 
	
		
			
				|  |  | -    {
 | 
	
		
			
				|  |  | -    cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | -    return -1;
 | 
	
		
			
				|  |  | -    }
 | 
	
		
			
				|  |  | -  totalCoverageMap::iterator fileIterator;
 | 
	
		
			
				|  |  | -  int cnt = 0;
 | 
	
		
			
				|  |  | -  long total_tested = 0;
 | 
	
		
			
				|  |  | -  long total_untested = 0;
 | 
	
		
			
				|  |  | -  //std::string fullSourceDir = sourceDir + "/";
 | 
	
		
			
				|  |  | -  //std::string fullBinaryDir = binaryDir + "/";
 | 
	
		
			
				|  |  | -  cmCTestLog(this->CTest, HANDLER_OUTPUT, std::endl);
 | 
	
		
			
				|  |  | -  cmCTestLog(this->CTest, HANDLER_OUTPUT,
 | 
	
		
			
				|  |  | -    "   Acumulating results (each . represents one file):" << std::endl);
 | 
	
		
			
				|  |  | -  cmCTestLog(this->CTest, HANDLER_OUTPUT, "    ");
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  std::vector<std::string> errorsWhileAccumulating;
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  file_count = 0;
 | 
	
		
			
				|  |  | -  for ( fileIterator = totalCoverage.begin();
 | 
	
		
			
				|  |  | -    fileIterator != totalCoverage.end();
 | 
	
		
			
				|  |  | -    ++fileIterator )
 | 
	
		
			
				|  |  | -    {
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, HANDLER_OUTPUT, "." << std::flush);
 | 
	
		
			
				|  |  | +        if ( sourceFile.size() > cont->BinaryDir.size() &&
 | 
	
		
			
				|  |  | +          sourceFile.substr(0, cont->BinaryDir.size()) == cont->BinaryDir &&
 | 
	
		
			
				|  |  | +          sourceFile[cont->BinaryDir.size()] == '/' )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "   produced b: "
 | 
	
		
			
				|  |  | +            << sourceFile.c_str() << std::endl);
 | 
	
		
			
				|  |  | +          *cont->OFS << "  produced in binary dir: " << sourceFile.c_str()
 | 
	
		
			
				|  |  | +            << std::endl;
 | 
	
		
			
				|  |  | +          actualSourceFile
 | 
	
		
			
				|  |  | +            = cmSystemTools::CollapseFullPath(sourceFile.c_str());
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +        if ( actualSourceFile.empty() )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          if ( missingFiles.find(actualSourceFile) == missingFiles.end() )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +              "Something went wrong" << std::endl);
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "File: ["
 | 
	
		
			
				|  |  | +              << sourceFile.c_str() << "]" << std::endl);
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "s: ["
 | 
	
		
			
				|  |  | +              << sourceFile.substr(0, cont->SourceDir.size()) << "]" << std::endl);
 | 
	
		
			
				|  |  | +            cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "b: ["
 | 
	
		
			
				|  |  | +              << sourceFile.substr(0, cont->BinaryDir.size()) << "]" << std::endl);
 | 
	
		
			
				|  |  | +            *cont->OFS << "  Something went wrong. Cannot find: "
 | 
	
		
			
				|  |  | +              << sourceFile.c_str()
 | 
	
		
			
				|  |  | +              << " in source dir: " << cont->SourceDir.c_str()
 | 
	
		
			
				|  |  | +              << " or binary dir: " << cont->BinaryDir.c_str() << std::endl;
 | 
	
		
			
				|  |  | +            missingFiles.insert(actualSourceFile);
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  |      file_count ++;
 | 
	
		
			
				|  |  |      if ( file_count % 50 == 0 )
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  |        cmCTestLog(this->CTest, HANDLER_OUTPUT, " processed: " << file_count
 | 
	
		
			
				|  |  | -        << " out of "
 | 
	
		
			
				|  |  | -        << totalCoverage.size() << std::endl);
 | 
	
		
			
				|  |  | +        << " out of " << files.size() << std::endl);
 | 
	
		
			
				|  |  |        cmCTestLog(this->CTest, HANDLER_OUTPUT, "    ");
 | 
	
		
			
				|  |  |        }
 | 
	
		
			
				|  |  | -    if ( cnt % 100 == 0 )
 | 
	
		
			
				|  |  | -      {
 | 
	
		
			
				|  |  | -      this->EndCoverageLogFile(covLogFile, logFileCount);
 | 
	
		
			
				|  |  | -      logFileCount ++;
 | 
	
		
			
				|  |  | -      if ( !this->StartCoverageLogFile(covLogFile, logFileCount) )
 | 
	
		
			
				|  |  | -        {
 | 
	
		
			
				|  |  | -        cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | -        return -1;
 | 
	
		
			
				|  |  | -        }
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | -    const std::string fullFileName = fileIterator->first;
 | 
	
		
			
				|  |  | -    const std::string fileName
 | 
	
		
			
				|  |  | -      = cmSystemTools::GetFilenameName(fullFileName.c_str());
 | 
	
		
			
				|  |  | -    std::string fullFilePath
 | 
	
		
			
				|  |  | -      = cmSystemTools::GetFilenamePath(fullFileName.c_str());
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, "Process file: "
 | 
	
		
			
				|  |  | -      << fullFileName << std::endl);
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | +  return file_count;
 | 
	
		
			
				|  |  | +}
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    cmSystemTools::ConvertToUnixSlashes(fullFilePath);
 | 
	
		
			
				|  |  | +//----------------------------------------------------------------------
 | 
	
		
			
				|  |  | +int cmCTestCoverageHandler::HandleTracePyCoverage(
 | 
	
		
			
				|  |  | +  cmCTestCoverageHandlerContainer* cont)
 | 
	
		
			
				|  |  | +{
 | 
	
		
			
				|  |  | +  cmsys::Glob gl;
 | 
	
		
			
				|  |  | +  gl.RecurseOn();
 | 
	
		
			
				|  |  | +  std::string daGlob = cont->BinaryDir + "/*.cover";
 | 
	
		
			
				|  |  | +  gl.FindFiles(daGlob);
 | 
	
		
			
				|  |  | +  std::vector<std::string> files = gl.GetFiles();
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    if ( !cmSystemTools::FileExists(fullFileName.c_str()) )
 | 
	
		
			
				|  |  | -      {
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, ERROR_MESSAGE, "Cannot find file: "
 | 
	
		
			
				|  |  | -        << fullFileName.c_str() << std::endl);
 | 
	
		
			
				|  |  | -      continue;
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | +  if ( files.size() == 0 )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +      " Cannot find any Python Trace.py coverage files."
 | 
	
		
			
				|  |  | +      << std::endl);
 | 
	
		
			
				|  |  | +    // No coverage files is a valid thing, so the exit code is 0 
 | 
	
		
			
				|  |  | +    return 0;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    bool shouldIDoCoverage
 | 
	
		
			
				|  |  | -      = this->ShouldIDoCoverage(fullFileName.c_str(),
 | 
	
		
			
				|  |  | -        sourceDir.c_str(), binaryDir.c_str());
 | 
	
		
			
				|  |  | -    if ( !shouldIDoCoverage )
 | 
	
		
			
				|  |  | -      {
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | -        ".NoDartCoverage found, so skip coverage check for: "
 | 
	
		
			
				|  |  | -        << fullFileName.c_str()
 | 
	
		
			
				|  |  | -        << std::endl);
 | 
	
		
			
				|  |  | -      continue;
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | +  std::string testingDir = this->CTest->GetBinaryDir() + "/Testing";
 | 
	
		
			
				|  |  | +  std::string tempDir = testingDir + "/CoverageInfo";
 | 
	
		
			
				|  |  | +  std::string currentDirectory = cmSystemTools::GetCurrentWorkingDirectory();
 | 
	
		
			
				|  |  | +  cmSystemTools::MakeDirectory(tempDir.c_str());
 | 
	
		
			
				|  |  | +  cmSystemTools::ChangeDirectory(tempDir.c_str());
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    const singleFileCoverageVector& fcov = fileIterator->second;
 | 
	
		
			
				|  |  | -    covLogFile << "\t<File Name=\""
 | 
	
		
			
				|  |  | -      << this->CTest->MakeXMLSafe(fileName.c_str())
 | 
	
		
			
				|  |  | -      << "\" FullPath=\"" << this->CTest->MakeXMLSafe(
 | 
	
		
			
				|  |  | -        this->CTest->GetShortPathToFile(
 | 
	
		
			
				|  |  | -          fileIterator->first.c_str())) << "\">" << std::endl
 | 
	
		
			
				|  |  | -      << "\t\t<Report>" << std::endl;
 | 
	
		
			
				|  |  | +  cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    std::ifstream ifs(fullFileName.c_str());
 | 
	
		
			
				|  |  | -    if ( !ifs)
 | 
	
		
			
				|  |  | +  std::vector<std::string>::iterator fileIt;
 | 
	
		
			
				|  |  | +  int file_count = 0;
 | 
	
		
			
				|  |  | +  for ( fileIt = files.begin(); fileIt != files.end(); ++ fileIt )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    std::string fileName = this->FindFile(cont, *fileIt);
 | 
	
		
			
				|  |  | +    if ( fileName.empty() )
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  | -      cmOStringStream ostr;
 | 
	
		
			
				|  |  | -      ostr <<  "Cannot open source file: " << fullFileName.c_str();
 | 
	
		
			
				|  |  | -      errorsWhileAccumulating.push_back(ostr.str());
 | 
	
		
			
				|  |  | -      error ++;
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +        "Cannot find source Python file corresponding to: "
 | 
	
		
			
				|  |  | +        << fileIt->c_str() << std::endl);
 | 
	
		
			
				|  |  |        continue;
 | 
	
		
			
				|  |  |        }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -    int tested = 0;
 | 
	
		
			
				|  |  | -    int untested = 0;
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -    singleFileCoverageVector::size_type cc;
 | 
	
		
			
				|  |  | -    std::string line;
 | 
	
		
			
				|  |  | -    for ( cc= 0; cc < fcov.size(); cc ++ )
 | 
	
		
			
				|  |  | -      {
 | 
	
		
			
				|  |  | -      if ( !cmSystemTools::GetLineFromStream(ifs, line) &&
 | 
	
		
			
				|  |  | -        cc != fcov.size() -1 )
 | 
	
		
			
				|  |  | -        {
 | 
	
		
			
				|  |  | -        cmOStringStream ostr;
 | 
	
		
			
				|  |  | -        ostr << "Problem reading source file: " << fullFileName.c_str()
 | 
	
		
			
				|  |  | -          << " line:" << cc;
 | 
	
		
			
				|  |  | -        errorsWhileAccumulating.push_back(ostr.str());
 | 
	
		
			
				|  |  | -        error ++;
 | 
	
		
			
				|  |  | -        break;
 | 
	
		
			
				|  |  | -        }
 | 
	
		
			
				|  |  | -      covLogFile << "\t\t<Line Number=\"" << cc << "\" Count=\"" << fcov[cc]
 | 
	
		
			
				|  |  | -        << "\">"
 | 
	
		
			
				|  |  | -        << this->CTest->MakeXMLSafe(line.c_str()) << "</Line>" << std::endl;
 | 
	
		
			
				|  |  | -      if ( fcov[cc] == 0 )
 | 
	
		
			
				|  |  | -        {
 | 
	
		
			
				|  |  | -        untested ++;
 | 
	
		
			
				|  |  | -        }
 | 
	
		
			
				|  |  | -      else if ( fcov[cc] > 0 )
 | 
	
		
			
				|  |  | -        {
 | 
	
		
			
				|  |  | -        tested ++;
 | 
	
		
			
				|  |  | -        }
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | -    if ( cmSystemTools::GetLineFromStream(ifs, line) )
 | 
	
		
			
				|  |  | -      {
 | 
	
		
			
				|  |  | -      cmOStringStream ostr;
 | 
	
		
			
				|  |  | -      ostr <<  "Looks like there are more lines in the file: " << line;
 | 
	
		
			
				|  |  | -      errorsWhileAccumulating.push_back(ostr.str());
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | -    float cper = 0;
 | 
	
		
			
				|  |  | -    float cmet = 0;
 | 
	
		
			
				|  |  | -    if ( tested + untested > 0 )
 | 
	
		
			
				|  |  | +    std::string actualSourceFile
 | 
	
		
			
				|  |  | +      = cmSystemTools::CollapseFullPath(fileName.c_str());
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +      "   Check coverage for file: " << actualSourceFile.c_str()
 | 
	
		
			
				|  |  | +      << std::endl);
 | 
	
		
			
				|  |  | +    cmCTestCoverageHandlerContainer::SingleFileCoverageVector* vec
 | 
	
		
			
				|  |  | +      = &cont->TotalCoverage[actualSourceFile];
 | 
	
		
			
				|  |  | +    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | +      "   in file: " << fileIt->c_str() << std::endl);
 | 
	
		
			
				|  |  | +    std::ifstream ifile(fileIt->c_str());
 | 
	
		
			
				|  |  | +    if ( ! ifile )
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  | -      cper = (100 * SAFEDIV(static_cast<float>(tested),
 | 
	
		
			
				|  |  | -          static_cast<float>(tested + untested)));
 | 
	
		
			
				|  |  | -      cmet = ( SAFEDIV(static_cast<float>(tested + 10),
 | 
	
		
			
				|  |  | -          static_cast<float>(tested + untested + 10)));
 | 
	
		
			
				|  |  | +      cmCTestLog(this->CTest, ERROR_MESSAGE, "Cannot open file: "
 | 
	
		
			
				|  |  | +        << fileIt->c_str() << std::endl);
 | 
	
		
			
				|  |  |        }
 | 
	
		
			
				|  |  | -    total_tested += tested;
 | 
	
		
			
				|  |  | -    total_untested += untested;
 | 
	
		
			
				|  |  | -    covLogFile << "\t\t</Report>" << std::endl
 | 
	
		
			
				|  |  | -      << "\t</File>" << std::endl;
 | 
	
		
			
				|  |  | -    covSumFile << "\t<File Name=\"" << this->CTest->MakeXMLSafe(fileName)
 | 
	
		
			
				|  |  | -      << "\" FullPath=\"" << this->CTest->MakeXMLSafe(
 | 
	
		
			
				|  |  | -        this->CTest->GetShortPathToFile(fullFileName.c_str()))
 | 
	
		
			
				|  |  | -      << "\" Covered=\"" << (cmet>0?"true":"false") << "\">\n"
 | 
	
		
			
				|  |  | -      << "\t\t<LOCTested>" << tested << "</LOCTested>\n"
 | 
	
		
			
				|  |  | -      << "\t\t<LOCUnTested>" << untested << "</LOCUnTested>\n"
 | 
	
		
			
				|  |  | -      << "\t\t<PercentCoverage>";
 | 
	
		
			
				|  |  | -    covSumFile.setf(std::ios::fixed, std::ios::floatfield);
 | 
	
		
			
				|  |  | -    covSumFile.precision(2);
 | 
	
		
			
				|  |  | -    covSumFile << (cper) << "</PercentCoverage>\n"
 | 
	
		
			
				|  |  | -      << "\t\t<CoverageMetric>";
 | 
	
		
			
				|  |  | -    covSumFile.setf(std::ios::fixed, std::ios::floatfield);
 | 
	
		
			
				|  |  | -    covSumFile.precision(2);
 | 
	
		
			
				|  |  | -    covSumFile << (cmet) << "</CoverageMetric>\n"
 | 
	
		
			
				|  |  | -      << "\t</File>" << std::endl;
 | 
	
		
			
				|  |  | -    cnt ++;
 | 
	
		
			
				|  |  | -    }
 | 
	
		
			
				|  |  | -  this->EndCoverageLogFile(covLogFile, logFileCount);
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  if ( errorsWhileAccumulating.size() > 0 )
 | 
	
		
			
				|  |  | -    {
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, ERROR_MESSAGE, std::endl);
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | -      "Error(s) while acumulating results:" << std::endl);
 | 
	
		
			
				|  |  | -    std::vector<std::string>::iterator erIt;
 | 
	
		
			
				|  |  | -    for ( erIt = errorsWhileAccumulating.begin();
 | 
	
		
			
				|  |  | -      erIt != errorsWhileAccumulating.end();
 | 
	
		
			
				|  |  | -      ++ erIt )
 | 
	
		
			
				|  |  | +    else
 | 
	
		
			
				|  |  |        {
 | 
	
		
			
				|  |  | -      cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | -        "  " << erIt->c_str() << std::endl);
 | 
	
		
			
				|  |  | -      }
 | 
	
		
			
				|  |  | -    }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  int total_lines = total_tested + total_untested;
 | 
	
		
			
				|  |  | -  float percent_coverage = 100 * SAFEDIV(static_cast<float>(total_tested),
 | 
	
		
			
				|  |  | -    static_cast<float>(total_lines));
 | 
	
		
			
				|  |  | -  if ( total_lines == 0 )
 | 
	
		
			
				|  |  | -    {
 | 
	
		
			
				|  |  | -    percent_coverage = 0;
 | 
	
		
			
				|  |  | -    }
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  std::string end_time = this->CTest->CurrentTime();
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  covSumFile << "\t<LOCTested>" << total_tested << "</LOCTested>\n"
 | 
	
		
			
				|  |  | -    << "\t<LOCUntested>" << total_untested << "</LOCUntested>\n"
 | 
	
		
			
				|  |  | -    << "\t<LOC>" << total_lines << "</LOC>\n"
 | 
	
		
			
				|  |  | -    << "\t<PercentCoverage>";
 | 
	
		
			
				|  |  | -  covSumFile.setf(std::ios::fixed, std::ios::floatfield);
 | 
	
		
			
				|  |  | -  covSumFile.precision(2);
 | 
	
		
			
				|  |  | -  covSumFile << (percent_coverage)<< "</PercentCoverage>\n"
 | 
	
		
			
				|  |  | -    << "\t<EndDateTime>" << end_time << "</EndDateTime>\n";
 | 
	
		
			
				|  |  | -  covSumFile << "<ElapsedMinutes>" <<
 | 
	
		
			
				|  |  | -    static_cast<int>((cmSystemTools::GetTime() - elapsed_time_start)/6)/10.0
 | 
	
		
			
				|  |  | -    << "</ElapsedMinutes>"
 | 
	
		
			
				|  |  | -    << "</Coverage>" << std::endl;
 | 
	
		
			
				|  |  | -  this->CTest->EndXML(covSumFile);
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -  cmCTestLog(this->CTest, HANDLER_OUTPUT, "\tCovered LOC:         "
 | 
	
		
			
				|  |  | -    << total_tested << std::endl
 | 
	
		
			
				|  |  | -    << "\tNot covered LOC:     " << total_untested << std::endl
 | 
	
		
			
				|  |  | -    << "\tTotal LOC:           " << total_lines << std::endl
 | 
	
		
			
				|  |  | -    << "\tPercentage Coverage: "
 | 
	
		
			
				|  |  | -    << std::setiosflags(std::ios::fixed)
 | 
	
		
			
				|  |  | -    << std::setprecision(2)
 | 
	
		
			
				|  |  | -    << (percent_coverage) << "%" << std::endl);
 | 
	
		
			
				|  |  | +      long cnt = -1;
 | 
	
		
			
				|  |  | +      std::string nl;
 | 
	
		
			
				|  |  | +      while ( cmSystemTools::GetLineFromStream(ifile, nl) )
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +        cnt ++;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  ofs << "\tCovered LOC:         " << total_tested << std::endl
 | 
	
		
			
				|  |  | -    << "\tNot covered LOC:     " << total_untested << std::endl
 | 
	
		
			
				|  |  | -    << "\tTotal LOC:           " << total_lines << std::endl
 | 
	
		
			
				|  |  | -    << "\tPercentage Coverage: "
 | 
	
		
			
				|  |  | -    << std::setiosflags(std::ios::fixed)
 | 
	
		
			
				|  |  | -    << std::setprecision(2)
 | 
	
		
			
				|  |  | -    << (percent_coverage) << "%" << std::endl;
 | 
	
		
			
				|  |  | +        // Skip empty lines
 | 
	
		
			
				|  |  | +        if ( !nl.size() )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          continue;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | +        // Skip unused lines
 | 
	
		
			
				|  |  | +        if ( nl.size() < 12 )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          continue;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -  if ( error )
 | 
	
		
			
				|  |  | -    {
 | 
	
		
			
				|  |  | -    return -1;
 | 
	
		
			
				|  |  | +        // Read the coverage count from the beginning of the Trace.py output
 | 
	
		
			
				|  |  | +        // line
 | 
	
		
			
				|  |  | +        std::string prefix = nl.substr(0, 6);
 | 
	
		
			
				|  |  | +        if ( prefix[5] != ' ' && prefix[5] != ':' )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          // This is a hack. We should really do something more elaborate
 | 
	
		
			
				|  |  | +          prefix = nl.substr(0, 7);
 | 
	
		
			
				|  |  | +          if ( prefix[6] != ' ' && prefix[6] != ':' )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            prefix = nl.substr(0, 8);
 | 
	
		
			
				|  |  | +            if ( prefix[7] != ' ' && prefix[7] != ':' )
 | 
	
		
			
				|  |  | +              {
 | 
	
		
			
				|  |  | +              cmCTestLog(this->CTest, ERROR_MESSAGE,
 | 
	
		
			
				|  |  | +                "Currently the limit is maximum coverage of 999999"
 | 
	
		
			
				|  |  | +                << std::endl);
 | 
	
		
			
				|  |  | +              }
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +        int cov = atoi(prefix.c_str());
 | 
	
		
			
				|  |  | +        if ( prefix[prefix.size()-1] != ':' )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          // This line does not have ':' so no coverage here. That said,
 | 
	
		
			
				|  |  | +          // Trace.py does not handle not covered lines versus comments etc.
 | 
	
		
			
				|  |  | +          // So, this will be set to 0.
 | 
	
		
			
				|  |  | +          cov = 0;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +        cmCTestLog(this->CTest, DEBUG, "Prefix: " << prefix.c_str()
 | 
	
		
			
				|  |  | +          << " cov: " << cov
 | 
	
		
			
				|  |  | +          << std::endl);
 | 
	
		
			
				|  |  | +        // Read the line number starting at the 10th character of the gcov
 | 
	
		
			
				|  |  | +        // output line
 | 
	
		
			
				|  |  | +        int lineIdx = cnt;
 | 
	
		
			
				|  |  | +        if ( lineIdx >= 0 )
 | 
	
		
			
				|  |  | +          {
 | 
	
		
			
				|  |  | +          while ( vec->size() <=
 | 
	
		
			
				|  |  | +            static_cast<size_t>(lineIdx) )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            vec->push_back(-1);
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          // Initially all entries are -1 (not used). If we get coverage
 | 
	
		
			
				|  |  | +          // information, increment it to 0 first.
 | 
	
		
			
				|  |  | +          if ( (*vec)[lineIdx] < 0 )
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +            if ( cov >= 0 )
 | 
	
		
			
				|  |  | +              {
 | 
	
		
			
				|  |  | +              (*vec)[lineIdx] = 0;
 | 
	
		
			
				|  |  | +              }
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +          (*vec)[lineIdx] += cov;
 | 
	
		
			
				|  |  | +          }
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +      }
 | 
	
		
			
				|  |  | +    ++ file_count;
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  | -  return 0;
 | 
	
		
			
				|  |  | +  cmSystemTools::ChangeDirectory(currentDirectory.c_str());
 | 
	
		
			
				|  |  | +  return file_count;
 | 
	
		
			
				|  |  |  }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  //----------------------------------------------------------------------
 | 
	
		
			
				|  |  | -void cmCTestCoverageHandler::PopulateCustomVectors(cmMakefile *mf)
 | 
	
		
			
				|  |  | +std::string cmCTestCoverageHandler::FindFile(
 | 
	
		
			
				|  |  | +  cmCTestCoverageHandlerContainer* cont,
 | 
	
		
			
				|  |  | +  std::string fileName)
 | 
	
		
			
				|  |  |  {
 | 
	
		
			
				|  |  | -  cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
 | 
	
		
			
				|  |  | -    " Add coverage exclude regular expressions." << std::endl);
 | 
	
		
			
				|  |  | -  this->CTest->PopulateCustomVector(mf, "CTEST_CUSTOM_COVERAGE_EXCLUDE",
 | 
	
		
			
				|  |  | -                                this->CustomCoverageExclude);
 | 
	
		
			
				|  |  | -  std::vector<cmStdString>::iterator it;
 | 
	
		
			
				|  |  | -  for ( it = this->CustomCoverageExclude.begin();
 | 
	
		
			
				|  |  | -    it != this->CustomCoverageExclude.end();
 | 
	
		
			
				|  |  | -    ++ it )
 | 
	
		
			
				|  |  | +  std::string fileNameNoE
 | 
	
		
			
				|  |  | +    = cmSystemTools::GetFilenameWithoutLastExtension(fileName);
 | 
	
		
			
				|  |  | +  // First check in source and binary directory
 | 
	
		
			
				|  |  | +  std::string fullName = cont->SourceDir + "/" + fileNameNoE + ".py";
 | 
	
		
			
				|  |  | +  if ( cmSystemTools::FileExists(fullName.c_str()) )
 | 
	
		
			
				|  |  |      {
 | 
	
		
			
				|  |  | -    cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT, " Add coverage exclude: "
 | 
	
		
			
				|  |  | -      << it->c_str() << std::endl);
 | 
	
		
			
				|  |  | +    return fullName;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +  fullName = cont->BinaryDir + "/" + fileNameNoE + ".py";
 | 
	
		
			
				|  |  | +  if ( cmSystemTools::FileExists(fullName.c_str()) )
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +    return fullName;
 | 
	
		
			
				|  |  |      }
 | 
	
		
			
				|  |  | +  return "";
 | 
	
		
			
				|  |  |  }
 |