Commit d3859624 authored by Betsy McPhail's avatar Betsy McPhail Committed by Brad King

Add directory property 'LABELS' and CMAKE_DIRECTORY_LABELS variable

The specified LABELS will be passed down to subdirectories as well as
any targets or tests in the directory.
parent d08ec4d2
This diff is collapsed.
......@@ -74,6 +74,7 @@ Properties on Directories
/prop_dir/INCLUDE_REGULAR_EXPRESSION
/prop_dir/INTERPROCEDURAL_OPTIMIZATION_CONFIG
/prop_dir/INTERPROCEDURAL_OPTIMIZATION
/prop_dir/LABELS
/prop_dir/LINK_DIRECTORIES
/prop_dir/LISTFILE_STACK
/prop_dir/MACROS
......
......@@ -32,6 +32,7 @@ Variables that Provide Information
/variable/CMAKE_CURRENT_LIST_FILE
/variable/CMAKE_CURRENT_LIST_LINE
/variable/CMAKE_CURRENT_SOURCE_DIR
/variable/CMAKE_DIRECTORY_LABELS
/variable/CMAKE_DL_LIBS
/variable/CMAKE_EDIT_COMMAND
/variable/CMAKE_EXECUTABLE_SUFFIX
......
LABELS
------
Specify a list of text labels associated with a directory and all of its
subdirectories. This is equivalent to setting the :prop_tgt:`LABELS` target
property and the :prop_test:`LABELS` test property on all targets and tests in
the current directory and subdirectories. Note: Launchers must enabled to
propagate labels to targets.
The :variable:`CMAKE_DIRECTORY_LABELS` variable can be used to initialize this
property.
The list is reported in dashboard submissions.
CMAKE_DIRECTORY_LABELS
-----------------------
Specify labels for the current directory.
This is used to initialize the :prop_dir:`LABELS` directory property.
......@@ -238,6 +238,36 @@ bool cmCTestSetTestsPropertiesCommand::InitialPass(
return this->TestHandler->SetTestsProperties(args);
}
class cmCTestSetDirectoryPropertiesCommand : public cmCommand
{
public:
/**
* This is a virtual constructor for the command.
*/
cmCommand* Clone() CM_OVERRIDE
{
cmCTestSetDirectoryPropertiesCommand* c =
new cmCTestSetDirectoryPropertiesCommand;
c->TestHandler = this->TestHandler;
return c;
}
/**
* This is called when the command is first encountered in
* the CMakeLists.txt file.
*/
bool InitialPass(std::vector<std::string> const& /*unused*/,
cmExecutionStatus& /*unused*/) CM_OVERRIDE;
cmCTestTestHandler* TestHandler;
};
bool cmCTestSetDirectoryPropertiesCommand::InitialPass(
std::vector<std::string> const& args, cmExecutionStatus&)
{
return this->TestHandler->SetDirectoryProperties(args);
}
// get the next number in a string with numbers separated by ,
// pos is the start of the search and pos2 is the end of the search
// pos becomes pos2 after a call to GetNextNumber.
......@@ -1661,6 +1691,12 @@ void cmCTestTestHandler::GetListOfTests()
newCom4->TestHandler = this;
cm.GetState()->AddBuiltinCommand("set_tests_properties", newCom4);
// Add handler for SET_DIRECTORY_PROPERTIES
cmCTestSetDirectoryPropertiesCommand* newCom5 =
new cmCTestSetDirectoryPropertiesCommand;
newCom5->TestHandler = this;
cm.GetState()->AddBuiltinCommand("set_directory_properties", newCom5);
const char* testFilename;
if (cmSystemTools::FileExists("CTestTestfile.cmake")) {
// does the CTestTestfile.cmake exist ?
......@@ -2172,7 +2208,16 @@ bool cmCTestTestHandler::SetTestsProperties(
cmSystemTools::ExpandListArgument(val, rtit->Environment);
}
if (key == "LABELS") {
cmSystemTools::ExpandListArgument(val, rtit->Labels);
std::vector<std::string> Labels;
cmSystemTools::ExpandListArgument(val, Labels);
rtit->Labels.insert(rtit->Labels.end(), Labels.begin(),
Labels.end());
// sort the array
std::sort(rtit->Labels.begin(), rtit->Labels.end());
// remove duplicates
std::vector<std::string>::iterator new_end =
std::unique(rtit->Labels.begin(), rtit->Labels.end());
rtit->Labels.erase(new_end, rtit->Labels.end());
}
if (key == "MEASUREMENT") {
size_t pos = val.find_first_of('=');
......@@ -2225,6 +2270,54 @@ bool cmCTestTestHandler::SetTestsProperties(
return true;
}
bool cmCTestTestHandler::SetDirectoryProperties(
const std::vector<std::string>& args)
{
std::vector<std::string>::const_iterator it;
std::vector<std::string> tests;
bool found = false;
for (it = args.begin(); it != args.end(); ++it) {
if (*it == "PROPERTIES") {
found = true;
break;
}
tests.push_back(*it);
}
if (!found) {
return false;
}
++it; // skip PROPERTIES
for (; it != args.end(); ++it) {
std::string key = *it;
++it;
if (it == args.end()) {
break;
}
std::string val = *it;
cmCTestTestHandler::ListOfTests::iterator rtit;
for (rtit = this->TestList.begin(); rtit != this->TestList.end(); ++rtit) {
std::string cwd = cmSystemTools::GetCurrentWorkingDirectory();
if (cwd == rtit->Directory) {
if (key == "LABELS") {
std::vector<std::string> DirectoryLabels;
cmSystemTools::ExpandListArgument(val, DirectoryLabels);
rtit->Labels.insert(rtit->Labels.end(), DirectoryLabels.begin(),
DirectoryLabels.end());
// sort the array
std::sort(rtit->Labels.begin(), rtit->Labels.end());
// remove duplicates
std::vector<std::string>::iterator new_end =
std::unique(rtit->Labels.begin(), rtit->Labels.end());
rtit->Labels.erase(new_end, rtit->Labels.end());
}
}
}
}
return true;
}
bool cmCTestTestHandler::AddTest(const std::vector<std::string>& args)
{
const std::string& testname = args[0];
......
......@@ -90,6 +90,11 @@ public:
*/
bool SetTestsProperties(const std::vector<std::string>& args);
/**
* Set directory properties
*/
bool SetDirectoryProperties(const std::vector<std::string>& args);
void Initialize() CM_OVERRIDE;
// NOTE: This struct is Saved/Restored
......
......@@ -147,8 +147,6 @@ void GetScriptingCommands(cmState* state)
state->AddBuiltinCommand("separate_arguments",
new cmSeparateArgumentsCommand);
state->AddBuiltinCommand("set", new cmSetCommand);
state->AddBuiltinCommand("set_directory_properties",
new cmSetDirectoryPropertiesCommand);
state->AddBuiltinCommand("set_property", new cmSetPropertyCommand);
state->AddBuiltinCommand("site_name", new cmSiteNameCommand);
state->AddBuiltinCommand("string", new cmStringCommand);
......@@ -231,6 +229,8 @@ void GetProjectCommands(cmState* state)
state->AddBuiltinCommand("install_targets", new cmInstallTargetsCommand);
state->AddBuiltinCommand("link_directories", new cmLinkDirectoriesCommand);
state->AddBuiltinCommand("project", new cmProjectCommand);
state->AddBuiltinCommand("set_directory_properties",
new cmSetDirectoryPropertiesCommand);
state->AddBuiltinCommand("set_source_files_properties",
new cmSetSourceFilesPropertiesCommand);
state->AddBuiltinCommand("set_target_properties",
......
......@@ -2811,7 +2811,12 @@ void cmGlobalGenerator::WriteSummary(cmGeneratorTarget* target)
#ifdef CMAKE_BUILD_WITH_CMAKE
// Check whether labels are enabled for this target.
if (const char* value = target->GetProperty("LABELS")) {
const char* targetLabels = target->GetProperty("LABELS");
const char* directoryLabels =
target->Target->GetMakefile()->GetProperty("LABELS");
const char* cmakeDirectoryLabels =
target->Target->GetMakefile()->GetDefinition("CMAKE_DIRECTORY_LABELS");
if (targetLabels || directoryLabels || cmakeDirectoryLabels) {
Json::Value lj_root(Json::objectValue);
Json::Value& lj_target = lj_root["target"] = Json::objectValue;
lj_target["name"] = target->GetName();
......@@ -2821,19 +2826,53 @@ void cmGlobalGenerator::WriteSummary(cmGeneratorTarget* target)
cmSystemTools::MakeDirectory(dir.c_str());
cmGeneratedFileStream fout(file.c_str());
std::vector<std::string> labels;
// List the target-wide labels. All sources in the target get
// these labels.
std::vector<std::string> labels;
cmSystemTools::ExpandListArgument(value, labels);
if (!labels.empty()) {
fout << "# Target labels\n";
for (std::vector<std::string>::const_iterator li = labels.begin();
li != labels.end(); ++li) {
fout << " " << *li << "\n";
lj_target_labels.append(*li);
if (targetLabels) {
cmSystemTools::ExpandListArgument(targetLabels, labels);
if (!labels.empty()) {
fout << "# Target labels\n";
for (std::vector<std::string>::const_iterator li = labels.begin();
li != labels.end(); ++li) {
fout << " " << *li << "\n";
lj_target_labels.append(*li);
}
}
}
// List directory labels
std::vector<std::string> directoryLabelsList;
std::vector<std::string> cmakeDirectoryLabelsList;
if (directoryLabels) {
cmSystemTools::ExpandListArgument(directoryLabels, directoryLabelsList);
}
if (cmakeDirectoryLabels) {
cmSystemTools::ExpandListArgument(cmakeDirectoryLabels,
cmakeDirectoryLabelsList);
}
if (!directoryLabelsList.empty() || !cmakeDirectoryLabelsList.empty()) {
fout << "# Directory labels\n";
}
for (std::vector<std::string>::const_iterator li =
directoryLabelsList.begin();
li != directoryLabelsList.end(); ++li) {
fout << " " << *li << "\n";
lj_target_labels.append(*li);
}
for (std::vector<std::string>::const_iterator li =
cmakeDirectoryLabelsList.begin();
li != cmakeDirectoryLabelsList.end(); ++li) {
fout << " " << *li << "\n";
lj_target_labels.append(*li);
}
// List the source files with any per-source labels.
fout << "# Source files and their labels\n";
std::vector<cmSourceFile*> sources;
......
......@@ -277,6 +277,25 @@ void cmLocalGenerator::GenerateTestFiles()
outP = cmOutputConverter::EscapeForCMake(outP);
fout << "subdirs(" << outP << ")" << std::endl;
}
// Add directory labels property
const char* directoryLabels =
this->Makefile->GetDefinition("CMAKE_DIRECTORY_LABELS");
const char* labels = this->Makefile->GetProperty("LABELS");
if (labels || directoryLabels) {
fout << "set_directory_properties(PROPERTIES LABELS ";
if (labels) {
fout << cmOutputConverter::EscapeForCMake(labels);
}
if (labels && directoryLabels) {
fout << ";";
}
if (directoryLabels) {
fout << cmOutputConverter::EscapeForCMake(directoryLabels);
}
fout << ")" << std::endl;
}
}
void cmLocalGenerator::CreateEvaluationFileOutputs(std::string const& config)
......@@ -327,6 +346,7 @@ void cmLocalGenerator::GenerateInstallRules()
{
// Compute the install prefix.
const char* prefix = this->Makefile->GetDefinition("CMAKE_INSTALL_PREFIX");
#if defined(_WIN32) && !defined(__CYGWIN__)
std::string prefix_win32;
if (!prefix) {
......
......@@ -1237,6 +1237,9 @@ void cmMakefile::InitializeFromParent(cmMakefile* parent)
}
}
// labels
this->SetProperty("LABELS", parent->GetProperty("LABELS"));
// link libraries
this->SetProperty("LINK_LIBRARIES", parent->GetProperty("LINK_LIBRARIES"));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment