|
|
@@ -760,7 +760,9 @@ bool cmCTest::UpdateCTestConfiguration()
|
|
|
}
|
|
|
if (!this->GetCTestConfiguration("BuildDirectory").empty()) {
|
|
|
this->Impl->BinaryDir = this->GetCTestConfiguration("BuildDirectory");
|
|
|
- cmSystemTools::ChangeDirectory(this->Impl->BinaryDir);
|
|
|
+ if (this->Impl->TestDir.empty()) {
|
|
|
+ cmSystemTools::ChangeDirectory(this->Impl->BinaryDir);
|
|
|
+ }
|
|
|
}
|
|
|
this->Impl->TimeOut =
|
|
|
std::chrono::seconds(atoi(this->GetCTestConfiguration("TimeOut").c_str()));
|
|
|
@@ -1890,6 +1892,7 @@ bool cmCTest::HandleCommandLineArguments(size_t& i,
|
|
|
std::string& errormsg)
|
|
|
{
|
|
|
std::string arg = args[i];
|
|
|
+ cm::string_view noTestsPrefix = "--no-tests=";
|
|
|
if (this->CheckArgument(arg, "-F"_s)) {
|
|
|
this->Impl->Failover = true;
|
|
|
} else if (this->CheckArgument(arg, "-j"_s, "--parallel")) {
|
|
|
@@ -2151,8 +2154,7 @@ bool cmCTest::HandleCommandLineArguments(size_t& i,
|
|
|
this->SetOutputJUnitFileName(std::string(args[i]));
|
|
|
}
|
|
|
|
|
|
- cm::string_view noTestsPrefix = "--no-tests=";
|
|
|
- if (cmHasPrefix(arg, noTestsPrefix)) {
|
|
|
+ else if (cmHasPrefix(arg, noTestsPrefix)) {
|
|
|
cm::string_view noTestsMode =
|
|
|
cm::string_view(arg).substr(noTestsPrefix.length());
|
|
|
if (noTestsMode == "error") {
|
|
|
@@ -2260,6 +2262,8 @@ bool cmCTest::HandleCommandLineArguments(size_t& i,
|
|
|
else if (this->CheckArgument(arg, "--rerun-failed"_s)) {
|
|
|
this->GetTestHandler()->SetPersistentOption("RerunFailed", "true");
|
|
|
this->GetMemCheckHandler()->SetPersistentOption("RerunFailed", "true");
|
|
|
+ } else {
|
|
|
+ return false;
|
|
|
}
|
|
|
return true;
|
|
|
}
|
|
|
@@ -2309,7 +2313,7 @@ bool cmCTest::ColoredOutputSupportedByConsole()
|
|
|
}
|
|
|
|
|
|
// handle the -S -SR and -SP arguments
|
|
|
-void cmCTest::HandleScriptArguments(size_t& i, std::vector<std::string>& args,
|
|
|
+bool cmCTest::HandleScriptArguments(size_t& i, std::vector<std::string>& args,
|
|
|
bool& SRArgumentSpecified)
|
|
|
{
|
|
|
std::string arg = args[i];
|
|
|
@@ -2324,8 +2328,8 @@ void cmCTest::HandleScriptArguments(size_t& i, std::vector<std::string>& args,
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- if (this->CheckArgument(arg, "-SR"_s, "--script-run") &&
|
|
|
- i < args.size() - 1) {
|
|
|
+ else if (this->CheckArgument(arg, "-SR"_s, "--script-run") &&
|
|
|
+ i < args.size() - 1) {
|
|
|
SRArgumentSpecified = true;
|
|
|
this->Impl->RunConfigurationScript = true;
|
|
|
i++;
|
|
|
@@ -2333,7 +2337,8 @@ void cmCTest::HandleScriptArguments(size_t& i, std::vector<std::string>& args,
|
|
|
ch->AddConfigurationScript(args[i], true);
|
|
|
}
|
|
|
|
|
|
- if (this->CheckArgument(arg, "-S"_s, "--script") && i < args.size() - 1) {
|
|
|
+ else if (this->CheckArgument(arg, "-S"_s, "--script") &&
|
|
|
+ i < args.size() - 1) {
|
|
|
this->Impl->RunConfigurationScript = true;
|
|
|
i++;
|
|
|
cmCTestScriptHandler* ch = this->GetScriptHandler();
|
|
|
@@ -2341,7 +2346,10 @@ void cmCTest::HandleScriptArguments(size_t& i, std::vector<std::string>& args,
|
|
|
if (!SRArgumentSpecified) {
|
|
|
ch->AddConfigurationScript(args[i], true);
|
|
|
}
|
|
|
+ } else {
|
|
|
+ return false;
|
|
|
}
|
|
|
+ return true;
|
|
|
}
|
|
|
|
|
|
bool cmCTest::AddVariableDefinition(const std::string& arg)
|
|
|
@@ -2734,16 +2742,18 @@ int cmCTest::Run(std::vector<std::string>& args, std::string* output)
|
|
|
for (size_t i = 1; i < args.size(); ++i) {
|
|
|
// handle the simple commandline arguments
|
|
|
std::string errormsg;
|
|
|
- if (!this->HandleCommandLineArguments(i, args, errormsg)) {
|
|
|
+ bool validArg = this->HandleCommandLineArguments(i, args, errormsg);
|
|
|
+ if (!validArg && !errormsg.empty()) {
|
|
|
cmSystemTools::Error(errormsg);
|
|
|
return 1;
|
|
|
}
|
|
|
+ std::string arg = args[i];
|
|
|
|
|
|
// handle the script arguments -S -SR -SP
|
|
|
- this->HandleScriptArguments(i, args, SRArgumentSpecified);
|
|
|
+ validArg =
|
|
|
+ validArg || this->HandleScriptArguments(i, args, SRArgumentSpecified);
|
|
|
|
|
|
// --dashboard: handle a request for a dashboard
|
|
|
- std::string arg = args[i];
|
|
|
if (this->CheckArgument(arg, "-D"_s, "--dashboard") &&
|
|
|
i < args.size() - 1) {
|
|
|
this->Impl->ProduceXML = true;
|
|
|
@@ -2757,6 +2767,7 @@ int cmCTest::Run(std::vector<std::string>& args, std::string* output)
|
|
|
executeTests = false;
|
|
|
}
|
|
|
}
|
|
|
+ validArg = true;
|
|
|
}
|
|
|
|
|
|
// If it's not exactly -D, but it starts with -D, then try to parse out
|
|
|
@@ -2767,16 +2778,17 @@ int cmCTest::Run(std::vector<std::string>& args, std::string* output)
|
|
|
if (arg != "-D" && cmHasLiteralPrefix(arg, "-D")) {
|
|
|
std::string input = arg.substr(2);
|
|
|
this->AddVariableDefinition(input);
|
|
|
+ validArg = true;
|
|
|
}
|
|
|
|
|
|
// --test-action: calls SetTest(<stage>, /*report=*/ false) to enable
|
|
|
// the corresponding stage
|
|
|
- if (!this->HandleTestActionArgument(ctestExec, i, args)) {
|
|
|
+ if (!this->HandleTestActionArgument(ctestExec, i, args, validArg)) {
|
|
|
executeTests = false;
|
|
|
}
|
|
|
|
|
|
// --test-model: what type of test model
|
|
|
- if (!this->HandleTestModelArgument(ctestExec, i, args)) {
|
|
|
+ if (!this->HandleTestModelArgument(ctestExec, i, args, validArg)) {
|
|
|
executeTests = false;
|
|
|
}
|
|
|
|
|
|
@@ -2788,30 +2800,39 @@ int cmCTest::Run(std::vector<std::string>& args, std::string* output)
|
|
|
if (!this->SubmitExtraFiles(args[i])) {
|
|
|
return 0;
|
|
|
}
|
|
|
+ validArg = true;
|
|
|
}
|
|
|
|
|
|
// --build-and-test options
|
|
|
if (this->CheckArgument(arg, "--build-and-test"_s) &&
|
|
|
i < args.size() - 1) {
|
|
|
cmakeAndTest = true;
|
|
|
+ validArg = true;
|
|
|
}
|
|
|
|
|
|
// --schedule-random
|
|
|
if (this->CheckArgument(arg, "--schedule-random"_s)) {
|
|
|
this->Impl->ScheduleType = "Random";
|
|
|
+ validArg = true;
|
|
|
}
|
|
|
|
|
|
// pass the argument to all the handlers as well, but it may no longer be
|
|
|
// set to what it was originally so I'm not sure this is working as
|
|
|
// intended
|
|
|
for (auto& handler : this->Impl->GetTestingHandlers()) {
|
|
|
- if (!handler->ProcessCommandLineArguments(arg, i, args)) {
|
|
|
+ if (!handler->ProcessCommandLineArguments(arg, i, args, validArg)) {
|
|
|
cmCTestLog(
|
|
|
this, ERROR_MESSAGE,
|
|
|
"Problem parsing command line arguments within a handler\n");
|
|
|
return 0;
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+ if (!validArg && cmHasLiteralPrefix(arg, "-") &&
|
|
|
+ !cmHasLiteralPrefix(arg, "--preset")) {
|
|
|
+ cmSystemTools::Error(cmStrCat("Invalid argument: ", arg));
|
|
|
+ return 1;
|
|
|
+ }
|
|
|
} // the close of the for argument loop
|
|
|
|
|
|
// handle CTEST_PARALLEL_LEVEL environment variable
|
|
|
@@ -2877,12 +2898,14 @@ int cmCTest::Run(std::vector<std::string>& args, std::string* output)
|
|
|
}
|
|
|
|
|
|
bool cmCTest::HandleTestActionArgument(const char* ctestExec, size_t& i,
|
|
|
- const std::vector<std::string>& args)
|
|
|
+ const std::vector<std::string>& args,
|
|
|
+ bool& validArg)
|
|
|
{
|
|
|
bool success = true;
|
|
|
std::string const& arg = args[i];
|
|
|
if (this->CheckArgument(arg, "-T"_s, "--test-action") &&
|
|
|
(i < args.size() - 1)) {
|
|
|
+ validArg = true;
|
|
|
this->Impl->ProduceXML = true;
|
|
|
i++;
|
|
|
if (!this->SetTest(args[i], false)) {
|
|
|
@@ -2909,12 +2932,14 @@ bool cmCTest::HandleTestActionArgument(const char* ctestExec, size_t& i,
|
|
|
}
|
|
|
|
|
|
bool cmCTest::HandleTestModelArgument(const char* ctestExec, size_t& i,
|
|
|
- const std::vector<std::string>& args)
|
|
|
+ const std::vector<std::string>& args,
|
|
|
+ bool& validArg)
|
|
|
{
|
|
|
bool success = true;
|
|
|
std::string const& arg = args[i];
|
|
|
if (this->CheckArgument(arg, "-M"_s, "--test-model") &&
|
|
|
(i < args.size() - 1)) {
|
|
|
+ validArg = true;
|
|
|
i++;
|
|
|
std::string const& str = args[i];
|
|
|
if (cmSystemTools::LowerCase(str) == "nightly"_s) {
|