|
|
|
@@ -1049,420 +1049,6 @@ protected: |
|
|
|
JUCE_DECLARE_NON_COPYABLE (MSVCProjectExporterBase)
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
class MSVCProjectExporterVC2008 : public MSVCProjectExporterBase
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
//==============================================================================
|
|
|
|
MSVCProjectExporterVC2008 (Project& p, const ValueTree& s,
|
|
|
|
const char* folderName = "VisualStudio2008")
|
|
|
|
: MSVCProjectExporterBase (p, s, folderName)
|
|
|
|
{
|
|
|
|
name = getName();
|
|
|
|
}
|
|
|
|
|
|
|
|
static const char* getName() { return "Visual Studio 2008"; }
|
|
|
|
static const char* getValueTreeTypeName() { return "VS2008"; }
|
|
|
|
int getVisualStudioVersion() const override { return 9; }
|
|
|
|
|
|
|
|
static MSVCProjectExporterVC2008* createForSettings (Project& project, const ValueTree& settings)
|
|
|
|
{
|
|
|
|
if (settings.hasType (getValueTreeTypeName()))
|
|
|
|
return new MSVCProjectExporterVC2008 (project, settings);
|
|
|
|
|
|
|
|
return nullptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
class MSVC2008Target : public MSVCTargetBase
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
MSVC2008Target (ProjectType::Target::Type targetType, const MSVCProjectExporterVC2008& exporter)
|
|
|
|
: MSVCTargetBase (targetType, exporter)
|
|
|
|
{}
|
|
|
|
|
|
|
|
const MSVCProjectExporterVC2008& getOwner() const { return dynamic_cast<const MSVCProjectExporterVC2008&> (owner); }
|
|
|
|
String getProjectVersionString() const override { return "9.00"; }
|
|
|
|
String getProjectFileSuffix() const override { return ".vcproj"; }
|
|
|
|
String getTopLevelXmlEntity() const override { return "VisualStudioProject"; }
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
void fillInProjectXml (XmlElement& projectXml) const override
|
|
|
|
{
|
|
|
|
projectXml.setAttribute("ProjectType", "Visual C++");
|
|
|
|
projectXml.setAttribute("Version", getProjectVersionString());
|
|
|
|
|
|
|
|
String fullTargetName = (getOwner().getProjectName() + String (" (") + getName() + String (")"));
|
|
|
|
|
|
|
|
projectXml.setAttribute("Name", fullTargetName);
|
|
|
|
projectXml.setAttribute("ProjectGUID", getProjectGuid());
|
|
|
|
projectXml.setAttribute("TargetFrameworkVersion", "131072");
|
|
|
|
|
|
|
|
{
|
|
|
|
XmlElement* platforms = projectXml.createNewChildElement("Platforms");
|
|
|
|
XmlElement* platform = platforms->createNewChildElement("Platform");
|
|
|
|
platform->setAttribute("Name", "Win32");
|
|
|
|
}
|
|
|
|
|
|
|
|
projectXml.createNewChildElement("ToolFiles");
|
|
|
|
createConfigs (*projectXml.createNewChildElement("Configurations"));
|
|
|
|
projectXml.createNewChildElement("References");
|
|
|
|
createFiles (*projectXml.createNewChildElement("Files"));
|
|
|
|
projectXml.createNewChildElement("Globals");
|
|
|
|
}
|
|
|
|
|
|
|
|
void createConfig (XmlElement& xml, const MSVCBuildConfiguration& config) const
|
|
|
|
{
|
|
|
|
const bool isDebug = config.isDebug();
|
|
|
|
|
|
|
|
xml.setAttribute ("Name", config.createMSVCConfigName());
|
|
|
|
|
|
|
|
if (getConfigTargetPath (config).isNotEmpty())
|
|
|
|
xml.setAttribute ("OutputDirectory", FileHelpers::windowsStylePath (getConfigTargetPath (config)));
|
|
|
|
|
|
|
|
xml.setAttribute ("IntermediateDirectory", FileHelpers::windowsStylePath (getIntermediatesPath (config)));
|
|
|
|
|
|
|
|
const ProjectType::Target::TargetFileType fileType = getTargetFileType();
|
|
|
|
|
|
|
|
xml.setAttribute ("ConfigurationType", (fileType == sharedLibraryOrDLL || fileType == pluginBundle) ? "2"
|
|
|
|
: ((fileType == staticLibrary) ? "4" : "1"));
|
|
|
|
xml.setAttribute ("UseOfMFC", "0");
|
|
|
|
xml.setAttribute ("ATLMinimizesCRunTimeLibraryUsage", "false");
|
|
|
|
xml.setAttribute ("CharacterSet", "2");
|
|
|
|
|
|
|
|
if (! (isDebug || config.shouldDisableWholeProgramOpt()))
|
|
|
|
xml.setAttribute ("WholeProgramOptimization", "1");
|
|
|
|
|
|
|
|
XmlElement* preBuildEvent = createToolElement (xml, "VCPreBuildEventTool");
|
|
|
|
const String preBuildCommand = getPreBuildSteps (config);
|
|
|
|
if (preBuildCommand.isNotEmpty())
|
|
|
|
{
|
|
|
|
preBuildEvent->setAttribute ("Description", "Pre-build");
|
|
|
|
preBuildEvent->setAttribute ("CommandLine", preBuildCommand);
|
|
|
|
}
|
|
|
|
|
|
|
|
createToolElement (xml, "VCCustomBuildTool");
|
|
|
|
createToolElement (xml, "VCXMLDataGeneratorTool");
|
|
|
|
createToolElement (xml, "VCWebServiceProxyGeneratorTool");
|
|
|
|
|
|
|
|
if (fileType != staticLibrary)
|
|
|
|
{
|
|
|
|
XmlElement* midl = createToolElement (xml, "VCMIDLTool");
|
|
|
|
midl->setAttribute ("PreprocessorDefinitions", isDebug ? "_DEBUG" : "NDEBUG");
|
|
|
|
midl->setAttribute ("MkTypLibCompatible", "true");
|
|
|
|
midl->setAttribute ("SuppressStartupBanner", "true");
|
|
|
|
midl->setAttribute ("TargetEnvironment", "1");
|
|
|
|
midl->setAttribute ("TypeLibraryName", getOwner().getIntDirFile (config, config.getOutputFilename (".tlb", true)));
|
|
|
|
midl->setAttribute ("HeaderFileName", "");
|
|
|
|
}
|
|
|
|
|
|
|
|
{
|
|
|
|
XmlElement* compiler = createToolElement (xml, "VCCLCompilerTool");
|
|
|
|
|
|
|
|
compiler->setAttribute ("Optimization", getOptimisationLevelString (config.getOptimisationLevelInt()));
|
|
|
|
|
|
|
|
if (isDebug)
|
|
|
|
{
|
|
|
|
compiler->setAttribute ("BufferSecurityCheck", "");
|
|
|
|
compiler->setAttribute ("DebugInformationFormat", (fileType == staticLibrary) ? "3" : "4");
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
compiler->setAttribute ("InlineFunctionExpansion", "1");
|
|
|
|
compiler->setAttribute ("StringPooling", "true");
|
|
|
|
}
|
|
|
|
|
|
|
|
compiler->setAttribute ("AdditionalIncludeDirectories", getOwner().replacePreprocessorTokens (config, getOwner().getHeaderSearchPaths (config).joinIntoString (";")));
|
|
|
|
compiler->setAttribute ("PreprocessorDefinitions", getPreprocessorDefs (config, ";"));
|
|
|
|
|
|
|
|
const bool runtimeDLL = shouldUseRuntimeDLL (config);
|
|
|
|
compiler->setAttribute ("RuntimeLibrary", runtimeDLL ? (isDebug ? 3 : 2) // MT DLL
|
|
|
|
: (isDebug ? 1 : 0)); // MT static
|
|
|
|
compiler->setAttribute ("RuntimeTypeInfo", "true");
|
|
|
|
compiler->setAttribute ("UsePrecompiledHeader", "0");
|
|
|
|
compiler->setAttribute ("PrecompiledHeaderFile", getOwner().getIntDirFile (config, config.getOutputFilename (".pch", true)));
|
|
|
|
compiler->setAttribute ("AssemblerListingLocation", "$(IntDir)\\");
|
|
|
|
compiler->setAttribute ("ObjectFile", "$(IntDir)\\");
|
|
|
|
compiler->setAttribute ("ProgramDataBaseFileName", "$(IntDir)\\");
|
|
|
|
compiler->setAttribute ("WarningLevel", String (config.getWarningLevel()));
|
|
|
|
compiler->setAttribute ("SuppressStartupBanner", "true");
|
|
|
|
|
|
|
|
const String extraFlags (getOwner().replacePreprocessorTokens (config, getOwner().getExtraCompilerFlagsString()).trim());
|
|
|
|
if (extraFlags.isNotEmpty())
|
|
|
|
compiler->setAttribute ("AdditionalOptions", extraFlags);
|
|
|
|
}
|
|
|
|
|
|
|
|
createToolElement (xml, "VCManagedResourceCompilerTool");
|
|
|
|
|
|
|
|
{
|
|
|
|
XmlElement* resCompiler = createToolElement (xml, "VCResourceCompilerTool");
|
|
|
|
resCompiler->setAttribute ("PreprocessorDefinitions", isDebug ? "_DEBUG" : "NDEBUG");
|
|
|
|
}
|
|
|
|
|
|
|
|
createToolElement (xml, "VCPreLinkEventTool");
|
|
|
|
|
|
|
|
if (fileType != staticLibrary)
|
|
|
|
{
|
|
|
|
XmlElement* linker = createToolElement (xml, "VCLinkerTool");
|
|
|
|
|
|
|
|
linker->setAttribute ("OutputFile", getOutputFilePath (config));
|
|
|
|
linker->setAttribute ("SuppressStartupBanner", "true");
|
|
|
|
|
|
|
|
linker->setAttribute ("IgnoreDefaultLibraryNames", isDebug ? "libcmt.lib, msvcrt.lib" : "");
|
|
|
|
linker->setAttribute ("GenerateDebugInformation", (isDebug || config.shouldGenerateDebugSymbols()) ? "true" : "false");
|
|
|
|
linker->setAttribute ("LinkIncremental", config.shouldLinkIncremental() ? "2" : "1");
|
|
|
|
linker->setAttribute ("ProgramDatabaseFile", getOwner().getIntDirFile (config, config.getOutputFilename (".pdb", true)));
|
|
|
|
linker->setAttribute ("SubSystem", (type != ConsoleApp ? "2" : "1"));
|
|
|
|
|
|
|
|
const StringArray librarySearchPaths (getLibrarySearchPaths (config));
|
|
|
|
if (librarySearchPaths.size() > 0)
|
|
|
|
linker->setAttribute ("AdditionalLibraryDirectories", librarySearchPaths.joinIntoString (";"));
|
|
|
|
|
|
|
|
linker->setAttribute ("GenerateManifest", config.shouldGenerateManifest() ? "true" : "false");
|
|
|
|
|
|
|
|
if (! isDebug)
|
|
|
|
{
|
|
|
|
linker->setAttribute ("OptimizeReferences", "2");
|
|
|
|
linker->setAttribute ("EnableCOMDATFolding", "2");
|
|
|
|
}
|
|
|
|
|
|
|
|
linker->setAttribute ("TargetMachine", "1"); // (64-bit build = 5)
|
|
|
|
|
|
|
|
const String delayLoadedDLLs (getDelayLoadedDLLs());
|
|
|
|
if (delayLoadedDLLs.isNotEmpty())
|
|
|
|
linker->setAttribute ("DelayLoadDLLs", delayLoadedDLLs);
|
|
|
|
|
|
|
|
if (config.config [Ids::msvcModuleDefinitionFile].toString().isNotEmpty())
|
|
|
|
linker->setAttribute ("ModuleDefinitionFile", config.config [Ids::msvcModuleDefinitionFile].toString());
|
|
|
|
|
|
|
|
const String externalLibraries (getExternalLibraries (config, getOwner().getExternalLibrariesString()));
|
|
|
|
if (externalLibraries.isNotEmpty())
|
|
|
|
linker->setAttribute ("AdditionalDependencies", getOwner().replacePreprocessorTokens (config, externalLibraries).trim());
|
|
|
|
|
|
|
|
String extraLinkerOptions (getOwner().getExtraLinkerFlagsString());
|
|
|
|
if (extraLinkerOptions.isNotEmpty())
|
|
|
|
linker->setAttribute ("AdditionalOptions", getOwner().replacePreprocessorTokens (config, extraLinkerOptions).trim());
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
XmlElement* librarian = createToolElement (xml, "VCLibrarianTool");
|
|
|
|
|
|
|
|
librarian->setAttribute ("OutputFile", getOutputFilePath (config));
|
|
|
|
librarian->setAttribute ("IgnoreDefaultLibraryNames", isDebug ? "libcmt.lib, msvcrt.lib" : "");
|
|
|
|
}
|
|
|
|
|
|
|
|
createToolElement (xml, "VCALinkTool");
|
|
|
|
createToolElement (xml, "VCManifestTool");
|
|
|
|
createToolElement (xml, "VCXDCMakeTool");
|
|
|
|
|
|
|
|
{
|
|
|
|
XmlElement* bscMake = createToolElement (xml, "VCBscMakeTool");
|
|
|
|
bscMake->setAttribute ("SuppressStartupBanner", "true");
|
|
|
|
bscMake->setAttribute ("OutputFile", getOwner().getIntDirFile (config, config.getOutputFilename (".bsc", true)));
|
|
|
|
}
|
|
|
|
|
|
|
|
createToolElement (xml, "VCFxCopTool");
|
|
|
|
|
|
|
|
if (fileType != staticLibrary)
|
|
|
|
createToolElement (xml, "VCAppVerifierTool");
|
|
|
|
|
|
|
|
XmlElement* postBuildEvent = createToolElement (xml, "VCPostBuildEventTool");
|
|
|
|
const String postBuild = getPostBuildSteps (config);
|
|
|
|
|
|
|
|
if (postBuild.isNotEmpty())
|
|
|
|
{
|
|
|
|
postBuildEvent->setAttribute ("Description", "Post-build");
|
|
|
|
postBuildEvent->setAttribute ("CommandLine", postBuild);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void createConfigs (XmlElement& xml) const
|
|
|
|
{
|
|
|
|
for (ConstConfigIterator config (getOwner()); config.next();)
|
|
|
|
createConfig (*xml.createNewChildElement ("Configuration"),
|
|
|
|
dynamic_cast<const MSVCBuildConfiguration&> (*config));
|
|
|
|
}
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
void addFile (const RelativePath& file, XmlElement& parent, const bool useStdcall) const
|
|
|
|
{
|
|
|
|
jassert (file.getRoot() == RelativePath::buildTargetFolder);
|
|
|
|
|
|
|
|
XmlElement* fileXml = parent.createNewChildElement ("File");
|
|
|
|
fileXml->setAttribute ("RelativePath", file.toWindowsStyle());
|
|
|
|
|
|
|
|
if (useStdcall)
|
|
|
|
{
|
|
|
|
for (ConstConfigIterator i (getOwner()); i.next();)
|
|
|
|
{
|
|
|
|
const MSVCBuildConfiguration& config = dynamic_cast<const MSVCBuildConfiguration&> (*i);
|
|
|
|
XmlElement* fileConfig = fileXml->createNewChildElement ("FileConfiguration");
|
|
|
|
fileConfig->setAttribute ("Name", config.createMSVCConfigName());
|
|
|
|
|
|
|
|
XmlElement* tool = createToolElement (*fileConfig, "VCCLCompilerTool");
|
|
|
|
|
|
|
|
if (useStdcall)
|
|
|
|
tool->setAttribute ("CallingConvention", "2");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
XmlElement* createGroup (const String& groupName, XmlElement& parent) const
|
|
|
|
{
|
|
|
|
XmlElement* filter = parent.createNewChildElement ("Filter");
|
|
|
|
filter->setAttribute ("Name", groupName);
|
|
|
|
return filter;
|
|
|
|
}
|
|
|
|
|
|
|
|
void addFiles (const Project::Item& projectItem, XmlElement& parent) const
|
|
|
|
{
|
|
|
|
const Type targetType = (getOwner().getProject().getProjectType().isAudioPlugin() ? type : SharedCodeTarget);
|
|
|
|
|
|
|
|
if (projectItem.isGroup())
|
|
|
|
{
|
|
|
|
XmlElement* filter = createGroup (projectItem.getName(), parent);
|
|
|
|
|
|
|
|
for (int i = 0; i < projectItem.getNumChildren(); ++i)
|
|
|
|
addFiles (projectItem.getChild (i), *filter);
|
|
|
|
}
|
|
|
|
else if (projectItem.shouldBeCompiled()
|
|
|
|
&& getOwner().getProject().getTargetTypeFromFilePath (projectItem.getFile(), true) == targetType)
|
|
|
|
{
|
|
|
|
const RelativePath path (projectItem.getFile(), getOwner().getTargetFolder(), RelativePath::buildTargetFolder);
|
|
|
|
|
|
|
|
if (getOwner().shouldFileBeCompiledByDefault (path))
|
|
|
|
addFile (path, parent, getOwner().shouldFileBeCompiledByDefault (path) && shouldUseStdCall (path));
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void createFiles (XmlElement& files) const
|
|
|
|
{
|
|
|
|
for (int i = 0; i < getOwner().getAllGroups().size(); ++i)
|
|
|
|
{
|
|
|
|
const Project::Item& group = getOwner().getAllGroups().getReference (i);
|
|
|
|
|
|
|
|
if (group.getNumChildren() > 0)
|
|
|
|
addFiles (group, files);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
void addPlatformSpecificSettingsForProjectType (const ProjectType& type) override
|
|
|
|
{
|
|
|
|
MSVCProjectExporterBase::addPlatformSpecificSettingsForProjectType (type);
|
|
|
|
|
|
|
|
callForAllSupportedTargets ([this] (ProjectType::Target::Type targetType)
|
|
|
|
{
|
|
|
|
if (MSVCTargetBase* target = new MSVC2008Target (targetType, *this))
|
|
|
|
{
|
|
|
|
if (targetType != ProjectType::Target::AggregateTarget)
|
|
|
|
targets.add (target);
|
|
|
|
}
|
|
|
|
});
|
|
|
|
|
|
|
|
// If you hit this assert, you tried to generate a project for an exporter
|
|
|
|
// that does not support any of your targets!
|
|
|
|
jassert (targets.size() > 0);
|
|
|
|
}
|
|
|
|
|
|
|
|
void create (const OwnedArray<LibraryModule>&) const override
|
|
|
|
{
|
|
|
|
createResourcesAndIcon();
|
|
|
|
|
|
|
|
if (hasResourceFile())
|
|
|
|
{
|
|
|
|
for (int i = 0; i < getAllGroups().size(); ++i)
|
|
|
|
{
|
|
|
|
Project::Item& group = getAllGroups().getReference (i);
|
|
|
|
|
|
|
|
if (group.getID() == ProjectSaver::getGeneratedGroupID())
|
|
|
|
{
|
|
|
|
if (iconFile != File())
|
|
|
|
{
|
|
|
|
group.addFileAtIndex (iconFile, -1, true);
|
|
|
|
group.findItemForFile (iconFile).getShouldAddToBinaryResourcesValue() = false;
|
|
|
|
}
|
|
|
|
|
|
|
|
group.addFileAtIndex (rcFile, -1, true);
|
|
|
|
group.findItemForFile (rcFile).getShouldAddToBinaryResourcesValue() = false;
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
for (int i = 0; i < targets.size(); ++i)
|
|
|
|
if (MSVCTargetBase* target = targets[i])
|
|
|
|
target->writeProjectFile();
|
|
|
|
|
|
|
|
{
|
|
|
|
MemoryOutputStream mo;
|
|
|
|
writeSolutionFile (mo, getSolutionVersionString(), String());
|
|
|
|
|
|
|
|
overwriteFileIfDifferentOrThrow (getSLNFile(), mo);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
protected:
|
|
|
|
virtual String getSolutionVersionString() const { return String ("10.00") + newLine + "# Visual C++ Express 2008"; }
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
static const char* getOptimisationLevelString (int level)
|
|
|
|
{
|
|
|
|
switch (level)
|
|
|
|
{
|
|
|
|
case optimiseMaxSpeed: return "3";
|
|
|
|
case optimiseMinSize: return "1";
|
|
|
|
default: return "0";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
JUCE_DECLARE_NON_COPYABLE (MSVCProjectExporterVC2008)
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
class MSVCProjectExporterVC2005 : public MSVCProjectExporterVC2008
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
MSVCProjectExporterVC2005 (Project& p, const ValueTree& t)
|
|
|
|
: MSVCProjectExporterVC2008 (p, t, "VisualStudio2005")
|
|
|
|
{
|
|
|
|
name = getName();
|
|
|
|
}
|
|
|
|
|
|
|
|
class MSVC2005Target : public MSVC2008Target
|
|
|
|
{
|
|
|
|
public:
|
|
|
|
MSVC2005Target (ProjectType::Target::Type targetType, const MSVCProjectExporterVC2005& exporter)
|
|
|
|
: MSVC2008Target (targetType, exporter)
|
|
|
|
{}
|
|
|
|
|
|
|
|
const MSVCProjectExporterVC2005& getOwner() const { return dynamic_cast<const MSVCProjectExporterVC2005&> (owner); }
|
|
|
|
String getProjectVersionString() const override { return "8.00"; }
|
|
|
|
};
|
|
|
|
|
|
|
|
static const char* getName() { return "Visual Studio 2005"; }
|
|
|
|
static const char* getValueTreeTypeName() { return "VS2005"; }
|
|
|
|
int getVisualStudioVersion() const override { return 8; }
|
|
|
|
|
|
|
|
static MSVCProjectExporterVC2005* createForSettings (Project& project, const ValueTree& settings)
|
|
|
|
{
|
|
|
|
if (settings.hasType (getValueTreeTypeName()))
|
|
|
|
return new MSVCProjectExporterVC2005 (project, settings);
|
|
|
|
|
|
|
|
return nullptr;
|
|
|
|
}
|
|
|
|
|
|
|
|
protected:
|
|
|
|
String getSolutionVersionString() const override { return String ("9.00") + newLine + "# Visual C++ Express 2005"; }
|
|
|
|
|
|
|
|
JUCE_DECLARE_NON_COPYABLE (MSVCProjectExporterVC2005)
|
|
|
|
};
|
|
|
|
|
|
|
|
//==============================================================================
|
|
|
|
class MSVCProjectExporterVC2010 : public MSVCProjectExporterBase
|
|
|
|
{
|
|
|
|
|