ENH: Add initial memory check support which works for Valgrind

This commit is contained in:
Andy Cedilnik 2003-12-15 17:26:00 -05:00
parent ce8a34907a
commit 5b232ded15
10 changed files with 523 additions and 155 deletions

View File

@ -69,7 +69,9 @@ IF(BUILD_TESTING)
DOC "Path to program used to compress files for transfer to the dart server") DOC "Path to program used to compress files for transfer to the dart server")
FIND_PROGRAM(GUNZIPCOMMAND gunzip DOC "Path to gunzip executable") FIND_PROGRAM(GUNZIPCOMMAND gunzip DOC "Path to gunzip executable")
FIND_PROGRAM(JAVACOMMAND java DOC "Path to java command, used by the Dart server to create html.") FIND_PROGRAM(JAVACOMMAND java DOC "Path to java command, used by the Dart server to create html.")
FIND_PROGRAM(PURIFYCOMMAND purify FIND_PROGRAM(MEMORYCHECK_COMMAND
NAMES purify valgrind boundscheck
PATHS
"[HKEY_LOCAL_MACHINE\\SOFTWARE\\Rational Software\\Purify\\Setup;InstallFolder]" "[HKEY_LOCAL_MACHINE\\SOFTWARE\\Rational Software\\Purify\\Setup;InstallFolder]"
DOC "Path to Rational purify command, used for memory error detection." DOC "Path to Rational purify command, used for memory error detection."
) )
@ -95,11 +97,25 @@ IF(BUILD_TESTING)
ELSE(WIN32) ELSE(WIN32)
SET(DART_NAME_COMPONENT "NAME") SET(DART_NAME_COMPONENT "NAME")
ENDIF(WIN32) ENDIF(WIN32)
SET(BUILD_NAME_SYSTEM_NAME "${CMAKE_SYSTEM_NAME}")
IF(WIN32)
SET(BUILD_NAME_SYSTEM_NAME "Win32")
ENDIF(WIN32)
IF(UNIX OR BORLAND) IF(UNIX OR BORLAND)
GET_FILENAME_COMPONENT(DART_CXX_NAME "${CMAKE_CXX_COMPILER}" ${DART_NAME_COMPONENT}) GET_FILENAME_COMPONENT(DART_CXX_NAME "${CMAKE_CXX_COMPILER}" ${DART_NAME_COMPONENT})
ELSE(UNIX OR BORLAND) ELSE(UNIX OR BORLAND)
GET_FILENAME_COMPONENT(DART_CXX_NAME "${CMAKE_BUILD_TOOL}" ${DART_NAME_COMPONENT}) GET_FILENAME_COMPONENT(DART_CXX_NAME "${CMAKE_BUILD_TOOL}" ${DART_NAME_COMPONENT})
ENDIF(UNIX OR BORLAND) ENDIF(UNIX OR BORLAND)
IF(DART_CXX_NAME MATCHES "msdev")
SET(DART_CXX_NAME "vs60")
ENDIF(DART_CXX_NAME MATCHES "msdev")
IF(DART_CXX_NAME MATCHES "devenv")
IF(CMAKE_GENERATOR MATCHES "^Visual Studio 7$")
SET(DART_CXX_NAME "vs70")
ELSE(CMAKE_GENERATOR MATCHES "^Visual Studio 7$")
SET(DART_CXX_NAME "vs71")
ENDIF(CMAKE_GENERATOR MATCHES "^Visual Studio 7$")
ENDIF(DART_CXX_NAME MATCHES "devenv")
SET(BUILDNAME "${CMAKE_SYSTEM_NAME}-${DART_CXX_NAME}") SET(BUILDNAME "${CMAKE_SYSTEM_NAME}-${DART_CXX_NAME}")
MESSAGE(STATUS "Using Buildname: ${BUILDNAME}") MESSAGE(STATUS "Using Buildname: ${BUILDNAME}")
ENDIF(NOT BUILDNAME) ENDIF(NOT BUILDNAME)
@ -140,7 +156,7 @@ IF(BUILD_TESTING)
# configure files # configure files
CONFIGURE_FILE( CONFIGURE_FILE(
${DART_ROOT}/Source/Client/Utility.conf.in ${DART_ROOT}/Source/Client/Dart.conf.in
${PROJECT_BINARY_DIR}/DartConfiguration.tcl ) ${PROJECT_BINARY_DIR}/DartConfiguration.tcl )
# #

View File

@ -40,6 +40,8 @@ ScpCommand: @SCPCOMMAND@
PurifyCommand: @PURIFYCOMMAND@ PurifyCommand: @PURIFYCOMMAND@
ValgrindCommand: @VALGRIND_COMMAND@ ValgrindCommand: @VALGRIND_COMMAND@
ValgrindCommandOptions: @VALGRIND_COMMAND_OPTIONS@ ValgrindCommandOptions: @VALGRIND_COMMAND_OPTIONS@
MemoryCheckCommand: @MEMORYCHECK_COMMAND@
MemoryCheckCommandOptions: @MEMORYCHECK_COMMAND_OPTIONS@
CoverageCommand: @COVERAGE_COMMAND@ CoverageCommand: @COVERAGE_COMMAND@
# Compression commands # Compression commands
GunzipCommand: @GUNZIPCOMMAND@ GunzipCommand: @GUNZIPCOMMAND@

View File

@ -37,7 +37,7 @@ cmCTestSubmit::cmCTestSubmit() : m_HTTPProxy(), m_FTPProxy()
} }
if ( getenv("HTTP_PROXY_TYPE") ) if ( getenv("HTTP_PROXY_TYPE") )
{ {
std::string type = getenv("HTTP_PROXY_TYPE"); cmStdString type = getenv("HTTP_PROXY_TYPE");
// HTTP/SOCKS4/SOCKS5 // HTTP/SOCKS4/SOCKS5
if ( type == "HTTP" ) if ( type == "HTTP" )
{ {
@ -66,7 +66,7 @@ cmCTestSubmit::cmCTestSubmit() : m_HTTPProxy(), m_FTPProxy()
} }
if ( getenv("FTP_PROXY_TYPE") ) if ( getenv("FTP_PROXY_TYPE") )
{ {
std::string type = getenv("FTP_PROXY_TYPE"); cmStdString type = getenv("FTP_PROXY_TYPE");
// HTTP/SOCKS4/SOCKS5 // HTTP/SOCKS4/SOCKS5
if ( type == "HTTP" ) if ( type == "HTTP" )
{ {
@ -92,10 +92,10 @@ cmCTestSubmit::cmCTestSubmit() : m_HTTPProxy(), m_FTPProxy()
} }
} }
bool cmCTestSubmit::SubmitUsingFTP(const std::string& localprefix, bool cmCTestSubmit::SubmitUsingFTP(const cmStdString& localprefix,
const std::vector<std::string>& files, const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url) const cmStdString& url)
{ {
CURL *curl; CURL *curl;
CURLcode res; CURLcode res;
@ -105,7 +105,7 @@ bool cmCTestSubmit::SubmitUsingFTP(const std::string& localprefix,
/* In windows, this will init the winsock stuff */ /* In windows, this will init the winsock stuff */
::curl_global_init(CURL_GLOBAL_ALL); ::curl_global_init(CURL_GLOBAL_ALL);
std::string::size_type cc; cmStdString::size_type cc;
for ( cc = 0; cc < files.size(); cc ++ ) for ( cc = 0; cc < files.size(); cc ++ )
{ {
/* get a curl handle */ /* get a curl handle */
@ -132,8 +132,8 @@ bool cmCTestSubmit::SubmitUsingFTP(const std::string& localprefix,
// enable uploading // enable uploading
::curl_easy_setopt(curl, CURLOPT_UPLOAD, TRUE) ; ::curl_easy_setopt(curl, CURLOPT_UPLOAD, TRUE) ;
std::string local_file = localprefix + "/" + files[cc]; cmStdString local_file = localprefix + "/" + files[cc];
std::string upload_as = url + "/" + remoteprefix + files[cc]; cmStdString upload_as = url + "/" + remoteprefix + files[cc];
struct stat st; struct stat st;
if ( ::stat(local_file.c_str(), &st) ) if ( ::stat(local_file.c_str(), &st) )
@ -184,10 +184,10 @@ bool cmCTestSubmit::SubmitUsingFTP(const std::string& localprefix,
} }
// Uploading files is simpler // Uploading files is simpler
bool cmCTestSubmit::SubmitUsingHTTP(const std::string& localprefix, bool cmCTestSubmit::SubmitUsingHTTP(const cmStdString& localprefix,
const std::vector<std::string>& files, const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url) const cmStdString& url)
{ {
CURL *curl; CURL *curl;
CURLcode res; CURLcode res;
@ -196,7 +196,7 @@ bool cmCTestSubmit::SubmitUsingHTTP(const std::string& localprefix,
/* In windows, this will init the winsock stuff */ /* In windows, this will init the winsock stuff */
::curl_global_init(CURL_GLOBAL_ALL); ::curl_global_init(CURL_GLOBAL_ALL);
std::string::size_type cc, kk; cmStdString::size_type cc, kk;
for ( cc = 0; cc < files.size(); cc ++ ) for ( cc = 0; cc < files.size(); cc ++ )
{ {
/* get a curl handle */ /* get a curl handle */
@ -231,9 +231,9 @@ bool cmCTestSubmit::SubmitUsingHTTP(const std::string& localprefix,
::curl_easy_setopt(curl, CURLOPT_VERBOSE, 1); ::curl_easy_setopt(curl, CURLOPT_VERBOSE, 1);
} }
std::string local_file = localprefix + "/" + files[cc]; cmStdString local_file = localprefix + "/" + files[cc];
std::string remote_file = remoteprefix + files[cc]; cmStdString remote_file = remoteprefix + files[cc];
std::string ofile = ""; cmStdString ofile = "";
for ( kk = 0; kk < remote_file.size(); kk ++ ) for ( kk = 0; kk < remote_file.size(); kk ++ )
{ {
char c = remote_file[kk]; char c = remote_file[kk];
@ -256,7 +256,7 @@ bool cmCTestSubmit::SubmitUsingHTTP(const std::string& localprefix,
ofile.append(hex); ofile.append(hex);
} }
} }
std::string upload_as = url + "?FileName=" + ofile; cmStdString upload_as = url + "?FileName=" + ofile;
struct stat st; struct stat st;
if ( ::stat(local_file.c_str(), &st) ) if ( ::stat(local_file.c_str(), &st) )
@ -301,16 +301,16 @@ bool cmCTestSubmit::SubmitUsingHTTP(const std::string& localprefix,
return true; return true;
} }
bool cmCTestSubmit::TriggerUsingHTTP(const std::vector<std::string>& files, bool cmCTestSubmit::TriggerUsingHTTP(const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url) const cmStdString& url)
{ {
CURL *curl; CURL *curl;
/* In windows, this will init the winsock stuff */ /* In windows, this will init the winsock stuff */
::curl_global_init(CURL_GLOBAL_ALL); ::curl_global_init(CURL_GLOBAL_ALL);
std::string::size_type cc, kk; cmStdString::size_type cc, kk;
for ( cc = 0; cc < files.size(); cc ++ ) for ( cc = 0; cc < files.size(); cc ++ )
{ {
/* get a curl handle */ /* get a curl handle */
@ -339,8 +339,8 @@ bool cmCTestSubmit::TriggerUsingHTTP(const std::vector<std::string>& files,
{ {
::curl_easy_setopt(curl, CURLOPT_VERBOSE, 1); ::curl_easy_setopt(curl, CURLOPT_VERBOSE, 1);
} }
std::string file = remoteprefix + files[cc]; cmStdString file = remoteprefix + files[cc];
std::string ofile = ""; cmStdString ofile = "";
for ( kk = 0; kk < file.size(); kk ++ ) for ( kk = 0; kk < file.size(); kk ++ )
{ {
char c = file[kk]; char c = file[kk];
@ -363,7 +363,7 @@ bool cmCTestSubmit::TriggerUsingHTTP(const std::vector<std::string>& files,
ofile.append(hex); ofile.append(hex);
} }
} }
std::string turl = url + "?xmlfile=" + ofile; cmStdString turl = url + "?xmlfile=" + ofile;
if ( m_Verbose ) if ( m_Verbose )
{ {
std::cout << " Trigger url: " << turl.c_str() << std::endl; std::cout << " Trigger url: " << turl.c_str() << std::endl;
@ -386,10 +386,10 @@ bool cmCTestSubmit::TriggerUsingHTTP(const std::vector<std::string>& files,
return true; return true;
} }
bool cmCTestSubmit::SubmitUsingSCP(const std::string&, bool cmCTestSubmit::SubmitUsingSCP(const cmStdString&,
const std::vector<std::string>&, const std::vector<cmStdString>&,
const std::string&, const cmStdString&,
const std::string&) const cmStdString&)
{ {
std::cout << "SubmitUsingSCP is not yet implemented" << std::endl; std::cout << "SubmitUsingSCP is not yet implemented" << std::endl;
return false; return false;

View File

@ -41,27 +41,27 @@ public:
/** /**
* Submit file using various ways * Submit file using various ways
*/ */
bool SubmitUsingFTP(const std::string& localprefix, bool SubmitUsingFTP(const cmStdString& localprefix,
const std::vector<std::string>& files, const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url); const cmStdString& url);
bool SubmitUsingHTTP(const std::string& localprefix, bool SubmitUsingHTTP(const cmStdString& localprefix,
const std::vector<std::string>& files, const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url); const cmStdString& url);
bool SubmitUsingSCP(const std::string& localprefix, bool SubmitUsingSCP(const cmStdString& localprefix,
const std::vector<std::string>& files, const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url); const cmStdString& url);
bool TriggerUsingHTTP(const std::vector<std::string>& files, bool TriggerUsingHTTP(const std::vector<cmStdString>& files,
const std::string& remoteprefix, const cmStdString& remoteprefix,
const std::string& url); const cmStdString& url);
private: private:
std::string m_HTTPProxy; cmStdString m_HTTPProxy;
int m_HTTPProxyType; int m_HTTPProxyType;
std::string m_FTPProxy; cmStdString m_FTPProxy;
int m_FTPProxyType; int m_FTPProxyType;
bool m_Verbose; bool m_Verbose;
}; };

View File

@ -62,7 +62,7 @@ void cmCursesPathWidget::OnTab(cmCursesMainForm* fm, WINDOW* w)
{ {
glob = cstr + "*"; glob = cstr + "*";
} }
std::vector<std::string> dirs; std::vector<cmStdString> dirs;
cmSystemTools::SimpleGlob(glob.c_str(), dirs, (m_Type == cmCacheManager::PATH?-1:0)); cmSystemTools::SimpleGlob(glob.c_str(), dirs, (m_Type == cmCacheManager::PATH?-1:0));
if ( m_CurrentIndex < dirs.size() ) if ( m_CurrentIndex < dirs.size() )

View File

@ -22,10 +22,8 @@
#include <cmsys/Directory.hxx> #include <cmsys/Directory.hxx>
#include "cmListFileCache.h" #include "cmListFileCache.h"
#ifdef HAVE_CURL #include "cmCTestSubmit.h"
# include "cmCTestSubmit.h" #include "curl/curl.h"
# include "curl/curl.h"
#endif
#include <cmsys/RegularExpression.hxx> #include <cmsys/RegularExpression.hxx>
#include <cmsys/Process.h> #include <cmsys/Process.h>
@ -38,7 +36,6 @@
#define SAFEDIV(x,y) (((y)!=0)?((x)/(y)):(0)) #define SAFEDIV(x,y) (((y)!=0)?((x)/(y)):(0))
#ifdef HAVE_CURL
static struct tm* GetNightlyTime(std::string str) static struct tm* GetNightlyTime(std::string str)
{ {
struct tm* lctime; struct tm* lctime;
@ -66,7 +63,6 @@ static struct tm* GetNightlyTime(std::string str)
lctime = gmtime(&ntime); lctime = gmtime(&ntime);
return lctime; return lctime;
} }
#endif
static std::string CleanString(std::string str) static std::string CleanString(std::string str)
{ {
@ -175,6 +171,32 @@ static const char* cmCTestWarningExceptions[] = {
0 0
}; };
static const char* cmCTestMemCheckResultStrings[] = {
"ABR",
"ABW",
"ABWL",
"COR",
"EXU",
"FFM",
"FIM",
"FMM",
"FMR",
"FMW",
"FUM",
"IPR",
"IPW",
"MAF",
"MLK",
"MPK",
"NPR",
"ODS",
"PAR",
"PLK",
"UMC",
"UMR",
0
};
std::string cmCTest::MakeXMLSafe(const std::string& str) std::string cmCTest::MakeXMLSafe(const std::string& str)
{ {
cmOStringStream ost; cmOStringStream ost;
@ -271,6 +293,7 @@ cmCTest::cmCTest()
m_RunConfigurationScript = false; m_RunConfigurationScript = false;
m_TestModel = cmCTest::EXPERIMENTAL; m_TestModel = cmCTest::EXPERIMENTAL;
m_TimeOut = 0; m_TimeOut = 0;
m_CompatibilityMode = 1;
int cc; int cc;
for ( cc=0; cc < cmCTest::LAST_TEST; cc ++ ) for ( cc=0; cc < cmCTest::LAST_TEST; cc ++ )
{ {
@ -369,14 +392,12 @@ void cmCTest::Initialize()
} }
if ( tag.size() == 0 || m_Tests[cmCTest::START_TEST] || m_Tests[ALL_TEST]) if ( tag.size() == 0 || m_Tests[cmCTest::START_TEST] || m_Tests[ALL_TEST])
{ {
#ifdef HAVE_CURL
//std::cout << "TestModel: " << this->GetTestModelString() << std::endl; //std::cout << "TestModel: " << this->GetTestModelString() << std::endl;
//std::cout << "TestModel: " << m_TestModel << std::endl; //std::cout << "TestModel: " << m_TestModel << std::endl;
if ( m_TestModel == cmCTest::NIGHTLY ) if ( m_TestModel == cmCTest::NIGHTLY )
{ {
lctime = ::GetNightlyTime(m_DartConfiguration["NightlyStartTime"]); lctime = ::GetNightlyTime(m_DartConfiguration["NightlyStartTime"]);
} }
#endif
char datestring[100]; char datestring[100];
sprintf(datestring, "%04d%02d%02d-%02d%02d", sprintf(datestring, "%04d%02d%02d-%02d%02d",
lctime->tm_year + 1900, lctime->tm_year + 1900,
@ -427,9 +448,9 @@ bool cmCTest::SetTest(const char* ttype)
{ {
m_Tests[cmCTest::COVERAGE_TEST] = 1; m_Tests[cmCTest::COVERAGE_TEST] = 1;
} }
else if ( cmSystemTools::LowerCase(ttype) == "purify" ) else if ( cmSystemTools::LowerCase(ttype) == "memcheck" )
{ {
m_Tests[cmCTest::PURIFY_TEST] = 1; m_Tests[cmCTest::MEMCHECK_TEST] = 1;
} }
else if ( cmSystemTools::LowerCase(ttype) == "submit" ) else if ( cmSystemTools::LowerCase(ttype) == "submit" )
{ {
@ -543,7 +564,6 @@ int cmCTest::UpdateDirectory()
} }
std::string extra_update_opts; std::string extra_update_opts;
#ifdef HAVE_CURL
if ( m_TestModel == cmCTest::NIGHTLY ) if ( m_TestModel == cmCTest::NIGHTLY )
{ {
struct tm* t = ::GetNightlyTime(m_DartConfiguration["NightlyStartTime"]); struct tm* t = ::GetNightlyTime(m_DartConfiguration["NightlyStartTime"]);
@ -560,7 +580,6 @@ int cmCTest::UpdateDirectory()
extra_update_opts += "-D \"" + today_update_date +"\""; extra_update_opts += "-D \"" + today_update_date +"\"";
//std::cout << "Update: " << extra_update_opts << std::endl; //std::cout << "Update: " << extra_update_opts << std::endl;
} }
#endif
std::string command = cvsCommand + " -z3 update " + cvsOptions + std::string command = cvsCommand + " -z3 update " + cvsOptions +
" " + extra_update_opts; " " + extra_update_opts;
@ -597,8 +616,8 @@ int cmCTest::UpdateDirectory()
<< "\t<BuildName>" << m_DartConfiguration["BuildName"] << "\t<BuildName>" << m_DartConfiguration["BuildName"]
<< "</BuildName>\n" << "</BuildName>\n"
<< "\t<BuildStamp>" << m_CurrentTag << "-" << "\t<BuildStamp>" << m_CurrentTag << "-"
<< this->GetTestModelString() << "</BuildStamp>\n" << this->GetTestModelString() << "</BuildStamp>" << std::endl;
<< "\t<StartDateTime>" << start_time << "</StartDateTime>\n" os << "\t<StartDateTime>" << start_time << "</StartDateTime>\n"
<< "\t<UpdateCommand>" << command << "</UpdateCommand>\n" << "\t<UpdateCommand>" << command << "</UpdateCommand>\n"
<< "\t<UpdateReturnStatus>"; << "\t<UpdateReturnStatus>";
if ( retVal ) if ( retVal )
@ -904,12 +923,8 @@ int cmCTest::ConfigureDirectory()
if ( os ) if ( os )
{ {
os << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" this->StartXML(os);
<< "<Site BuildName=\"" << m_DartConfiguration["BuildName"] os << "<Configure>\n"
<< "\" BuildStamp=\"" << m_CurrentTag << "-"
<< this->GetTestModelString() << "\" Name=\""
<< m_DartConfiguration["Site"] << "\">\n"
<< "<Configure>\n"
<< "\t<StartDateTime>" << start_time << "</StartDateTime>" << std::endl; << "\t<StartDateTime>" << start_time << "</StartDateTime>" << std::endl;
if ( res == cmsysProcess_State_Exited && retVal ) if ( res == cmsysProcess_State_Exited && retVal )
{ {
@ -921,8 +936,8 @@ int cmCTest::ConfigureDirectory()
std::string end_time = ::CurrentTime(); std::string end_time = ::CurrentTime();
os << "\t<ConfigureStatus>" << retVal << "</ConfigureStatus>\n" os << "\t<ConfigureStatus>" << retVal << "</ConfigureStatus>\n"
<< "\t<EndDateTime>" << end_time << "</EndDateTime>\n" << "\t<EndDateTime>" << end_time << "</EndDateTime>\n"
<< "</Configure>\n" << "</Configure>" << std::endl;
<< "</Site>" << std::endl; this->EndXML(os);
} }
} }
else else
@ -999,7 +1014,7 @@ int cmCTest::BuildDirectory()
for ( cc = 0; cmCTestErrorMatches[cc]; cc ++ ) for ( cc = 0; cmCTestErrorMatches[cc]; cc ++ )
{ {
cmsys::RegularExpression re(cmCTestErrorMatches[cc]); cmsys::RegularExpression re(cmCTestErrorMatches[cc]);
std::vector<std::string>::size_type kk; cmCTest::tm_VectorOfStrings::size_type kk;
for ( kk = 0; kk < lines.size(); kk ++ ) for ( kk = 0; kk < lines.size(); kk ++ )
{ {
if ( re.find(lines[kk]) ) if ( re.find(lines[kk]) )
@ -1012,7 +1027,7 @@ int cmCTest::BuildDirectory()
for ( cc = 0; cmCTestWarningMatches[cc]; cc ++ ) for ( cc = 0; cmCTestWarningMatches[cc]; cc ++ )
{ {
cmsys::RegularExpression re(cmCTestWarningMatches[cc]); cmsys::RegularExpression re(cmCTestWarningMatches[cc]);
std::vector<std::string>::size_type kk; cmCTest::tm_VectorOfStrings::size_type kk;
for ( kk = 0; kk < lines.size(); kk ++ ) for ( kk = 0; kk < lines.size(); kk ++ )
{ {
if ( re.find(lines[kk]) ) if ( re.find(lines[kk]) )
@ -1128,9 +1143,9 @@ int cmCTest::BuildDirectory()
int cmCTest::CoverageDirectory() int cmCTest::CoverageDirectory()
{ {
std::cout << "Performing coverage" << std::endl; std::cout << "Performing coverage" << std::endl;
std::vector<std::string> files; cmCTest::tm_VectorOfStrings files;
std::vector<std::string> cfiles; cmCTest::tm_VectorOfStrings cfiles;
std::vector<std::string> cdirs; cmCTest::tm_VectorOfStrings cdirs;
bool done = false; bool done = false;
std::string::size_type cc; std::string::size_type cc;
std::string glob; std::string glob;
@ -1279,7 +1294,7 @@ int cmCTest::CoverageDirectory()
std::cout << "Cannot found any coverage files" << std::endl; std::cout << "Cannot found any coverage files" << std::endl;
return 1; return 1;
} }
std::map<std::string, std::vector<std::string> > sourcefiles; std::map<std::string, cmCTest::tm_VectorOfStrings > sourcefiles;
for ( cc = 0; cc < cfiles.size(); cc ++ ) for ( cc = 0; cc < cfiles.size(); cc ++ )
{ {
std::string& fname = cfiles[cc]; std::string& fname = cfiles[cc];
@ -1302,7 +1317,7 @@ int cmCTest::CoverageDirectory()
if ( allsourcefiles.find(nf) != allsourcefiles.end() || if ( allsourcefiles.find(nf) != allsourcefiles.end() ||
allbinaryfiles.find(nf) != allbinaryfiles.end() ) allbinaryfiles.find(nf) != allbinaryfiles.end() )
{ {
std::vector<std::string> &cvec = sourcefiles[nf]; cmCTest::tm_VectorOfStrings &cvec = sourcefiles[nf];
cvec.push_back(fname); cvec.push_back(fname);
} }
} }
@ -1313,15 +1328,11 @@ int cmCTest::CoverageDirectory()
// std::cout << "File: " << files[cc] << std::endl; // std::cout << "File: " << files[cc] << std::endl;
// } // }
std::map<std::string, std::vector<std::string> >::iterator it; std::map<std::string, cmCTest::tm_VectorOfStrings >::iterator it;
cmCTest::tm_CoverageMap coverageresults; cmCTest::tm_CoverageMap coverageresults;
log << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" this->StartXML(log);
<< "<Site BuildName=\"" << m_DartConfiguration["BuildName"] log << "<Coverage>\n"
<< "\" BuildStamp=\"" << m_CurrentTag << "-"
<< this->GetTestModelString() << "\" Name=\""
<< m_DartConfiguration["Site"] << "\">\n"
<< "<Coverage>\n"
<< "\t<StartDateTime>" << start_time << "</StartDateTime>" << std::endl; << "\t<StartDateTime>" << start_time << "</StartDateTime>" << std::endl;
int total_tested = 0; int total_tested = 0;
@ -1329,8 +1340,9 @@ int cmCTest::CoverageDirectory()
for ( it = sourcefiles.begin(); it != sourcefiles.end(); it ++ ) for ( it = sourcefiles.begin(); it != sourcefiles.end(); it ++ )
{ {
// std::cerr << "Source file: " << it->first << std::endl; //std::cerr << "Source file: " << it->first << std::endl;
std::vector<std::string> &gfiles = it->second; cmCTest::tm_VectorOfStrings &gfiles = it->second;
for ( cc = 0; cc < gfiles.size(); cc ++ ) for ( cc = 0; cc < gfiles.size(); cc ++ )
{ {
//std::cout << "\t" << gfiles[cc] << std::endl; //std::cout << "\t" << gfiles[cc] << std::endl;
@ -1435,8 +1447,8 @@ int cmCTest::CoverageDirectory()
{ {
local_end_time = ::CurrentTime(); local_end_time = ::CurrentTime();
cfileoutput << "\t<EndDateTime>" << local_end_time << "</EndDateTime>\n" cfileoutput << "\t<EndDateTime>" << local_end_time << "</EndDateTime>\n"
<< "</CoverageLog>\n" << "</CoverageLog>" << std::endl;
<< "</Site>" << std::endl; this->EndXML(cfileoutput);
cfileoutput.close(); cfileoutput.close();
std::cout << "Close file: " << cfileoutputname << std::endl; std::cout << "Close file: " << cfileoutputname << std::endl;
ccount = 0; ccount = 0;
@ -1451,12 +1463,8 @@ int cmCTest::CoverageDirectory()
return 1; return 1;
} }
local_start_time = ::CurrentTime(); local_start_time = ::CurrentTime();
cfileoutput << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" this->StartXML(cfileoutput);
<< "<Site BuildName=\"" << m_DartConfiguration["BuildName"] cfileoutput << "<CoverageLog>\n"
<< "\" BuildStamp=\"" << m_CurrentTag << "-"
<< this->GetTestModelString() << "\" Site=\""
<< m_DartConfiguration["Site"] << "\">\n"
<< "<CoverageLog>\n"
<< "\t<StartDateTime>" << local_start_time << "</StartDateTime>" << std::endl; << "\t<StartDateTime>" << local_start_time << "</StartDateTime>" << std::endl;
} }
@ -1524,8 +1532,8 @@ int cmCTest::CoverageDirectory()
{ {
local_end_time = ::CurrentTime(); local_end_time = ::CurrentTime();
cfileoutput << "\t<EndDateTime>" << local_end_time << "</EndDateTime>\n" cfileoutput << "\t<EndDateTime>" << local_end_time << "</EndDateTime>\n"
<< "</CoverageLog>\n" << "</CoverageLog>" << std::endl;
<< "</Site>" << std::endl; this->EndXML(cfileoutput);
cfileoutput.close(); cfileoutput.close();
} }
@ -1547,8 +1555,8 @@ int cmCTest::CoverageDirectory()
log.precision(2); log.precision(2);
log << (percent_coverage)<< "</PercentCoverage>\n" log << (percent_coverage)<< "</PercentCoverage>\n"
<< "\t<EndDateTime>" << end_time << "</EndDateTime>\n" << "\t<EndDateTime>" << end_time << "</EndDateTime>\n"
<< "</Coverage>\n" << "</Coverage>" << std::endl;
<< "</Site>" << std::endl; this->EndXML(log);
std::cout << "\tCovered LOC: " << total_tested << std::endl std::cout << "\tCovered LOC: " << total_tested << std::endl
<< "\tNot covered LOC: " << total_untested << std::endl << "\tNot covered LOC: " << total_untested << std::endl
@ -1603,12 +1611,8 @@ bool cmCTest::OpenOutputFile(const std::string& path,
void cmCTest::GenerateDartBuildOutput(std::ostream& os, void cmCTest::GenerateDartBuildOutput(std::ostream& os,
std::vector<cmCTestBuildErrorWarning> ew) std::vector<cmCTestBuildErrorWarning> ew)
{ {
os << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" this->StartXML(os);
<< "<Site BuildName=\"" << m_DartConfiguration["BuildName"] os << "<Build>\n"
<< "\" BuildStamp=\"" << m_CurrentTag << "-"
<< this->GetTestModelString() << "\" Name=\""
<< m_DartConfiguration["Site"] << "\">\n"
<< "<Build>\n"
<< "\t<StartDateTime>" << m_StartBuild << "</StartDateTime>\n" << "\t<StartDateTime>" << m_StartBuild << "</StartDateTime>\n"
<< "<BuildCommand>" << "<BuildCommand>"
<< this->MakeXMLSafe(m_DartConfiguration["MakeCommand"]) << this->MakeXMLSafe(m_DartConfiguration["MakeCommand"])
@ -1647,12 +1651,13 @@ void cmCTest::GenerateDartBuildOutput(std::ostream& os,
} }
os << "\t<Log Encoding=\"base64\" Compression=\"/bin/gzip\">\n\t</Log>\n" os << "\t<Log Encoding=\"base64\" Compression=\"/bin/gzip\">\n\t</Log>\n"
<< "\t<EndDateTime>" << m_EndBuild << "</EndDateTime>\n" << "\t<EndDateTime>" << m_EndBuild << "</EndDateTime>\n"
<< "</Build>\n" << "</Build>" << std::endl;
<< "</Site>" << std::endl; this->EndXML(os);
} }
void cmCTest::ProcessDirectory(std::vector<std::string> &passed, void cmCTest::ProcessDirectory(cmCTest::tm_VectorOfStrings &passed,
std::vector<std::string> &failed) cmCTest::tm_VectorOfStrings &failed,
bool memcheck)
{ {
// does the DartTestfile.txt exist ? // does the DartTestfile.txt exist ?
if(!cmSystemTools::FileExists("DartTestfile.txt")) if(!cmSystemTools::FileExists("DartTestfile.txt"))
@ -1692,7 +1697,7 @@ void cmCTest::ProcessDirectory(std::vector<std::string> &passed,
if (cmSystemTools::FileIsDirectory(nwd.c_str())) if (cmSystemTools::FileIsDirectory(nwd.c_str()))
{ {
cmSystemTools::ChangeDirectory(nwd.c_str()); cmSystemTools::ChangeDirectory(nwd.c_str());
this->ProcessDirectory(passed, failed); this->ProcessDirectory(passed, failed, memcheck);
} }
} }
// return to the original directory // return to the original directory
@ -1724,7 +1729,10 @@ void cmCTest::ProcessDirectory(std::vector<std::string> &passed,
if (firstTest) if (firstTest)
{ {
std::string nwd = cmSystemTools::GetCurrentWorkingDirectory(); std::string nwd = cmSystemTools::GetCurrentWorkingDirectory();
std::cerr << "Changing directory into " << nwd.c_str() << "\n"; if ( m_Verbose )
{
std::cerr << "Changing directory into " << nwd.c_str() << "\n";
}
firstTest = 0; firstTest = 0;
} }
cres.m_Name = args[0].Value; cres.m_Name = args[0].Value;
@ -1756,6 +1764,15 @@ void cmCTest::ProcessDirectory(std::vector<std::string> &passed,
++j; ++j;
++j; ++j;
std::vector<const char*> arguments; std::vector<const char*> arguments;
if ( memcheck )
{
cmCTest::tm_VectorOfStrings::size_type pp;
arguments.push_back(m_MemoryTester.c_str());
for ( pp = 0; pp < m_MemoryTesterOptionsParsed.size(); pp ++ )
{
arguments.push_back(m_MemoryTesterOptionsParsed[pp].c_str());
}
}
arguments.push_back(actualCommand.c_str()); arguments.push_back(actualCommand.c_str());
for(;j != args.end(); ++j) for(;j != args.end(); ++j)
{ {
@ -1867,15 +1884,97 @@ void cmCTest::ProcessDirectory(std::vector<std::string> &passed,
} }
} }
int cmCTest::TestDirectory() bool cmCTest::InitializeMemoryChecking()
{ {
std::cout << "Test project" << std::endl; if ( cmSystemTools::FileExists(m_DartConfiguration["MemoryCheckCommand"].c_str()) )
std::vector<std::string> passed; {
std::vector<std::string> failed; m_MemoryTester
= cmSystemTools::ConvertToOutputPath(m_DartConfiguration["MemoryCheckCommand"].c_str());
}
else if ( cmSystemTools::FileExists(m_DartConfiguration["PurifyCommand"].c_str()) )
{
m_MemoryTester
= cmSystemTools::ConvertToOutputPath(m_DartConfiguration["PurifyCommand"].c_str());
}
else if ( cmSystemTools::FileExists(m_DartConfiguration["ValgrindCommand"].c_str()) )
{
m_MemoryTester
= cmSystemTools::ConvertToOutputPath(m_DartConfiguration["ValgrindCommand"].c_str());
}
else
{
std::cout << "Memory checker (MemoryCheckCommand) not set, or cannot find the specified program."
<< std::endl;
return false;
}
if ( m_DartConfiguration["MemoryCheckCommandOptions"].size() )
{
m_MemoryTesterOptions = m_DartConfiguration["MemoryCheckCommandOptions"];
}
else if ( m_DartConfiguration["ValgrindCommandOptions"].size() )
{
m_MemoryTesterOptions = m_DartConfiguration["ValgrindCommandOptions"];
}
m_MemoryTesterOutputFile = m_ToplevelPath + "/Testing/Temporary/MemoryChecker.log";
m_MemoryTesterOutputFile = cmSystemTools::EscapeSpaces(m_MemoryTesterOutputFile.c_str());
if ( m_MemoryTester.find("valgrind") )
{
m_MemoryTesterStyle = cmCTest::VALGRIND;
if ( !m_MemoryTesterOptions.size() )
{
m_MemoryTesterOptions = "-q --skin=memcheck --leak-check=yes --show-reachable=yes --workaround-gcc296-bugs=yes --num-callers=100";
}
}
else if ( m_MemoryTester.find("purify") )
{
m_MemoryTesterStyle = cmCTest::PURIFY;
#ifdef _WIN32
m_MemoryTesterOptions += " /SAVETEXTDATA=" + m_MemoryTesterOutputFile;
#else
m_MemoryTesterOptions += " -log-file=" + m_MemoryTesterOutputFile;
#endif
}
else if ( m_MemoryTester.find("boundschecker") )
{
m_MemoryTesterStyle = cmCTest::BOUNDS_CHECKER;
std::cout << "Bounds checker not yet implemented" << std::endl;
return false;
}
else
{
std::cout << "Do not understand memory checker: " << m_MemoryTester.c_str() << std::endl;
return false;
}
m_MemoryTesterOptionsParsed = cmSystemTools::ParseArguments(m_MemoryTesterOptions.c_str());
cmCTest::tm_VectorOfStrings::size_type cc;
for ( cc = 0; cmCTestMemCheckResultStrings[cc]; cc ++ )
{
m_MemoryTesterGlobalResults[cc] = 0;
}
return true;
}
int cmCTest::TestDirectory(bool memcheck)
{
std::cout << (memcheck ? "Memory check" : "Test") << " project" << std::endl;
if ( memcheck )
{
if ( !this->InitializeMemoryChecking() )
{
return 1;
}
}
cmCTest::tm_VectorOfStrings passed;
cmCTest::tm_VectorOfStrings failed;
int total; int total;
m_StartTest = ::CurrentTime(); m_StartTest = ::CurrentTime();
this->ProcessDirectory(passed, failed); this->ProcessDirectory(passed, failed, memcheck);
m_EndTest = ::CurrentTime(); m_EndTest = ::CurrentTime();
total = int(passed.size()) + int(failed.size()); total = int(passed.size()) + int(failed.size());
@ -1892,7 +1991,7 @@ int cmCTest::TestDirectory()
if (passed.size() && (m_UseIncludeRegExp || m_UseExcludeRegExp)) if (passed.size() && (m_UseIncludeRegExp || m_UseExcludeRegExp))
{ {
std::cerr << "\nThe following tests passed:\n"; std::cerr << "\nThe following tests passed:\n";
for(std::vector<std::string>::iterator j = passed.begin(); for(cmCTest::tm_VectorOfStrings::iterator j = passed.begin();
j != passed.end(); ++j) j != passed.end(); ++j)
{ {
std::cerr << "\t" << *j << "\n"; std::cerr << "\t" << *j << "\n";
@ -1906,7 +2005,7 @@ int cmCTest::TestDirectory()
if (failed.size()) if (failed.size())
{ {
std::cerr << "\nThe following tests FAILED:\n"; std::cerr << "\nThe following tests FAILED:\n";
for(std::vector<std::string>::iterator j = failed.begin(); for(cmCTest::tm_VectorOfStrings::iterator j = failed.begin();
j != failed.end(); ++j) j != failed.end(); ++j)
{ {
std::cerr << "\t" << *j << "\n"; std::cerr << "\t" << *j << "\n";
@ -1917,12 +2016,21 @@ int cmCTest::TestDirectory()
if ( m_DartMode ) if ( m_DartMode )
{ {
std::ofstream ofs; std::ofstream ofs;
if( !this->OpenOutputFile(m_CurrentTag, "Test.xml", ofs) ) if( !this->OpenOutputFile(m_CurrentTag,
(memcheck ? (m_CompatibilityMode?"Purify.xml":"MemCheck.xml") : "Test.xml"), ofs) )
{ {
std::cerr << "Cannot create testing XML file" << std::endl; std::cerr << "Cannot create " << (memcheck ? "memory check" : "testing")
<< " XML file" << std::endl;
return 1; return 1;
} }
this->GenerateDartTestOutput(ofs); if ( memcheck )
{
this->GenerateDartMemCheckOutput(ofs);
}
else
{
this->GenerateDartTestOutput(ofs);
}
} }
return int(failed.size()); return int(failed.size());
@ -1930,8 +2038,7 @@ int cmCTest::TestDirectory()
int cmCTest::SubmitResults() int cmCTest::SubmitResults()
{ {
#ifdef HAVE_CURL cmCTest::tm_VectorOfStrings files;
std::vector<std::string> files;
std::string prefix = this->GetSubmitResultsPrefix(); std::string prefix = this->GetSubmitResultsPrefix();
// TODO: // TODO:
// Check if test is enabled // Check if test is enabled
@ -1954,7 +2061,7 @@ int cmCTest::SubmitResults()
if ( this->CTestFileExists("Coverage.xml") ) if ( this->CTestFileExists("Coverage.xml") )
{ {
files.push_back("Coverage.xml"); files.push_back("Coverage.xml");
std::vector<std::string> gfiles; cmCTest::tm_VectorOfStrings gfiles;
std::string gpath = m_ToplevelPath + "/Testing/" + m_CurrentTag; std::string gpath = m_ToplevelPath + "/Testing/" + m_CurrentTag;
std::string::size_type glen = gpath.size() + 1; std::string::size_type glen = gpath.size() + 1;
gpath = gpath + "/CoverageLog*"; gpath = gpath + "/CoverageLog*";
@ -1974,6 +2081,10 @@ int cmCTest::SubmitResults()
std::cout << "Problem globbing" << std::endl; std::cout << "Problem globbing" << std::endl;
} }
} }
if ( this->CTestFileExists("MemCheck.xml") )
{
files.push_back("MemCheck.xml");
}
if ( this->CTestFileExists("Purify.xml") ) if ( this->CTestFileExists("Purify.xml") )
{ {
files.push_back("Purify.xml"); files.push_back("Purify.xml");
@ -2035,7 +2146,6 @@ int cmCTest::SubmitResults()
std::cout << "SCP submit not yet implemented" << std::endl; std::cout << "SCP submit not yet implemented" << std::endl;
} }
#endif
return 0; return 0;
} }
@ -2055,6 +2165,96 @@ std::string cmCTest::GetSubmitResultsPrefix()
return name; return name;
} }
void cmCTest::GenerateDartMemCheckOutput(std::ostream& os)
{
if ( !m_DartMode )
{
return;
}
this->StartXML(os);
if ( m_CompatibilityMode )
{
os << "<Purify>" << std::endl;
}
else
{
os << "<MemCheck>" << std::endl;
}
os << "\t<StartDateTime>" << m_StartTest << "</StartDateTime>\n"
<< "\t<TestList>\n";
tm_TestResultsVector::size_type cc;
for ( cc = 0; cc < m_TestResults.size(); cc ++ )
{
cmCTestTestResult *result = &m_TestResults[cc];
os << "\t\t<Test>" << this->MakeXMLSafe(result->m_Path)
<< "/" << this->MakeXMLSafe(result->m_Name)
<< "</Test>" << std::endl;
}
os << "\t</TestList>\n";
for ( cc = 0; cc < m_TestResults.size(); cc ++ )
{
cmCTestTestResult *result = &m_TestResults[cc];
std::string memcheckstr;
int memcheckresults[cmCTest::NO_MEMORY_FAULT];
int kk;
this->ProcessMemCheckOutput(result->m_Output, memcheckstr, memcheckresults);
os << "\t<Test Status=\"";
if ( result->m_Status == cmCTest::COMPLETED )
{
os << "passed";
}
else if ( result->m_Status == cmCTest::NOT_RUN )
{
os << "notrun";
}
else
{
os << "failed";
}
os << "\">\n"
<< "\t\t<Name>" << this->MakeXMLSafe(result->m_Name) << "</Name>\n"
<< "\t\t<Path>" << this->MakeXMLSafe(result->m_Path) << "</Path>\n"
<< "\t\t<FullName>" << this->MakeXMLSafe(result->m_Path)
<< "/" << this->MakeXMLSafe(result->m_Name) << "</FullName>\n"
<< "\t\t<FullCommandLine>"
<< this->MakeXMLSafe(result->m_FullCommandLine)
<< "</FullCommandLine>\n"
<< "\t\t<Results>" << std::endl;
for ( kk = 0; cmCTestMemCheckResultStrings[kk]; kk ++ )
{
os << "\t\t\t<" << cmCTestMemCheckResultStrings[kk] << ">"
<< memcheckresults[kk]
<< "</" << cmCTestMemCheckResultStrings[kk] << ">" << std::endl;
m_MemoryTesterGlobalResults[kk] += memcheckresults[kk];
}
os
<< "\t\t</Results>\n"
<< "\t<Log>\n" << cmCTest::MakeXMLSafe(memcheckstr) << std::endl
<< "\t</Log>\n"
<< "\t</Test>" << std::endl;
}
os << "\t<EndDateTime>" << m_EndTest << "</EndDateTime>" << std::endl;
if ( m_CompatibilityMode )
{
os << "</Purify>" << std::endl;
}
else
{
os << "</MemCheck>" << std::endl;
}
this->EndXML(os);
std::cerr << "Memory checking results:" << std::endl;
for ( cc = 0; cmCTestMemCheckResultStrings[cc]; cc ++ )
{
std::cerr << "\t\t" << cmCTestMemCheckResultStrings[cc] << " - "
<< m_MemoryTesterGlobalResults[cc] << std::endl;
}
}
void cmCTest::GenerateDartTestOutput(std::ostream& os) void cmCTest::GenerateDartTestOutput(std::ostream& os)
{ {
if ( !m_DartMode ) if ( !m_DartMode )
@ -2062,12 +2262,8 @@ void cmCTest::GenerateDartTestOutput(std::ostream& os)
return; return;
} }
os << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" this->StartXML(os);
<< "<Site BuildName=\"" << m_DartConfiguration["BuildName"] os << "<Testing>\n"
<< "\" BuildStamp=\"" << m_CurrentTag << "-"
<< this->GetTestModelString() << "\" Name=\""
<< m_DartConfiguration["Site"] << "\">\n"
<< "<Testing>\n"
<< "\t<StartDateTime>" << m_StartTest << "</StartDateTime>\n" << "\t<StartDateTime>" << m_StartTest << "</StartDateTime>\n"
<< "\t<TestList>\n"; << "\t<TestList>\n";
tm_TestResultsVector::size_type cc; tm_TestResultsVector::size_type cc;
@ -2132,8 +2328,8 @@ void cmCTest::GenerateDartTestOutput(std::ostream& os)
} }
os << "\t<EndDateTime>" << m_EndTest << "</EndDateTime>\n" os << "\t<EndDateTime>" << m_EndTest << "</EndDateTime>\n"
<< "</Testing>\n" << "</Testing>" << std::endl;
<< "</Site>" << std::endl; this->EndXML(os);
} }
int cmCTest::ProcessTests() int cmCTest::ProcessTests()
@ -2173,23 +2369,19 @@ int cmCTest::ProcessTests()
} }
if ( m_Tests[TEST_TEST] || m_Tests[ALL_TEST] || notest ) if ( m_Tests[TEST_TEST] || m_Tests[ALL_TEST] || notest )
{ {
res += this->TestDirectory(); res += this->TestDirectory(false);
} }
if ( m_Tests[COVERAGE_TEST] || m_Tests[ALL_TEST] ) if ( m_Tests[COVERAGE_TEST] || m_Tests[ALL_TEST] )
{ {
this->CoverageDirectory(); this->CoverageDirectory();
} }
if ( m_Tests[PURIFY_TEST] || m_Tests[ALL_TEST] ) if ( m_Tests[MEMCHECK_TEST] || m_Tests[ALL_TEST] )
{ {
std::cerr << "Purify test is not yet implemented" << std::endl; res += this->TestDirectory(true);
} }
if ( m_Tests[SUBMIT_TEST] || m_Tests[ALL_TEST] ) if ( m_Tests[SUBMIT_TEST] || m_Tests[ALL_TEST] )
{ {
#ifdef HAVE_CURL
this->SubmitResults(); this->SubmitResults();
#else
std::cerr << "Submit test is not yet implemented" << std::endl;
#endif
} }
return res; return res;
} }
@ -2763,3 +2955,100 @@ int cmCTest::RunConfigurationScript()
return 0; return 0;
} }
void cmCTest::StartXML(ostream& ostr)
{
ostr << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n"
<< "<Site BuildName=\"" << m_DartConfiguration["BuildName"]
<< "\" BuildStamp=\"" << m_CurrentTag << "-"
<< this->GetTestModelString() << "\" Name=\""
<< m_DartConfiguration["Site"] << "\">" << std::endl;
}
void cmCTest::EndXML(ostream& ostr)
{
ostr << "</Site>" << std::endl;
}
bool cmCTest::ProcessMemCheckValgrindOutput(const std::string& str, std::string& log, int* results)
{
std::vector<cmStdString> lines;
cmSystemTools::Split(str.c_str(), lines);
std::string::size_type cc;
cmOStringStream ostr;
log = "";
cmsys::RegularExpression valgrindLine("^==[0-9][0-9]*==");
cmsys::RegularExpression vgFIM("== .*Invalid free\\(\\) / delete / delete\\[\\]");
cmsys::RegularExpression vgFMM("== .*Mismatched free\\(\\) / delete / delete \\[\\]");
cmsys::RegularExpression vgMLK("== .*[0-9][0-9]* bytes in [0-9][0-9]* blocks are definitely lost in loss record [0-9][0-9]* of [0-9]");
cmsys::RegularExpression vgPAR("== .*Syscall param .* contains unaddressable byte\\(s\\)");
cmsys::RegularExpression vgMPK1("== .*[0-9][0-9]* bytes in [0-9][0-9]* blocks are possibly lost in loss record [0-9][0-9]* of [0-9]");
cmsys::RegularExpression vgMPK2("== .*[0-9][0-9]* bytes in [0-9][0-9]* blocks are still reachable in loss record [0-9][0-9]* of [0-9]");
cmsys::RegularExpression vgUMC("== .*Conditional jump or move depends on uninitialised value\\(s\\)");
cmsys::RegularExpression vgUMR1("== .*Use of uninitialised value of size [0-9][0-9]*");
cmsys::RegularExpression vgUMR2("== .*Invalid read of size [0-9][0-9]*");
cmsys::RegularExpression vgUMR3("== .*Jump to the invalid address ");
cmsys::RegularExpression vgUMR4("== .*Syscall param .* contains uninitialised or unaddressable byte\\(s\\)");
cmsys::RegularExpression vgIPW("== .*Invalid write of size [0-9]");
for ( cc = 0; cc < lines.size(); cc ++ )
{
if ( valgrindLine.find(lines[cc]) )
{
if ( vgFIM.find(lines[cc]) ) { results[cmCTest::FIM] ++; ostr << "FIM"; }
else if ( vgFMM.find(lines[cc]) ) { results[cmCTest::FMM] ++; ostr << "FMM"; }
else if ( vgMLK.find(lines[cc]) ) { results[cmCTest::MLK] ++; ostr << "MLK"; }
else if ( vgPAR.find(lines[cc]) ) { results[cmCTest::PAR] ++; ostr << "PAR"; }
else if ( vgMPK1.find(lines[cc]) ) { results[cmCTest::MPK] ++; ostr << "MPK"; }
else if ( vgMPK2.find(lines[cc]) ) { results[cmCTest::MPK] ++; ostr << "MPK"; }
else if ( vgUMC.find(lines[cc]) ) { results[cmCTest::UMC] ++; ostr << "UMC"; }
else if ( vgUMR1.find(lines[cc]) ) { results[cmCTest::UMR] ++; ostr << "UMR"; }
else if ( vgUMR2.find(lines[cc]) ) { results[cmCTest::UMR] ++; ostr << "UMR"; }
else if ( vgUMR3.find(lines[cc]) ) { results[cmCTest::UMR] ++; ostr << "UMR"; }
else if ( vgUMR4.find(lines[cc]) ) { results[cmCTest::UMR] ++; ostr << "UMR"; }
else if ( vgIPW.find(lines[cc]) ) { results[cmCTest::IPW] ++; ostr << "IPW"; }
ostr << lines[cc] << std::endl;
}
}
log = ostr.str();
return true;
}
bool cmCTest::ProcessMemCheckOutput(const std::string& str, std::string& log, int* results)
{
std::string::size_type cc;
for ( cc = 0; cc < cmCTest::NO_MEMORY_FAULT; cc ++ )
{
results[cc] = 0;
}
if ( m_MemoryTesterStyle == cmCTest::VALGRIND )
{
return ProcessMemCheckValgrindOutput(str, log, results);
}
else if ( m_MemoryTesterStyle == cmCTest::PURIFY )
{
log.append("\nMemory checking style used was: ");
log.append("Purify");
}
else if ( m_MemoryTesterStyle == cmCTest::BOUNDS_CHECKER )
{
log.append("\nMemory checking style used was: ");
log.append("Bounds Checker");
}
else
{
log.append("\nMemory checking style used was: ");
log.append("None that I know");
log = str;
}
return true;
}

View File

@ -24,6 +24,8 @@
class cmCTest class cmCTest
{ {
public: public:
typedef std::vector<cmStdString> tm_VectorOfStrings;
/** /**
* Run a dashboard using a specified confiuration script * Run a dashboard using a specified confiuration script
*/ */
@ -55,7 +57,7 @@ public:
/** /**
* Try to run tests of the project * Try to run tests of the project
*/ */
int TestDirectory(); int TestDirectory(bool memcheck);
/** /**
* Try to get coverage of the project * Try to get coverage of the project
@ -86,8 +88,9 @@ public:
/** /**
* Run the test for a directory and any subdirectories * Run the test for a directory and any subdirectories
*/ */
void ProcessDirectory(std::vector<std::string> &passed, void ProcessDirectory(tm_VectorOfStrings &passed,
std::vector<std::string> &failed); tm_VectorOfStrings &failed,
bool memcheck);
/** /**
* Find the executable for a test * Find the executable for a test
@ -143,7 +146,7 @@ private:
BUILD_TEST = 4, BUILD_TEST = 4,
TEST_TEST = 5, TEST_TEST = 5,
COVERAGE_TEST = 6, COVERAGE_TEST = 6,
PURIFY_TEST = 7, MEMCHECK_TEST = 7,
SUBMIT_TEST = 8, SUBMIT_TEST = 8,
ALL_TEST = 9, ALL_TEST = 9,
LAST_TEST = 10 LAST_TEST = 10
@ -162,6 +165,40 @@ private:
COMPLETED COMPLETED
}; };
enum { // Memory checkers
UNKNOWN = 0,
VALGRIND,
PURIFY,
BOUNDS_CHECKER
};
enum { // Memory faults
ABR = 0,
ABW,
ABWL,
COR,
EXU,
FFM,
FIM,
FMM,
FMR,
FMW,
FUM,
IPR,
IPW,
MAF,
MLK,
MPK,
NPR,
ODS,
PAR,
PLK,
UMC,
UMR,
NO_MEMORY_FAULT
};
struct cmCTestTestResult struct cmCTestTestResult
{ {
std::string m_Name; std::string m_Name;
@ -235,10 +272,20 @@ private:
int m_TimeOut; int m_TimeOut;
std::string m_MemoryTester;
std::string m_MemoryTesterOptions;
int m_MemoryTesterStyle;
std::string m_MemoryTesterOutputFile;
tm_VectorOfStrings m_MemoryTesterOptionsParsed;
int m_MemoryTesterGlobalResults[NO_MEMORY_FAULT];
int m_CompatibilityMode;
/** /**
* Generate the Dart compatible output * Generate the Dart compatible output
*/ */
void GenerateDartTestOutput(std::ostream& os); void GenerateDartTestOutput(std::ostream& os);
void GenerateDartMemCheckOutput(std::ostream& os);
void GenerateDartBuildOutput(std::ostream& os, void GenerateDartBuildOutput(std::ostream& os,
std::vector<cmCTestBuildErrorWarning>); std::vector<cmCTestBuildErrorWarning>);
@ -259,6 +306,20 @@ private:
std::string GenerateRegressionImages(const std::string& xml); std::string GenerateRegressionImages(const std::string& xml);
const char* GetTestStatus(int status); const char* GetTestStatus(int status);
//! Start CTest XML output file
void StartXML(ostream& ostr);
//! End CTest XML output file
void EndXML(ostream& ostr);
//! Parse Valgrind/Purify/Bounds Checker result out of the output string. After running,
// log holds the output and results hold the different memmory errors.
bool ProcessMemCheckOutput(const std::string& str, std::string& log, int* results);
bool ProcessMemCheckValgrindOutput(const std::string& str, std::string& log, int* results);
//! Initialize memory checking subsystem.
bool InitializeMemoryChecking();
}; };
#endif #endif

View File

@ -909,8 +909,8 @@ void cmSystemTools::ExpandListArgument(const std::string& arg,
} }
} }
bool cmSystemTools::SimpleGlob(const std::string& glob, bool cmSystemTools::SimpleGlob(const cmStdString& glob,
std::vector<std::string>& files, std::vector<cmStdString>& files,
int type /* = 0 */) int type /* = 0 */)
{ {
files.clear(); files.clear();

View File

@ -139,7 +139,7 @@ public:
* want to find. 0 means all files, -1 means directories, 1 means * want to find. 0 means all files, -1 means directories, 1 means
* files only. This method returns true if search was succesfull. * files only. This method returns true if search was succesfull.
*/ */
static bool SimpleGlob(const std::string& glob, std::vector<std::string>& files, static bool SimpleGlob(const cmStdString& glob, std::vector<cmStdString>& files,
int type = 0); int type = 0);
///! Copy a file. ///! Copy a file.

View File

@ -197,10 +197,10 @@ int main (int argc, char *argv[])
inst.SetTestModel(cmCTest::EXPERIMENTAL); inst.SetTestModel(cmCTest::EXPERIMENTAL);
inst.SetTest("Test"); inst.SetTest("Test");
} }
else if ( targ == "ExperimentalPurify" ) else if ( targ == "ExperimentalMemCheck" || targ == "ExperimentalPurify" )
{ {
inst.SetTestModel(cmCTest::EXPERIMENTAL); inst.SetTestModel(cmCTest::EXPERIMENTAL);
inst.SetTest("Purify"); inst.SetTest("MemCheck");
} }
else if ( targ == "ExperimentalCoverage" ) else if ( targ == "ExperimentalCoverage" )
{ {
@ -248,10 +248,10 @@ int main (int argc, char *argv[])
inst.SetTestModel(cmCTest::CONTINUOUS); inst.SetTestModel(cmCTest::CONTINUOUS);
inst.SetTest("Test"); inst.SetTest("Test");
} }
else if ( targ == "ContinuousPurify" ) else if ( targ == "ContinuousMemCheck" || targ == "ContinuousPurify" )
{ {
inst.SetTestModel(cmCTest::CONTINUOUS); inst.SetTestModel(cmCTest::CONTINUOUS);
inst.SetTest("Purify"); inst.SetTest("MemCheck");
} }
else if ( targ == "ContinuousCoverage" ) else if ( targ == "ContinuousCoverage" )
{ {
@ -299,10 +299,10 @@ int main (int argc, char *argv[])
inst.SetTestModel(cmCTest::NIGHTLY); inst.SetTestModel(cmCTest::NIGHTLY);
inst.SetTest("Test"); inst.SetTest("Test");
} }
else if ( targ == "NightlyPurify" ) else if ( targ == "NightlyMemCheck" || targ == "NightlyPurify" )
{ {
inst.SetTestModel(cmCTest::NIGHTLY); inst.SetTestModel(cmCTest::NIGHTLY);
inst.SetTest("Purify"); inst.SetTest("MemCheck");
} }
else if ( targ == "NightlyCoverage" ) else if ( targ == "NightlyCoverage" )
{ {
@ -320,7 +320,7 @@ int main (int argc, char *argv[])
inst.SetTest("Start"); inst.SetTest("Start");
inst.SetTest("Configure"); inst.SetTest("Configure");
inst.SetTest("Build"); inst.SetTest("Build");
inst.SetTest("Purify"); inst.SetTest("MemCheck");
inst.SetTest("Coverage"); inst.SetTest("Coverage");
inst.SetTest("Submit"); inst.SetTest("Submit");
} }
@ -331,7 +331,7 @@ int main (int argc, char *argv[])
inst.SetTest("Update"); inst.SetTest("Update");
inst.SetTest("Configure"); inst.SetTest("Configure");
inst.SetTest("Build"); inst.SetTest("Build");
inst.SetTest("Purify"); inst.SetTest("MemCheck");
inst.SetTest("Coverage"); inst.SetTest("Coverage");
inst.SetTest("Submit"); inst.SetTest("Submit");
} }