diff options
author | Brad King <brad.king@kitware.com> | 2017-04-10 15:37:49 (GMT) |
---|---|---|
committer | Brad King <brad.king@kitware.com> | 2017-04-13 20:10:32 (GMT) |
commit | 97cc29c7662f51f0e532f92e37070f9b44791b88 (patch) | |
tree | 7d048531d0208743c4acf9b36f6046547f73b0c7 | |
parent | 2f6f6f0c153f19f7efab96b2a4c3c9c05362372b (diff) | |
download | CMake-97cc29c7662f51f0e532f92e37070f9b44791b88.zip CMake-97cc29c7662f51f0e532f92e37070f9b44791b88.tar.gz CMake-97cc29c7662f51f0e532f92e37070f9b44791b88.tar.bz2 |
VS: Teach generators how to mark per-config source files
Add internal infrastructure for looping over all sources for all
configurations and generating each source with exclusion marks
for configurations in which they do not participate. This does
not yet make per-config sources available in general but does
set up some of the needed infrastructure.
Unfortunately doing this cleanly will require major refactoring of both
the VS 7-9 generators and the VS 10+ generators (for separate reasons).
Instead add some extra internal structures to carry information where we
need it.
-rw-r--r-- | Source/cmLocalVisualStudio7Generator.cxx | 63 | ||||
-rw-r--r-- | Source/cmLocalVisualStudio7Generator.h | 3 | ||||
-rw-r--r-- | Source/cmVisualStudio10TargetGenerator.cxx | 66 | ||||
-rw-r--r-- | Source/cmVisualStudio10TargetGenerator.h | 1 |
4 files changed, 97 insertions, 36 deletions
diff --git a/Source/cmLocalVisualStudio7Generator.cxx b/Source/cmLocalVisualStudio7Generator.cxx index 1a33a28..a36e1f6 100644 --- a/Source/cmLocalVisualStudio7Generator.cxx +++ b/Source/cmLocalVisualStudio7Generator.cxx @@ -1368,14 +1368,14 @@ void cmLocalVisualStudio7Generator::WriteVCProjFile(std::ostream& fout, // We may be modifying the source groups temporarily, so make a copy. std::vector<cmSourceGroup> sourceGroups = this->Makefile->GetSourceGroups(); - // get the classes from the source lists then add them to the groups - std::vector<cmSourceFile*> classes; - if (!target->GetConfigCommonSourceFiles(classes)) { - return; - } - for (std::vector<cmSourceFile*>::const_iterator i = classes.begin(); - i != classes.end(); i++) { - if (!(*i)->GetObjectLibrary().empty()) { + std::vector<cmGeneratorTarget::AllConfigSource> const& sources = + target->GetAllConfigSources(); + std::map<cmSourceFile const*, size_t> sourcesIndex; + + for (size_t si = 0; si < sources.size(); ++si) { + cmSourceFile const* sf = sources[si].Source; + sourcesIndex[sf] = si; + if (!sf->GetObjectLibrary().empty()) { if (this->GetVersion() < cmGlobalVisualStudioGenerator::VS8 || this->FortranProject) { // VS < 8 does not support per-config source locations so we @@ -1385,10 +1385,10 @@ void cmLocalVisualStudio7Generator::WriteVCProjFile(std::ostream& fout, } } // Add the file to the list of sources. - std::string source = (*i)->GetFullPath(); + std::string const source = sf->GetFullPath(); cmSourceGroup* sourceGroup = this->Makefile->FindSourceGroup(source.c_str(), sourceGroups); - sourceGroup->AssignSource(*i); + sourceGroup->AssignSource(sf); } // open the project @@ -1401,7 +1401,7 @@ void cmLocalVisualStudio7Generator::WriteVCProjFile(std::ostream& fout, // Loop through every source group. for (unsigned int i = 0; i < sourceGroups.size(); ++i) { cmSourceGroup sg = sourceGroups[i]; - this->WriteGroup(&sg, target, fout, libName, configs); + this->WriteGroup(&sg, target, fout, libName, configs, sourcesIndex); } fout << "\t</Files>\n"; @@ -1423,25 +1423,28 @@ struct cmLVS7GFileConfig class cmLocalVisualStudio7GeneratorFCInfo { public: - cmLocalVisualStudio7GeneratorFCInfo(cmLocalVisualStudio7Generator* lg, - cmGeneratorTarget* target, - cmSourceFile const& sf, - std::vector<std::string> const& configs); + cmLocalVisualStudio7GeneratorFCInfo( + cmLocalVisualStudio7Generator* lg, cmGeneratorTarget* target, + cmGeneratorTarget::AllConfigSource const& acs, + std::vector<std::string> const& configs); std::map<std::string, cmLVS7GFileConfig> FileConfigMap; }; cmLocalVisualStudio7GeneratorFCInfo::cmLocalVisualStudio7GeneratorFCInfo( cmLocalVisualStudio7Generator* lg, cmGeneratorTarget* gt, - cmSourceFile const& sf, std::vector<std::string> const& configs) + cmGeneratorTarget::AllConfigSource const& acs, + std::vector<std::string> const& configs) { + cmSourceFile const& sf = *acs.Source; std::string objectName; if (gt->HasExplicitObjectName(&sf)) { objectName = gt->GetObjectName(&sf); } // Compute per-source, per-config information. + size_t ci = 0; for (std::vector<std::string>::const_iterator i = configs.begin(); - i != configs.end(); ++i) { + i != configs.end(); ++i, ++ci) { std::string configUpper = cmSystemTools::UpperCase(*i); cmLVS7GFileConfig fc; bool needfc = false; @@ -1507,7 +1510,9 @@ cmLocalVisualStudio7GeneratorFCInfo::cmLocalVisualStudio7GeneratorFCInfo( } // If HEADER_FILE_ONLY is set, we must suppress this generation in // the project file - fc.ExcludedFromBuild = (sf.GetPropertyAsBool("HEADER_FILE_ONLY")); + fc.ExcludedFromBuild = sf.GetPropertyAsBool("HEADER_FILE_ONLY") || + std::find(acs.Configs.begin(), acs.Configs.end(), ci) == + acs.Configs.end(); if (fc.ExcludedFromBuild) { needfc = true; } @@ -1562,7 +1567,8 @@ std::string cmLocalVisualStudio7Generator::ComputeLongestObjectDirectory( bool cmLocalVisualStudio7Generator::WriteGroup( const cmSourceGroup* sg, cmGeneratorTarget* target, std::ostream& fout, - const std::string& libName, std::vector<std::string> const& configs) + const std::string& libName, std::vector<std::string> const& configs, + std::map<cmSourceFile const*, size_t> const& sourcesIndex) { cmGlobalVisualStudio7Generator* gg = static_cast<cmGlobalVisualStudio7Generator*>(this->GlobalGenerator); @@ -1573,7 +1579,8 @@ bool cmLocalVisualStudio7Generator::WriteGroup( bool hasChildrenWithSources = false; std::ostringstream tmpOut; for (unsigned int i = 0; i < children.size(); ++i) { - if (this->WriteGroup(&children[i], target, tmpOut, libName, configs)) { + if (this->WriteGroup(&children[i], target, tmpOut, libName, configs, + sourcesIndex)) { hasChildrenWithSources = true; } } @@ -1589,15 +1596,26 @@ bool cmLocalVisualStudio7Generator::WriteGroup( this->WriteVCProjBeginGroup(fout, name.c_str(), ""); } + std::vector<cmGeneratorTarget::AllConfigSource> const& sources = + target->GetAllConfigSources(); + // Loop through each source in the source group. for (std::vector<const cmSourceFile*>::const_iterator sf = sourceFiles.begin(); sf != sourceFiles.end(); ++sf) { std::string source = (*sf)->GetFullPath(); - FCInfo fcinfo(this, target, *(*sf), configs); if (source != libName || target->GetType() == cmStateEnums::UTILITY || target->GetType() == cmStateEnums::GLOBAL_TARGET) { + // Look up the source kind and configs. + std::map<cmSourceFile const*, size_t>::const_iterator map_it = + sourcesIndex.find(*sf); + // The map entry must exist because we populated it earlier. + assert(map_it != sourcesIndex.end()); + cmGeneratorTarget::AllConfigSource const& acs = sources[map_it->second]; + + FCInfo fcinfo(this, target, acs, configs); + fout << "\t\t\t<File\n"; std::string d = this->ConvertToXMLOutputPathSingle(source.c_str()); // Tell MS-Dev what the source is. If the compiler knows how to @@ -1637,6 +1655,9 @@ bool cmLocalVisualStudio7Generator::WriteGroup( lang == "ASM_MASM") { aCompilerTool = "MASM"; } + if (acs.Kind == cmGeneratorTarget::SourceKindExternalObject) { + aCompilerTool = "VCCustomBuildTool"; + } for (std::map<std::string, cmLVS7GFileConfig>::const_iterator fci = fcinfo.FileConfigMap.begin(); fci != fcinfo.FileConfigMap.end(); ++fci) { diff --git a/Source/cmLocalVisualStudio7Generator.h b/Source/cmLocalVisualStudio7Generator.h index 2bf38ea..89a3ee3 100644 --- a/Source/cmLocalVisualStudio7Generator.h +++ b/Source/cmLocalVisualStudio7Generator.h @@ -119,7 +119,8 @@ private: bool WriteGroup(const cmSourceGroup* sg, cmGeneratorTarget* target, std::ostream& fout, const std::string& libName, - std::vector<std::string> const& configs); + std::vector<std::string> const& configs, + std::map<cmSourceFile const*, size_t> const& sourcesIndex); friend class cmLocalVisualStudio7GeneratorFCInfo; friend class cmLocalVisualStudio7GeneratorInternals; diff --git a/Source/cmVisualStudio10TargetGenerator.cxx b/Source/cmVisualStudio10TargetGenerator.cxx index 8e6014a..fbfc1ed 100644 --- a/Source/cmVisualStudio10TargetGenerator.cxx +++ b/Source/cmVisualStudio10TargetGenerator.cxx @@ -1241,16 +1241,15 @@ void cmVisualStudio10TargetGenerator::WriteGroups() // collect up group information std::vector<cmSourceGroup> sourceGroups = this->Makefile->GetSourceGroups(); - std::vector<cmSourceFile*> classes; - if (!this->GeneratorTarget->GetConfigCommonSourceFiles(classes)) { - return; - } + + std::vector<cmGeneratorTarget::AllConfigSource> const& sources = + this->GeneratorTarget->GetAllConfigSources(); std::set<cmSourceGroup*> groupsUsed; - for (std::vector<cmSourceFile*>::const_iterator s = classes.begin(); - s != classes.end(); s++) { - cmSourceFile* sf = *s; - std::string const& source = sf->GetFullPath(); + for (std::vector<cmGeneratorTarget::AllConfigSource>::const_iterator si = + sources.begin(); + si != sources.end(); ++si) { + std::string const& source = si->Source->GetFullPath(); cmSourceGroup* sourceGroup = this->Makefile->FindSourceGroup(source.c_str(), sourceGroups); groupsUsed.insert(sourceGroup); @@ -1734,12 +1733,17 @@ void cmVisualStudio10TargetGenerator::WriteAllSources() } this->WriteString("<ItemGroup>\n", 1); - cmGeneratorTarget::KindedSources const& sources = - this->GeneratorTarget->GetKindedSources(""); + std::vector<size_t> all_configs; + for (size_t ci = 0; ci < this->Configurations.size(); ++ci) { + all_configs.push_back(ci); + } + + std::vector<cmGeneratorTarget::AllConfigSource> const& sources = + this->GeneratorTarget->GetAllConfigSources(); - for (std::vector<cmGeneratorTarget::SourceAndKind>::const_iterator si = - sources.Sources.begin(); - si != sources.Sources.end(); ++si) { + for (std::vector<cmGeneratorTarget::AllConfigSource>::const_iterator si = + sources.begin(); + si != sources.end(); ++si) { std::string tool; switch (si->Kind) { case cmGeneratorTarget::SourceKindAppManifest: @@ -1810,14 +1814,35 @@ void cmVisualStudio10TargetGenerator::WriteAllSources() } if (!tool.empty()) { + // Compute set of configurations to exclude, if any. + std::vector<size_t> const& include_configs = si->Configs; + std::vector<size_t> exclude_configs; + std::set_difference(all_configs.begin(), all_configs.end(), + include_configs.begin(), include_configs.end(), + std::back_inserter(exclude_configs)); + if (si->Kind == cmGeneratorTarget::SourceKindObjectSource) { + // FIXME: refactor generation to avoid tracking XML syntax state. this->WriteSource(tool, si->Source, " "); - if (this->OutputSourceSpecificFlags(si->Source)) { + bool have_nested = this->OutputSourceSpecificFlags(si->Source); + if (!exclude_configs.empty()) { + if (!have_nested) { + (*this->BuildFileStream) << ">\n"; + } + this->WriteExcludeFromBuild(exclude_configs); + have_nested = true; + } + if (have_nested) { this->WriteString("</", 2); (*this->BuildFileStream) << tool << ">\n"; } else { (*this->BuildFileStream) << " />\n"; } + } else if (!exclude_configs.empty()) { + this->WriteSource(tool, si->Source, ">\n"); + this->WriteExcludeFromBuild(exclude_configs); + this->WriteString("</", 2); + (*this->BuildFileStream) << tool << ">\n"; } else { this->WriteSource(tool, si->Source); } @@ -2001,6 +2026,19 @@ bool cmVisualStudio10TargetGenerator::OutputSourceSpecificFlags( return hasFlags; } +void cmVisualStudio10TargetGenerator::WriteExcludeFromBuild( + std::vector<size_t> const& exclude_configs) +{ + for (std::vector<size_t>::const_iterator ci = exclude_configs.begin(); + ci != exclude_configs.end(); ++ci) { + this->WriteString("", 3); + (*this->BuildFileStream) + << "<ExcludedFromBuild Condition=\"'$(Configuration)|$(Platform)'=='" + << cmVS10EscapeXML(this->Configurations[*ci]) << "|" + << cmVS10EscapeXML(this->Platform) << "'\">true</ExcludedFromBuild>\n"; + } +} + void cmVisualStudio10TargetGenerator::WritePathAndIncrementalLinkOptions() { cmStateEnums::TargetType ttype = this->GeneratorTarget->GetType(); diff --git a/Source/cmVisualStudio10TargetGenerator.h b/Source/cmVisualStudio10TargetGenerator.h index 7432244..bd270bf 100644 --- a/Source/cmVisualStudio10TargetGenerator.h +++ b/Source/cmVisualStudio10TargetGenerator.h @@ -62,6 +62,7 @@ private: void WriteNsightTegraConfigurationValues(std::string const& config); void WriteSource(std::string const& tool, cmSourceFile const* sf, const char* end = 0); + void WriteExcludeFromBuild(std::vector<size_t> const& exclude_configs); void WriteAllSources(); void WriteDotNetReferences(); void WriteDotNetReference(std::string const& ref, std::string const& hint); |