From 6c0e9ee276e9e35a970990baec09c0c2c85b3804 Mon Sep 17 00:00:00 2001 From: Stephen Kelly Date: Sat, 1 Aug 2015 12:05:13 +0200 Subject: [PATCH 1/2] cmMakefile: Store EvaluationFiles. Relieve the cmGlobalGenerator of this responsibility. Evaluate the generator expressions in the context of the cmLocalGenerator. --- Source/cmFileCommand.cxx | 7 ++-- Source/cmGlobalGenerator.cxx | 56 ++++--------------------------- Source/cmGlobalGenerator.h | 8 ----- Source/cmGlobalNinjaGenerator.cxx | 26 +++++++------- Source/cmLocalGenerator.cxx | 48 ++++++++++++++++++++++++++ Source/cmLocalGenerator.h | 2 ++ Source/cmMakefile.cxx | 21 ++++++++++++ Source/cmMakefile.h | 9 +++++ 8 files changed, 100 insertions(+), 77 deletions(-) diff --git a/Source/cmFileCommand.cxx b/Source/cmFileCommand.cxx index 0daed66c2..87faf8468 100644 --- a/Source/cmFileCommand.cxx +++ b/Source/cmFileCommand.cxx @@ -3573,11 +3573,8 @@ void cmFileCommand::AddEvaluationFile(const std::string &inputName, cmsys::auto_ptr conditionCge = conditionGe.Parse(condition); - this->Makefile->GetGlobalGenerator()->AddEvaluationFile(inputName, - outputCge, - this->Makefile, - conditionCge, - inputIsContent); + this->Makefile->AddEvaluationFile(inputName, outputCge, + conditionCge, inputIsContent); } //---------------------------------------------------------------------------- diff --git a/Source/cmGlobalGenerator.cxx b/Source/cmGlobalGenerator.cxx index 1d6608b81..d6d36d48f 100644 --- a/Source/cmGlobalGenerator.cxx +++ b/Source/cmGlobalGenerator.cxx @@ -30,7 +30,6 @@ #include "cmGeneratedFileStream.h" #include "cmGeneratorTarget.h" #include "cmGeneratorExpression.h" -#include "cmGeneratorExpressionEvaluationFile.h" #include "cmExportBuildFileGenerator.h" #include "cmCPackPropertiesGenerator.h" #include "cmAlgorithms.h" @@ -1561,9 +1560,6 @@ void cmGlobalGenerator::ClearGeneratorMembers() cmDeleteAll(this->GeneratorTargets); this->GeneratorTargets.clear(); - cmDeleteAll(this->EvaluationFiles); - this->EvaluationFiles.clear(); - cmDeleteAll(this->BuildExportSets); this->BuildExportSets.clear(); @@ -3032,61 +3028,21 @@ cmGlobalGenerator::GetFilenameTargetDepends(cmSourceFile* sf) const { void cmGlobalGenerator::CreateEvaluationSourceFiles( std::string const& config) const { - for(std::vector::const_iterator - li = this->EvaluationFiles.begin(); - li != this->EvaluationFiles.end(); - ++li) + unsigned int i; + for (i = 0; i < this->LocalGenerators.size(); ++i) { - (*li)->CreateOutputFile(config); + this->LocalGenerators[i]->CreateEvaluationFileOutputs(config); } } -//---------------------------------------------------------------------------- -void cmGlobalGenerator::AddEvaluationFile(const std::string &inputFile, - cmsys::auto_ptr outputExpr, - cmMakefile *makefile, - cmsys::auto_ptr condition, - bool inputIsContent) -{ - this->EvaluationFiles.push_back( - new cmGeneratorExpressionEvaluationFile(inputFile, outputExpr, - makefile, condition, - inputIsContent)); -} - //---------------------------------------------------------------------------- void cmGlobalGenerator::ProcessEvaluationFiles() { std::vector generatedFiles; - for(std::vector::const_iterator - li = this->EvaluationFiles.begin(); - li != this->EvaluationFiles.end(); - ++li) + unsigned int i; + for (i = 0; i < this->LocalGenerators.size(); ++i) { - (*li)->Generate(); - if (cmSystemTools::GetFatalErrorOccured()) - { - return; - } - std::vector files = (*li)->GetFiles(); - std::sort(files.begin(), files.end()); - - std::vector intersection; - std::set_intersection(files.begin(), files.end(), - generatedFiles.begin(), generatedFiles.end(), - std::back_inserter(intersection)); - if (!intersection.empty()) - { - cmSystemTools::Error("Files to be generated by multiple different " - "commands: ", cmWrap('"', intersection, '"', " ").c_str()); - return; - } - - generatedFiles.insert(generatedFiles.end(), - files.begin(), files.end()); - std::vector::iterator newIt = - generatedFiles.end() - files.size(); - std::inplace_merge(generatedFiles.begin(), newIt, generatedFiles.end()); + this->LocalGenerators[i]->ProcessEvaluationFiles(generatedFiles); } } diff --git a/Source/cmGlobalGenerator.h b/Source/cmGlobalGenerator.h index 949237260..3402fbcde 100644 --- a/Source/cmGlobalGenerator.h +++ b/Source/cmGlobalGenerator.h @@ -34,7 +34,6 @@ class cmake; class cmGeneratorTarget; -class cmGeneratorExpressionEvaluationFile; class cmMakefile; class cmLocalGenerator; class cmExternalMakefileProjectGenerator; @@ -334,12 +333,6 @@ public: static std::string EscapeJSON(const std::string& s); - void AddEvaluationFile(const std::string &inputFile, - cmsys::auto_ptr outputName, - cmMakefile *makefile, - cmsys::auto_ptr condition, - bool inputIsContent); - void ProcessEvaluationFiles(); std::map& GetBuildExportSets() @@ -436,7 +429,6 @@ protected: TargetMap TotalTargets; TargetMap AliasTargets; TargetMap ImportedTargets; - std::vector EvaluationFiles; const char* GetPredefinedTargetsFolder(); virtual bool UseFolderProperty(); diff --git a/Source/cmGlobalNinjaGenerator.cxx b/Source/cmGlobalNinjaGenerator.cxx index d24cce837..cc7f78b5f 100644 --- a/Source/cmGlobalNinjaGenerator.cxx +++ b/Source/cmGlobalNinjaGenerator.cxx @@ -1055,23 +1055,21 @@ void cmGlobalNinjaGenerator::WriteUnknownExplicitDependencies(std::ostream& os) { knownDependencies.insert( ng->ConvertToNinjaPath( *j ) ); } - } - knownDependencies.insert( "CMakeCache.txt" ); - - for(std::vector::const_iterator - li = this->EvaluationFiles.begin(); - li != this->EvaluationFiles.end(); - ++li) - { - //get all the files created by generator expressions and convert them - //to ninja paths - std::vector files = (*li)->GetFiles(); - typedef std::vector::const_iterator vect_it; - for(vect_it j = files.begin(); j != files.end(); ++j) + std::vector const& ef = + (*i)->GetMakefile()->GetEvaluationFiles(); + for(std::vector::const_iterator + li = ef.begin(); li != ef.end(); ++li) { - knownDependencies.insert( ng->ConvertToNinjaPath( *j ) ); + //get all the files created by generator expressions and convert them + //to ninja paths + std::vector evaluationFiles = (*li)->GetFiles(); + for(vect_it j = evaluationFiles.begin(); j != evaluationFiles.end(); ++j) + { + knownDependencies.insert( ng->ConvertToNinjaPath( *j ) ); + } } } + knownDependencies.insert( "CMakeCache.txt" ); for(TargetAliasMap::const_iterator i= this->TargetAliases.begin(); i != this->TargetAliases.end(); diff --git a/Source/cmLocalGenerator.cxx b/Source/cmLocalGenerator.cxx index 6b48a447c..7cc256aca 100644 --- a/Source/cmLocalGenerator.cxx +++ b/Source/cmLocalGenerator.cxx @@ -16,6 +16,7 @@ #include "cmGlobalGenerator.h" #include "cmInstallGenerator.h" #include "cmInstallFilesGenerator.h" +#include "cmGeneratorExpressionEvaluationFile.h" #include "cmInstallScriptGenerator.h" #include "cmInstallTargetGenerator.h" #include "cmMakefile.h" @@ -212,6 +213,53 @@ void cmLocalGenerator::GenerateTestFiles() } } +void cmLocalGenerator::CreateEvaluationFileOutputs(std::string const& config) +{ + std::vector ef = + this->Makefile->GetEvaluationFiles(); + for(std::vector::const_iterator + li = ef.begin(); li != ef.end(); ++li) + { + (*li)->CreateOutputFile(config); + } +} + +void cmLocalGenerator::ProcessEvaluationFiles( + std::vector& generatedFiles) +{ + std::vector ef = + this->Makefile->GetEvaluationFiles(); + for(std::vector::const_iterator + li = ef.begin(); + li != ef.end(); + ++li) + { + (*li)->Generate(); + if (cmSystemTools::GetFatalErrorOccured()) + { + return; + } + std::vector files = (*li)->GetFiles(); + std::sort(files.begin(), files.end()); + + std::vector intersection; + std::set_intersection(files.begin(), files.end(), + generatedFiles.begin(), generatedFiles.end(), + std::back_inserter(intersection)); + if (!intersection.empty()) + { + cmSystemTools::Error("Files to be generated by multiple different " + "commands: ", cmWrap('"', intersection, '"', " ").c_str()); + return; + } + + generatedFiles.insert(generatedFiles.end(), files.begin(), files.end()); + std::vector::iterator newIt = + generatedFiles.end() - files.size(); + std::inplace_merge(generatedFiles.begin(), newIt, generatedFiles.end()); + } +} + //---------------------------------------------------------------------------- void cmLocalGenerator::GenerateInstallRules() { diff --git a/Source/cmLocalGenerator.h b/Source/cmLocalGenerator.h index 297157429..1c18788eb 100644 --- a/Source/cmLocalGenerator.h +++ b/Source/cmLocalGenerator.h @@ -305,6 +305,8 @@ public: void IssueMessage(cmake::MessageType t, std::string const& text) const; + void CreateEvaluationFileOutputs(const std::string& config); + void ProcessEvaluationFiles(std::vector& generatedFiles); void ComputeObjectMaxPath(); protected: diff --git a/Source/cmMakefile.cxx b/Source/cmMakefile.cxx index 4bdc9d53c..140788845 100644 --- a/Source/cmMakefile.cxx +++ b/Source/cmMakefile.cxx @@ -21,6 +21,7 @@ #include "cmState.h" #include "cmOutputConverter.h" #include "cmFunctionBlocker.h" +#include "cmGeneratorExpressionEvaluationFile.h" #include "cmListFileCache.h" #include "cmCommandArgumentParserHelper.h" #include "cmGeneratorExpression.h" @@ -235,6 +236,9 @@ cmMakefile::~cmMakefile() cmDeleteAll(this->ImportedTargetsOwned); cmDeleteAll(this->FinalPassCommands); cmDeleteAll(this->FunctionBlockers); + cmDeleteAll(this->EvaluationFiles); + this->EvaluationFiles.clear(); + this->FunctionBlockers.clear(); if (this->PolicyStack.size() != 1) { @@ -777,6 +781,23 @@ void cmMakefile::EnforceDirectoryLevelRules() const } } +void cmMakefile::AddEvaluationFile(const std::string& inputFile, + cmsys::auto_ptr outputName, + cmsys::auto_ptr condition, + bool inputIsContent) +{ + this->EvaluationFiles.push_back( + new cmGeneratorExpressionEvaluationFile(inputFile, outputName, + this, condition, + inputIsContent)); +} + +std::vector +cmMakefile::GetEvaluationFiles() const +{ + return this->EvaluationFiles; +} + namespace { struct file_not_persistent diff --git a/Source/cmMakefile.h b/Source/cmMakefile.h index 1e5c301e9..c16ab3d07 100644 --- a/Source/cmMakefile.h +++ b/Source/cmMakefile.h @@ -52,6 +52,7 @@ class cmVariableWatch; class cmake; class cmMakefileCall; class cmCMakePolicyCommand; +class cmGeneratorExpressionEvaluationFile; /** \class cmMakefile * \brief Process the input CMakeLists.txt file. @@ -799,6 +800,12 @@ public: void EnforceDirectoryLevelRules() const; + void AddEvaluationFile(const std::string &inputFile, + cmsys::auto_ptr outputName, + cmsys::auto_ptr condition, + bool inputIsContent); + std::vector GetEvaluationFiles() const; + protected: // add link libraries and directories to the target void AddGlobalLinkInformation(const std::string& name, cmTarget& target); @@ -895,6 +902,8 @@ private: std::vector UnConfiguredDirectories; + std::vector EvaluationFiles; + cmPropertyMap Properties; std::vector ContextStack; From 12c3f24827d2459154fcc9773b279f96c303e591 Mon Sep 17 00:00:00 2001 From: Stephen Kelly Date: Sat, 1 Aug 2015 12:19:32 +0200 Subject: [PATCH 2/2] cmGeneratorExpressionEvaluationFile: Require generator context. Avoid storing a cmMakefile as a member, and evaluate in the context of a cmLocalGenerator instead. --- .../cmGeneratorExpressionEvaluationFile.cxx | 40 ++++++++++--------- Source/cmGeneratorExpressionEvaluationFile.h | 15 +++---- Source/cmLocalGenerator.cxx | 4 +- Source/cmMakefile.cxx | 2 +- 4 files changed, 32 insertions(+), 29 deletions(-) diff --git a/Source/cmGeneratorExpressionEvaluationFile.cxx b/Source/cmGeneratorExpressionEvaluationFile.cxx index 92ff314b8..e4d9f107e 100644 --- a/Source/cmGeneratorExpressionEvaluationFile.cxx +++ b/Source/cmGeneratorExpressionEvaluationFile.cxx @@ -25,19 +25,18 @@ cmGeneratorExpressionEvaluationFile::cmGeneratorExpressionEvaluationFile( const std::string &input, cmsys::auto_ptr outputFileExpr, - cmMakefile *makefile, cmsys::auto_ptr condition, bool inputIsContent) : Input(input), OutputFileExpr(outputFileExpr), - Makefile(makefile), Condition(condition), InputIsContent(inputIsContent) { } //---------------------------------------------------------------------------- -void cmGeneratorExpressionEvaluationFile::Generate(const std::string& config, +void cmGeneratorExpressionEvaluationFile::Generate(cmLocalGenerator* lg, + const std::string& config, const std::string& lang, cmCompiledGeneratorExpression* inputExpression, std::map &outputFiles, mode_t perm) @@ -45,7 +44,8 @@ void cmGeneratorExpressionEvaluationFile::Generate(const std::string& config, std::string rawCondition = this->Condition->GetInput(); if (!rawCondition.empty()) { - std::string condResult = this->Condition->Evaluate(this->Makefile, config, + std::string condResult = this->Condition->Evaluate(lg->GetMakefile(), + config, false, 0, 0, 0, lang); if (condResult == "0") { @@ -56,16 +56,17 @@ void cmGeneratorExpressionEvaluationFile::Generate(const std::string& config, std::ostringstream e; e << "Evaluation file condition \"" << rawCondition << "\" did " "not evaluate to valid content. Got \"" << condResult << "\"."; - this->Makefile->IssueMessage(cmake::FATAL_ERROR, e.str()); + lg->IssueMessage(cmake::FATAL_ERROR, e.str()); return; } } const std::string outputFileName - = this->OutputFileExpr->Evaluate(this->Makefile, config, + = this->OutputFileExpr->Evaluate(lg->GetMakefile(), config, false, 0, 0, 0, lang); const std::string outputContent - = inputExpression->Evaluate(this->Makefile, config, + = inputExpression->Evaluate(lg->GetMakefile(), + config, false, 0, 0, 0, lang); std::map::iterator it @@ -81,11 +82,11 @@ void cmGeneratorExpressionEvaluationFile::Generate(const std::string& config, e << "Evaluation file to be written multiple times for different " "configurations or languages with different content:\n " << outputFileName; - this->Makefile->IssueMessage(cmake::FATAL_ERROR, e.str()); + lg->IssueMessage(cmake::FATAL_ERROR, e.str()); return; } - this->Makefile->AddCMakeOutputFile(outputFileName.c_str()); + lg->GetMakefile()->AddCMakeOutputFile(outputFileName.c_str()); this->Files.push_back(outputFileName); outputFiles[outputFileName] = outputContent; @@ -100,18 +101,19 @@ void cmGeneratorExpressionEvaluationFile::Generate(const std::string& config, //---------------------------------------------------------------------------- void cmGeneratorExpressionEvaluationFile::CreateOutputFile( - std::string const& config) + cmLocalGenerator *lg, std::string const& config) { std::vector enabledLanguages; - cmGlobalGenerator *gg = this->Makefile->GetGlobalGenerator(); + cmGlobalGenerator *gg = lg->GetGlobalGenerator(); gg->GetEnabledLanguages(enabledLanguages); for(std::vector::const_iterator le = enabledLanguages.begin(); le != enabledLanguages.end(); ++le) { - std::string name = this->OutputFileExpr->Evaluate(this->Makefile, config, + std::string name = this->OutputFileExpr->Evaluate(lg->GetMakefile(), + config, false, 0, 0, 0, *le); - cmSourceFile* sf = this->Makefile->GetOrCreateSource(name); + cmSourceFile* sf = lg->GetMakefile()->GetOrCreateSource(name); sf->SetProperty("GENERATED", "1"); gg->SetFilenameTargetDepends(sf, @@ -120,7 +122,7 @@ void cmGeneratorExpressionEvaluationFile::CreateOutputFile( } //---------------------------------------------------------------------------- -void cmGeneratorExpressionEvaluationFile::Generate() +void cmGeneratorExpressionEvaluationFile::Generate(cmLocalGenerator *lg) { mode_t perm = 0; std::string inputContent; @@ -130,14 +132,14 @@ void cmGeneratorExpressionEvaluationFile::Generate() } else { - this->Makefile->AddCMakeDependFile(this->Input.c_str()); + lg->GetMakefile()->AddCMakeDependFile(this->Input.c_str()); cmSystemTools::GetPermissions(this->Input.c_str(), perm); cmsys::ifstream fin(this->Input.c_str()); if(!fin) { std::ostringstream e; e << "Evaluation file \"" << this->Input << "\" cannot be read."; - this->Makefile->IssueMessage(cmake::FATAL_ERROR, e.str()); + lg->GetMakefile()->IssueMessage(cmake::FATAL_ERROR, e.str()); return; } @@ -159,7 +161,7 @@ void cmGeneratorExpressionEvaluationFile::Generate() std::map outputFiles; std::vector allConfigs; - this->Makefile->GetConfigurations(allConfigs); + lg->GetMakefile()->GetConfigurations(allConfigs); if (allConfigs.empty()) { @@ -167,7 +169,7 @@ void cmGeneratorExpressionEvaluationFile::Generate() } std::vector enabledLanguages; - cmGlobalGenerator *gg = this->Makefile->GetGlobalGenerator(); + cmGlobalGenerator *gg = lg->GetGlobalGenerator(); gg->GetEnabledLanguages(enabledLanguages); for(std::vector::const_iterator le = enabledLanguages.begin(); @@ -176,7 +178,7 @@ void cmGeneratorExpressionEvaluationFile::Generate() for(std::vector::const_iterator li = allConfigs.begin(); li != allConfigs.end(); ++li) { - this->Generate(*li, *le, inputExpression.get(), outputFiles, perm); + this->Generate(lg, *li, *le, inputExpression.get(), outputFiles, perm); if(cmSystemTools::GetFatalErrorOccured()) { return; diff --git a/Source/cmGeneratorExpressionEvaluationFile.h b/Source/cmGeneratorExpressionEvaluationFile.h index 5d8b54c0a..ad41274ca 100644 --- a/Source/cmGeneratorExpressionEvaluationFile.h +++ b/Source/cmGeneratorExpressionEvaluationFile.h @@ -18,31 +18,32 @@ #include "cmGeneratorExpression.h" +class cmLocalGenerator; + //---------------------------------------------------------------------------- class cmGeneratorExpressionEvaluationFile { public: cmGeneratorExpressionEvaluationFile(const std::string &input, cmsys::auto_ptr outputFileExpr, - cmMakefile *makefile, cmsys::auto_ptr condition, bool inputIsContent); - void Generate(); + void Generate(cmLocalGenerator* lg); std::vector GetFiles() const { return this->Files; } - void CreateOutputFile(std::string const& config); + void CreateOutputFile(cmLocalGenerator* lg, std::string const& config); private: - void Generate(const std::string& config, const std::string& lang, - cmCompiledGeneratorExpression* inputExpression, - std::map &outputFiles, mode_t perm); + void Generate(cmLocalGenerator* lg, const std::string& config, + const std::string& lang, + cmCompiledGeneratorExpression* inputExpression, + std::map &outputFiles, mode_t perm); private: const std::string Input; const cmsys::auto_ptr OutputFileExpr; - cmMakefile *Makefile; const cmsys::auto_ptr Condition; std::vector Files; const bool InputIsContent; diff --git a/Source/cmLocalGenerator.cxx b/Source/cmLocalGenerator.cxx index 7cc256aca..ea0f6580b 100644 --- a/Source/cmLocalGenerator.cxx +++ b/Source/cmLocalGenerator.cxx @@ -220,7 +220,7 @@ void cmLocalGenerator::CreateEvaluationFileOutputs(std::string const& config) for(std::vector::const_iterator li = ef.begin(); li != ef.end(); ++li) { - (*li)->CreateOutputFile(config); + (*li)->CreateOutputFile(this, config); } } @@ -234,7 +234,7 @@ void cmLocalGenerator::ProcessEvaluationFiles( li != ef.end(); ++li) { - (*li)->Generate(); + (*li)->Generate(this); if (cmSystemTools::GetFatalErrorOccured()) { return; diff --git a/Source/cmMakefile.cxx b/Source/cmMakefile.cxx index 140788845..3e8abbcbb 100644 --- a/Source/cmMakefile.cxx +++ b/Source/cmMakefile.cxx @@ -788,7 +788,7 @@ void cmMakefile::AddEvaluationFile(const std::string& inputFile, { this->EvaluationFiles.push_back( new cmGeneratorExpressionEvaluationFile(inputFile, outputName, - this, condition, + condition, inputIsContent)); }