diff options
Diffstat (limited to 'Source/cmVisualStudio10TargetGenerator.cxx')
-rw-r--r-- | Source/cmVisualStudio10TargetGenerator.cxx | 265 |
1 files changed, 129 insertions, 136 deletions
diff --git a/Source/cmVisualStudio10TargetGenerator.cxx b/Source/cmVisualStudio10TargetGenerator.cxx index 9418761..6caaad1 100644 --- a/Source/cmVisualStudio10TargetGenerator.cxx +++ b/Source/cmVisualStudio10TargetGenerator.cxx @@ -11,6 +11,7 @@ ============================================================================*/ #include "cmVisualStudio10TargetGenerator.h" #include "cmGlobalVisualStudio10Generator.h" +#include "cmGeneratorTarget.h" #include "cmTarget.h" #include "cmComputeLinkInformation.h" #include "cmGeneratedFileStream.h" @@ -62,6 +63,7 @@ cmVisualStudio10TargetGenerator(cmTarget* target, { this->GlobalGenerator = gg; this->Target = target; + this->GeneratorTarget = gg->GetGeneratorTarget(target); this->Makefile = target->GetMakefile(); this->LocalGenerator = (cmLocalVisualStudio7Generator*) @@ -70,7 +72,6 @@ cmVisualStudio10TargetGenerator(cmTarget* target, this->GlobalGenerator->CreateGUID(this->Name.c_str()); this->GUID = this->GlobalGenerator->GetGUID(this->Name.c_str()); this->Platform = gg->GetPlatformName(); - this->ComputeObjectNames(); this->BuildFileStream = 0; } @@ -147,7 +148,7 @@ void cmVisualStudio10TargetGenerator::Generate() this->Target->SetProperty("GENERATOR_FILE_NAME",this->Name.c_str()); this->Target->SetProperty("GENERATOR_FILE_NAME_EXT", ".vcxproj"); - if(this->Target->GetType() <= cmTarget::MODULE_LIBRARY) + if(this->Target->GetType() <= cmTarget::OBJECT_LIBRARY) { if(!this->ComputeClOptions()) { @@ -252,8 +253,7 @@ void cmVisualStudio10TargetGenerator::Generate() this->WritePathAndIncrementalLinkOptions(); this->WriteItemDefinitionGroups(); this->WriteCustomCommands(); - this->WriteObjSources(); - this->WriteCLSources(); + this->WriteAllSources(); this->WriteDotNetReferences(); this->WriteWinRTReferences(); this->WriteProjectReferences(); @@ -358,6 +358,7 @@ void cmVisualStudio10TargetGenerator::WriteProjectConfigurationValues() case cmTarget::MODULE_LIBRARY: configType += "DynamicLibrary"; break; + case cmTarget::OBJECT_LIBRARY: case cmTarget::STATIC_LIBRARY: configType += "StaticLibrary"; break; @@ -388,12 +389,17 @@ void cmVisualStudio10TargetGenerator::WriteProjectConfigurationValues() mfcLine += useOfMfcValue + "</UseOfMfc>\n"; this->WriteString(mfcLine.c_str(), 2); - if(this->Target->GetType() <= cmTarget::MODULE_LIBRARY && + if(this->Target->GetType() <= cmTarget::OBJECT_LIBRARY && this->ClOptions[*i]->UsingUnicode() || this->Target->GetPropertyAsBool("VS_WINRT_EXTENSIONS")) { this->WriteString("<CharacterSet>Unicode</CharacterSet>\n", 2); } + else if (this->Target->GetType() <= cmTarget::MODULE_LIBRARY && + this->ClOptions[*i]->UsingSBCS()) + { + this->WriteString("<CharacterSet>NotSet</CharacterSet>\n", 2); + } else { this->WriteString("<CharacterSet>MultiByte</CharacterSet>\n", 2); @@ -416,12 +422,11 @@ void cmVisualStudio10TargetGenerator::WriteProjectConfigurationValues() void cmVisualStudio10TargetGenerator::WriteCustomCommands() { this->SourcesVisited.clear(); - std::vector<cmSourceFile*> const& sources = this->Target->GetSourceFiles(); - for(std::vector<cmSourceFile*>::const_iterator source = sources.begin(); - source != sources.end(); ++source) + for(std::vector<cmSourceFile*>::const_iterator + si = this->GeneratorTarget->CustomCommands.begin(); + si != this->GeneratorTarget->CustomCommands.end(); ++si) { - cmSourceFile* sf = *source; - this->WriteCustomCommand(sf); + this->WriteCustomCommand(*si); } } @@ -629,6 +634,25 @@ void cmVisualStudio10TargetGenerator::WriteGroups() this->WriteGroupSources("Midl", idls, sourceGroups); this->WriteGroupSources("CustomBuild", customBuild, sourceGroups); + // Add object library contents as external objects. + std::vector<std::string> objs; + this->GeneratorTarget->UseObjectLibraries(objs); + if(!objs.empty()) + { + this->WriteString("<ItemGroup>\n", 1); + for(std::vector<std::string>::const_iterator + oi = objs.begin(); oi != objs.end(); ++oi) + { + std::string obj = *oi; + this->WriteString("<Object Include=\"", 2); + this->ConvertToWindowsSlash(obj); + (*this->BuildFileStream ) << obj << "\">\n"; + this->WriteString("<Filter>Object Libraries</Filter>\n", 3); + this->WriteString("</Object>\n", 2); + } + this->WriteString("</ItemGroup>\n", 1); + } + this->WriteString("<ItemGroup>\n", 1); for(std::set<cmSourceGroup*>::iterator g = groupsUsed.begin(); g != groupsUsed.end(); ++g) @@ -652,6 +676,18 @@ void cmVisualStudio10TargetGenerator::WriteGroups() this->WriteString("</Filter>\n", 2); } } + if(!objs.empty()) + { + this->WriteString("<Filter Include=\"Object Libraries\">\n", 2); + std::string guidName = "SG_Filter_Object Libraries"; + this->GlobalGenerator->CreateGUID(guidName.c_str()); + this->WriteString("<UniqueIdentifier>", 3); + std::string guid = + this->GlobalGenerator->GetGUID(guidName.c_str()); + (*this->BuildFileStream) << "{" << guid << "}" + << "</UniqueIdentifier>\n"; + this->WriteString("</Filter>\n", 2); + } this->WriteString("</ItemGroup>\n", 1); this->WriteGroupSources("None", none, sourceGroups); this->WriteString("</Project>\n", 0); @@ -758,107 +794,56 @@ WriteGroupSources(const char* name, this->WriteString("</ItemGroup>\n", 1); } -void cmVisualStudio10TargetGenerator::WriteObjSources() -{ - if(this->Target->GetType() > cmTarget::MODULE_LIBRARY) - { - return; - } - bool first = true; - std::vector<cmSourceFile*>const & sources = this->Target->GetSourceFiles(); - for(std::vector<cmSourceFile*>::const_iterator source = sources.begin(); - source != sources.end(); ++source) - { - std::string ext = - cmSystemTools::LowerCase((*source)->GetExtension()); - if(ext == "obj" || ext == "o") - { - if(first) - { - this->WriteString("<ItemGroup>\n", 1); - first = false; - } - // If an object file is generated, then vs10 - // will use it in the build, and we have to list - // it as None instead of Object - if((*source)->GetPropertyAsBool("GENERATED")) - { - this->WriteString("<None Include=\"", 2); - } - // If it is not a generated object then we have - // to use the Object type - else - { - this->WriteString("<Object Include=\"", 2); - } - (*this->BuildFileStream ) << (*source)->GetFullPath() << "\" />\n"; - } - } - if(!first) +void cmVisualStudio10TargetGenerator::WriteSource( + const char* tool, cmSourceFile* sf, bool end) +{ + std::string sourceFile = sf->GetFullPath(); + // do not use a relative path here because it means that you + // can not use as long a path to the file. + this->ConvertToWindowsSlash(sourceFile); + this->WriteString("<", 2); + (*this->BuildFileStream ) << tool << + " Include=\"" << sourceFile << (end? "\" />\n" : "\" "); +} + +void cmVisualStudio10TargetGenerator::WriteSources( + const char* tool, std::vector<cmSourceFile*> const& sources) +{ + for(std::vector<cmSourceFile*>::const_iterator + si = sources.begin(); si != sources.end(); ++si) { - this->WriteString("</ItemGroup>\n", 1); + this->WriteSource(tool, *si); } } - -void cmVisualStudio10TargetGenerator::WriteCLSources() +void cmVisualStudio10TargetGenerator::WriteAllSources() { if(this->Target->GetType() > cmTarget::UTILITY) { return; } this->WriteString("<ItemGroup>\n", 1); - std::vector<cmSourceFile*>const& sources = this->Target->GetSourceFiles(); - for(std::vector<cmSourceFile*>::const_iterator source = sources.begin(); - source != sources.end(); ++source) + + this->WriteSources("ClInclude", this->GeneratorTarget->HeaderSources); + this->WriteSources("Midl", this->GeneratorTarget->IDLSources); + + for(std::vector<cmSourceFile*>::const_iterator + si = this->GeneratorTarget->ObjectSources.begin(); + si != this->GeneratorTarget->ObjectSources.end(); ++si) { - std::string ext = cmSystemTools::LowerCase((*source)->GetExtension()); - if((*source)->GetCustomCommand() || ext == "o" || ext == "obj") - { - continue; - } - // If it is not a custom command and it is not a pre-built obj file, - // then add it as a source (c/c++/header/rc/idl) file - bool header = (*source)->GetPropertyAsBool("HEADER_FILE_ONLY") - || this->GlobalGenerator->IgnoreFile(ext.c_str()); - const char* lang = (*source)->GetLanguage(); - bool cl = lang && (strcmp(lang, "C") == 0 || strcmp(lang, "CXX") ==0); - bool rc = lang && (strcmp(lang, "RC") == 0); - bool idl = ext == "idl"; - std::string sourceFile = (*source)->GetFullPath(); - // do not use a relative path here because it means that you - // can not use as long a path to the file. - this->ConvertToWindowsSlash(sourceFile); - // output the source file - if(header) - { - this->WriteString("<ClInclude Include=\"", 2); - } - else if(cl) - { - this->WriteString("<ClCompile Include=\"", 2); - } - else if(rc) - { - this->WriteString("<ResourceCompile Include=\"", 2); - } - else if(idl) - { - this->WriteString("<Midl Include=\"", 2); - } - else - { - this->WriteString("<None Include=\"", 2); - } - (*this->BuildFileStream ) << sourceFile << "\""; + const char* lang = (*si)->GetLanguage(); + bool cl = strcmp(lang, "C") == 0 || strcmp(lang, "CXX") == 0; + bool rc = strcmp(lang, "RC") == 0; + const char* tool = cl? "ClCompile" : (rc? "ResourceCompile" : "None"); + this->WriteSource(tool, *si, false); // ouput any flags specific to this source file - if(!header && cl && this->OutputSourceSpecificFlags(*source)) + if(cl && this->OutputSourceSpecificFlags(*si)) { // if the source file has specific flags the tag // is ended on a new line this->WriteString("</ClCompile>\n", 2); } - else if(!header && rc && this->OutputSourceSpecificFlags(*source)) + else if(rc && this->OutputSourceSpecificFlags(*si)) { this->WriteString("</ResourceCompile>\n", 2); } @@ -867,32 +852,32 @@ void cmVisualStudio10TargetGenerator::WriteCLSources() (*this->BuildFileStream ) << " />\n"; } } - this->WriteString("</ItemGroup>\n", 1); -} -void cmVisualStudio10TargetGenerator::ComputeObjectNames() -{ - // We may be modifying the source groups temporarily, so make a copy. - std::vector<cmSourceGroup> sourceGroups = this->Makefile->GetSourceGroups(); + for(std::vector<cmSourceFile*>::const_iterator + si = this->GeneratorTarget->ExternalObjects.begin(); + si != this->GeneratorTarget->ExternalObjects.end(); ++si) + { + // If an object file is generated in this target, then vs10 will use + // it in the build, and we have to list it as None instead of Object. + std::vector<cmSourceFile*> const* d = this->Target->GetSourceDepends(*si); + this->WriteSource((d && !d->empty())? "None":"Object", *si); + } + + this->WriteSources("None", this->GeneratorTarget->ExtraSources); - // get the classes from the source lists then add them to the groups - std::vector<cmSourceFile*>const & classes = this->Target->GetSourceFiles(); - for(std::vector<cmSourceFile*>::const_iterator i = classes.begin(); - i != classes.end(); i++) + // Add object library contents as external objects. + std::vector<std::string> objs; + this->GeneratorTarget->UseObjectLibraries(objs); + for(std::vector<std::string>::const_iterator + oi = objs.begin(); oi != objs.end(); ++oi) { - // Add the file to the list of sources. - std::string source = (*i)->GetFullPath(); - if(cmSystemTools::UpperCase((*i)->GetExtension()) == "DEF") - { - this->ModuleDefinitionFile = (*i)->GetFullPath(); - } - cmSourceGroup& sourceGroup = - this->Makefile->FindSourceGroup(source.c_str(), sourceGroups); - sourceGroup.AssignSource(*i); + std::string obj = *oi; + this->WriteString("<Object Include=\"", 2); + this->ConvertToWindowsSlash(obj); + (*this->BuildFileStream ) << obj << "\" />\n"; } - // Compute which sources need unique object computation. - this->LocalGenerator->ComputeObjectNameRequirements(sourceGroups); + this->WriteString("</ItemGroup>\n", 1); } bool cmVisualStudio10TargetGenerator::OutputSourceSpecificFlags( @@ -901,16 +886,11 @@ bool cmVisualStudio10TargetGenerator::OutputSourceSpecificFlags( cmSourceFile& sf = *source; cmLocalVisualStudio7Generator* lg = this->LocalGenerator; - // Compute the maximum length full path to the intermediate - // files directory for any configuration. This is used to construct - // object file names that do not produce paths that are too long. - std::string dir_max; - lg->ComputeMaxDirectoryLength(dir_max, *this->Target); - std::string objectName; - if(lg->NeedObjectName.find(&sf) != lg->NeedObjectName.end()) + if(this->GeneratorTarget->ExplicitObjectName.find(&sf) + != this->GeneratorTarget->ExplicitObjectName.end()) { - objectName = lg->GetObjectFileNameWithoutTarget(sf, dir_max); + objectName = this->GeneratorTarget->Objects[&sf]; } std::string flags; std::string defines; @@ -1031,20 +1011,29 @@ void cmVisualStudio10TargetGenerator::WritePathAndIncrementalLinkOptions() } else { - std::string targetNameFull = - this->Target->GetFullName(config->c_str()); std::string intermediateDir = this->LocalGenerator-> GetTargetDirectory(*this->Target); intermediateDir += "/"; intermediateDir += *config; intermediateDir += "/"; + std::string outDir; + std::string targetNameFull; + if(ttype == cmTarget::OBJECT_LIBRARY) + { + outDir = intermediateDir; + targetNameFull = this->Target->GetName(); + targetNameFull += ".lib"; + } + else + { + outDir = this->Target->GetDirectory(config->c_str()) + "/"; + targetNameFull = this->Target->GetFullName(config->c_str()); + } this->ConvertToWindowsSlash(intermediateDir); - std::string outDir = this->Target->GetDirectory(config->c_str()); this->ConvertToWindowsSlash(outDir); this->WritePlatformConfigTag("OutDir", config->c_str(), 3); *this->BuildFileStream << outDir - << "\\" << "</OutDir>\n"; this->WritePlatformConfigTag("IntDir", config->c_str(), 3); @@ -1278,11 +1267,15 @@ void cmVisualStudio10TargetGenerator::WriteClOptions( *this->BuildFileStream << configName << "</AssemblerListingLocation>\n"; this->WriteString("<ObjectFileName>$(IntDir)</ObjectFileName>\n", 3); - this->WriteString("<ProgramDataBaseFileName>", 3); - *this->BuildFileStream << this->Target->GetDirectory(configName.c_str()) - << "/" - << this->Target->GetPDBName(configName.c_str()) - << "</ProgramDataBaseFileName>\n"; + if(this->Target->GetType() != cmTarget::OBJECT_LIBRARY) + { + // TODO: PDB for object library? + this->WriteString("<ProgramDataBaseFileName>", 3); + *this->BuildFileStream << this->Target->GetDirectory(configName.c_str()) + << "/" + << this->Target->GetPDBName(configName.c_str()) + << "</ProgramDataBaseFileName>\n"; + } this->WriteString("</ClCompile>\n", 2); } @@ -1514,10 +1507,10 @@ void cmVisualStudio10TargetGenerator::WriteLinkOptions(std::string const& linkOptions.AddFlag("ImportLibrary", imLib.c_str()); linkOptions.AddFlag("ProgramDataBaseFile", pdb.c_str()); linkOptions.Parse(flags.c_str()); - if(!this->ModuleDefinitionFile.empty()) + if(!this->GeneratorTarget->ModuleDefinitionFile.empty()) { linkOptions.AddFlag("ModuleDefinitionFile", - this->ModuleDefinitionFile.c_str()); + this->GeneratorTarget->ModuleDefinitionFile.c_str()); } linkOptions.RemoveFlag("GenerateManifest"); @@ -1586,14 +1579,14 @@ void cmVisualStudio10TargetGenerator::WriteItemDefinitionGroups() static_cast<cmGlobalVisualStudio7Generator *> (this->GlobalGenerator)->GetConfigurations(); std::vector<std::string> includes; - this->LocalGenerator->GetIncludeDirectories(includes); + this->LocalGenerator->GetIncludeDirectories(includes, this->Target); for(std::vector<std::string>::iterator i = configs->begin(); i != configs->end(); ++i) { this->WritePlatformConfigTag("ItemDefinitionGroup", i->c_str(), 1); *this->BuildFileStream << "\n"; // output cl compile flags <ClCompile></ClCompile> - if(this->Target->GetType() <= cmTarget::MODULE_LIBRARY) + if(this->Target->GetType() <= cmTarget::OBJECT_LIBRARY) { this->WriteClOptions(*i, includes); // output rc compile flags <ResourceCompile></ResourceCompile> |