|
|
@@ -151,7 +151,7 @@ protected:
|
|
|
helpFormatter.setHeader(
|
|
|
"\n"
|
|
|
"The POCO C++ Libraries Visual Studio Project File Generator.\n"
|
|
|
- "Copyright (c) 2010-2015 by Applied Informatics Software Engineering GmbH.\n"
|
|
|
+ "Copyright (c) 2010-2020 by Applied Informatics Software Engineering GmbH.\n"
|
|
|
"All rights reserved.\n\n"
|
|
|
"This program generates project and solution files "
|
|
|
"for Visual Studio .NET 2003, 2005, 2008 and 2010, 2012, 2013 and 2015 from "
|
|
|
@@ -206,7 +206,7 @@ protected:
|
|
|
}
|
|
|
}
|
|
|
|
|
|
- void setProperty(Poco::Util::AbstractConfiguration& properties, const std::string& name, const Poco::Util::AbstractConfiguration& projectConfig, const std::string& projectConfigName, const std::string& platformName, const std::string& configName, const std::string& delim = ";")
|
|
|
+ void setProperty(Poco::Util::AbstractConfiguration& properties, const std::string& name, const Poco::Util::AbstractConfiguration& projectConfig, const std::string& projectConfigName, const std::string& platformName, const std::string& archName, const std::string& configName, const std::string& delim = ";")
|
|
|
{
|
|
|
std::string value = projectConfig.getString(projectConfigName, "");
|
|
|
|
|
|
@@ -224,6 +224,13 @@ protected:
|
|
|
}
|
|
|
value += platformSpecificValue;
|
|
|
|
|
|
+ std::string platformArchSpecificValue = projectConfig.getString(projectConfigName + "." + platformName + "." + archName, "");
|
|
|
+ if (!value.empty() && !platformArchSpecificValue.empty())
|
|
|
+ {
|
|
|
+ value += delim;
|
|
|
+ }
|
|
|
+ value += platformArchSpecificValue;
|
|
|
+
|
|
|
std::string platformConfigSpecificValue = projectConfig.getString(projectConfigName + "." + platformName + "." + configName, "");
|
|
|
if (!value.empty() && !platformConfigSpecificValue.empty())
|
|
|
{
|
|
|
@@ -231,10 +238,17 @@ protected:
|
|
|
}
|
|
|
value += platformConfigSpecificValue;
|
|
|
|
|
|
+ std::string platformArchConfigSpecificValue = projectConfig.getString(projectConfigName + "." + platformName + "." + archName + "." + configName, "");
|
|
|
+ if (!value.empty() && !platformArchConfigSpecificValue.empty())
|
|
|
+ {
|
|
|
+ value += delim;
|
|
|
+ }
|
|
|
+ value += platformArchConfigSpecificValue;
|
|
|
+
|
|
|
properties.setString(name, value);
|
|
|
}
|
|
|
|
|
|
- void fixFileConfigurations(Poco::XML::Node* pFilesElem, const std::string& configs, const std::string& platform)
|
|
|
+ void fixFileConfigurations(Poco::XML::Node* pFilesElem, const std::string& configs, const std::set<std::string>& archs)
|
|
|
{
|
|
|
Poco::AutoPtr<Poco::XML::NodeList> pFileElems = static_cast<Poco::XML::Element*>(pFilesElem)->getElementsByTagName("File");
|
|
|
for (int fileIndex = 0; fileIndex < pFileElems->length(); fileIndex++)
|
|
|
@@ -251,15 +265,18 @@ protected:
|
|
|
pFileConfigElem = pFileElem->getChildElement("FileConfiguration");
|
|
|
}
|
|
|
Poco::StringTokenizer configsTokenizer(configs, ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator it = configsTokenizer.begin(); it != configsTokenizer.end(); ++it)
|
|
|
+ for (const auto& arch: archs)
|
|
|
{
|
|
|
- Poco::AutoPtr<Poco::XML::Element> pNewFileConfigElem = static_cast<Poco::XML::Element*>(pPrototypeFileConfigElem->cloneNode(true));
|
|
|
- pNewFileConfigElem->setAttribute("Name", *it + "|" + platform);
|
|
|
- if (relativePath.getExtension() == "rc" && it->find("static") != std::string::npos)
|
|
|
+ for (const auto& conf: configsTokenizer)
|
|
|
{
|
|
|
- pNewFileConfigElem->setAttribute("ExcludedFromBuild", "true");
|
|
|
+ Poco::AutoPtr<Poco::XML::Element> pNewFileConfigElem = static_cast<Poco::XML::Element*>(pPrototypeFileConfigElem->cloneNode(true));
|
|
|
+ pNewFileConfigElem->setAttribute("Name", conf + "|" + arch);
|
|
|
+ if (relativePath.getExtension() == "rc" && conf.find("static") != std::string::npos)
|
|
|
+ {
|
|
|
+ pNewFileConfigElem->setAttribute("ExcludedFromBuild", "true");
|
|
|
+ }
|
|
|
+ pFileElem->appendChild(pNewFileConfigElem);
|
|
|
}
|
|
|
- pFileElem->appendChild(pNewFileConfigElem);
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
@@ -268,9 +285,9 @@ protected:
|
|
|
void replaceFiles(Poco::XML::Node* pFilesElem, const std::string& replacements)
|
|
|
{
|
|
|
Poco::StringTokenizer replacementsTok(replacements, ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator it = replacementsTok.begin(); it != replacementsTok.end(); ++it)
|
|
|
+ for (const auto& repl: replacementsTok)
|
|
|
{
|
|
|
- Poco::StringTokenizer stmtTok(*it, ">", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
+ Poco::StringTokenizer stmtTok(repl, ">", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
if (stmtTok.count() == 2)
|
|
|
{
|
|
|
std::string oldPath = stmtTok[0];
|
|
|
@@ -298,112 +315,21 @@ protected:
|
|
|
solutionFile.setWriteable(true);
|
|
|
}
|
|
|
Poco::FileOutputStream solutionStream(solutionPath.toString());
|
|
|
- if (tool == "vs71")
|
|
|
- {
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 8.00\r\n";
|
|
|
- generateSolution71(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
- }
|
|
|
- else if (tool == "vs80")
|
|
|
+ if (tool == "vs140")
|
|
|
{
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 9.00\r\n# Visual Studio 2005\r\n";
|
|
|
- generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
- }
|
|
|
- else if (tool == "vs90")
|
|
|
- {
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 10.00\r\n# Visual Studio 2008\r\n";
|
|
|
- generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
- }
|
|
|
- else if (tool == "vs100")
|
|
|
- {
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 11.00\r\n# Visual Studio 2010\r\n";
|
|
|
- generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
- }
|
|
|
- else if (tool == "vs110")
|
|
|
- {
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio 2012\r\n";
|
|
|
- generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
- }
|
|
|
- else if (tool == "vs120")
|
|
|
- {
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio 2013\r\n";
|
|
|
- generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
- }
|
|
|
- else if (tool == "vs140")
|
|
|
- {
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio 2015\r\n";
|
|
|
+ solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio 14\r\n";
|
|
|
generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
}
|
|
|
else if (tool == "vs150")
|
|
|
{
|
|
|
- solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio 2017\r\n";
|
|
|
+ solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio 15\r\n";
|
|
|
generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
}
|
|
|
- }
|
|
|
-
|
|
|
- void generateSolution71(std::ostream& solutionStream, const Poco::Path& solutionPath, const std::string& solutionGUID, const Poco::Util::AbstractConfiguration& projectConfig, const Poco::Util::AbstractConfiguration& templateProps, const std::string& platform, const std::string& tool)
|
|
|
- {
|
|
|
- std::vector<std::string> dependencies;
|
|
|
- std::string projectName = projectConfig.getString("vc.project.name", "");
|
|
|
- std::string projectGUID = projectConfig.getString("vc.project.guid", "");
|
|
|
- std::string projectPlatform = templateProps.getString("project.platform", platform);
|
|
|
- std::string projectSuffix = templateProps.getString("project.finalSuffix", templateProps.getString("project.suffix"));
|
|
|
- bool includesHaveDependencies = projectConfig.getBool("vc.solution.fixedBuildOrder", false);
|
|
|
- if (!projectName.empty())
|
|
|
- {
|
|
|
- solutionStream << "Project(\"{" << solutionGUID << "}\") = \"" << projectName << "\", \"" << projectName << projectSuffix << "\", \"{" << projectGUID << "}\"\r\n";
|
|
|
- solutionStream << "\tProjectSection(ProjectDependencies) = postProject\r\n";
|
|
|
- solutionStream << "\tEndProjectSection\r\n";
|
|
|
- solutionStream << "EndProject\r\n";
|
|
|
- dependencies.push_back(projectGUID);
|
|
|
- includesHaveDependencies = true;
|
|
|
- }
|
|
|
- std::string includes = projectConfig.getString("vc.solution.include", "");
|
|
|
- Poco::StringTokenizer includesTokenizer(includes, ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator itIncl = includesTokenizer.begin(); itIncl != includesTokenizer.end(); ++itIncl)
|
|
|
- {
|
|
|
- Poco::Path basePath(solutionPath.parent());
|
|
|
- Poco::Path inclPath(basePath, Poco::Path(*itIncl));
|
|
|
- inclPath.setExtension("progen");
|
|
|
- Poco::AutoPtr<Poco::Util::PropertyFileConfiguration> pInclConfig = loadProjectConfig(inclPath);
|
|
|
- projectName = pInclConfig->getString("vc.project.name");
|
|
|
- projectGUID = pInclConfig->getString("vc.project.guid");
|
|
|
- solutionStream << "Project(\"{" << solutionGUID << "}\") = \"" << projectName << "\", \"" << *itIncl << projectSuffix << "\", \"{" << projectGUID << "}\"\r\n";
|
|
|
- solutionStream << "\tProjectSection(ProjectDependencies) = postProject\r\n";
|
|
|
- if (includesHaveDependencies)
|
|
|
- {
|
|
|
- for (std::vector<std::string>::const_iterator itDeps = dependencies.begin(); itDeps != dependencies.end(); ++itDeps)
|
|
|
- {
|
|
|
- solutionStream << "\t\t{" << *itDeps << "} = {" << *itDeps << "}\r\n";
|
|
|
- }
|
|
|
- }
|
|
|
- solutionStream << "\tEndProjectSection\r\n";
|
|
|
- solutionStream << "EndProject\r\n";
|
|
|
- dependencies.push_back(projectGUID);
|
|
|
- }
|
|
|
-
|
|
|
- solutionStream << "Global\r\n";
|
|
|
- solutionStream << "\tGlobalSection(SolutionConfiguration) = preSolution\r\n";
|
|
|
- Poco::StringTokenizer configsTokenizer(projectConfig.getString("vc.project.configurations", ""), ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator itConf = configsTokenizer.begin(); itConf != configsTokenizer.end(); ++itConf)
|
|
|
- {
|
|
|
- solutionStream << "\t\t" << *itConf << " = " << *itConf << "\r\n";
|
|
|
- }
|
|
|
- solutionStream << "\tEndGlobalSection\r\n";
|
|
|
- solutionStream << "\tGlobalSection(ProjectConfiguration) = postSolution\r\n";
|
|
|
- for (std::vector<std::string>::const_iterator itDeps = dependencies.begin(); itDeps != dependencies.end(); ++itDeps)
|
|
|
+ else if (tool == "vs160")
|
|
|
{
|
|
|
- for (Poco::StringTokenizer::Iterator itConf = configsTokenizer.begin(); itConf != configsTokenizer.end(); ++itConf)
|
|
|
- {
|
|
|
- solutionStream << "\t\t{" << *itDeps << "}." << *itConf << ".ActiveCfg = " << *itConf << "|" << projectPlatform << "\r\n";
|
|
|
- solutionStream << "\t\t{" << *itDeps << "}." << *itConf << ".Build.0 = " << *itConf << "|" << projectPlatform << "\r\n";
|
|
|
- }
|
|
|
+ solutionStream << "Microsoft Visual Studio Solution File, Format Version 12.00\r\n# Visual Studio Version 16\r\n";
|
|
|
+ generateSolution80(solutionStream, solutionPath, solutionGUID, projectConfig, templateProps, platform, tool);
|
|
|
}
|
|
|
- solutionStream << "\tEndGlobalSection\r\n";
|
|
|
- solutionStream << "\tGlobalSection(ExtensibilityGlobals) = postSolution\r\n";
|
|
|
- solutionStream << "\tEndGlobalSection\r\n";
|
|
|
- solutionStream << "\tGlobalSection(ExtensibilityAddIns) = postSolution\r\n";
|
|
|
- solutionStream << "\tEndGlobalSection\r\n";
|
|
|
- solutionStream << "EndGlobal\r\n";
|
|
|
}
|
|
|
|
|
|
void generateSolution80(std::ostream& solutionStream, const Poco::Path& solutionPath, const std::string& solutionGUID, const Poco::Util::AbstractConfiguration& projectConfig, const Poco::Util::AbstractConfiguration& templateProps, const std::string& platform, const std::string& tool)
|
|
|
@@ -423,21 +349,21 @@ protected:
|
|
|
}
|
|
|
std::string includes = projectConfig.getString("vc.solution.include", "");
|
|
|
Poco::StringTokenizer includesTokenizer(includes, ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator itIncl = includesTokenizer.begin(); itIncl != includesTokenizer.end(); ++itIncl)
|
|
|
+ for (const auto& incl: includesTokenizer)
|
|
|
{
|
|
|
Poco::Path basePath(solutionPath.parent());
|
|
|
- Poco::Path inclPath(basePath, Poco::Path(*itIncl));
|
|
|
+ Poco::Path inclPath(basePath, Poco::Path(incl));
|
|
|
inclPath.setExtension("progen");
|
|
|
Poco::AutoPtr<Poco::Util::PropertyFileConfiguration> pInclConfig = loadProjectConfig(inclPath);
|
|
|
projectName = pInclConfig->getString("vc.project.name");
|
|
|
projectGUID = pInclConfig->getString("vc.project.guid");
|
|
|
- solutionStream << "Project(\"{" << solutionGUID << "}\") = \"" << projectName << "\", \"" << *itIncl << projectSuffix << "\", \"{" << projectGUID << "}\"\r\n";
|
|
|
+ solutionStream << "Project(\"{" << solutionGUID << "}\") = \"" << projectName << "\", \"" << incl << projectSuffix << "\", \"{" << projectGUID << "}\"\r\n";
|
|
|
if (includesHaveDependencies)
|
|
|
{
|
|
|
solutionStream << "\tProjectSection(ProjectDependencies) = postProject\r\n";
|
|
|
- for (std::vector<std::string>::const_iterator itDeps = dependencies.begin(); itDeps != dependencies.end(); ++itDeps)
|
|
|
+ for (const auto& dep: dependencies)
|
|
|
{
|
|
|
- solutionStream << "\t\t{" << *itDeps << "} = {" << *itDeps << "}\r\n";
|
|
|
+ solutionStream << "\t\t{" << dep << "} = {" << dep << "}\r\n";
|
|
|
}
|
|
|
solutionStream << "\tEndProjectSection\r\n";
|
|
|
}
|
|
|
@@ -447,20 +373,31 @@ protected:
|
|
|
|
|
|
solutionStream << "Global\r\n";
|
|
|
solutionStream << "\tGlobalSection(SolutionConfigurationPlatforms) = preSolution\r\n";
|
|
|
+
|
|
|
+ Poco::StringTokenizer archTok(templateProps.getString("project.architectures"), ";,", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
+ std::set<std::string> archs(archTok.begin(), archTok.end());
|
|
|
+
|
|
|
Poco::StringTokenizer configsTokenizer(projectConfig.getString("vc.project.configurations", ""), ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator itConf = configsTokenizer.begin(); itConf != configsTokenizer.end(); ++itConf)
|
|
|
+ for (const auto& arch: archs)
|
|
|
{
|
|
|
- solutionStream << "\t\t" << *itConf << "|" << projectPlatform << " = " << *itConf << "|" << projectPlatform << "\r\n";
|
|
|
+ for (const auto& conf: configsTokenizer)
|
|
|
+ {
|
|
|
+ solutionStream << "\t\t" << conf << "|" << arch << " = " << conf << "|" << arch << "\r\n";
|
|
|
+ }
|
|
|
}
|
|
|
solutionStream << "\tEndGlobalSection\r\n";
|
|
|
solutionStream << "\tGlobalSection(ProjectConfigurationPlatforms) = postSolution\r\n";
|
|
|
- for (std::vector<std::string>::const_iterator itDeps = dependencies.begin(); itDeps != dependencies.end(); ++itDeps)
|
|
|
+
|
|
|
+ for (const auto& dep: dependencies)
|
|
|
{
|
|
|
- for (Poco::StringTokenizer::Iterator itConf = configsTokenizer.begin(); itConf != configsTokenizer.end(); ++itConf)
|
|
|
+ for (const auto& arch: archs)
|
|
|
{
|
|
|
- solutionStream << "\t\t{" << *itDeps << "}." << *itConf << "|" << projectPlatform << ".ActiveCfg = " << *itConf << "|" << projectPlatform << "\r\n";
|
|
|
- solutionStream << "\t\t{" << *itDeps << "}." << *itConf << "|" << projectPlatform << ".Build.0 = " << *itConf << "|" << projectPlatform << "\r\n";
|
|
|
- solutionStream << "\t\t{" << *itDeps << "}." << *itConf << "|" << projectPlatform << ".Deploy.0 = " << *itConf << "|" << projectPlatform << "\r\n";
|
|
|
+ for (const auto& conf: configsTokenizer)
|
|
|
+ {
|
|
|
+ solutionStream << "\t\t{" << dep << "}." << conf << "|" << arch << ".ActiveCfg = " << conf << "|" << arch << "\r\n";
|
|
|
+ solutionStream << "\t\t{" << dep << "}." << conf << "|" << arch << ".Build.0 = " << conf << "|" << arch << "\r\n";
|
|
|
+ solutionStream << "\t\t{" << dep << "}." << conf << "|" << arch << ".Deploy.0 = " << conf << "|" << arch << "\r\n";
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
solutionStream << "\tEndGlobalSection\r\n";
|
|
|
@@ -474,16 +411,23 @@ protected:
|
|
|
{
|
|
|
std::set<std::string> validConfigs;
|
|
|
std::set<std::string> validConditions;
|
|
|
- for (std::set<std::string>::const_iterator it = configSet.begin(); it != configSet.end(); ++it)
|
|
|
+
|
|
|
+ Poco::StringTokenizer archTok(templateProps.getString("project.architectures"), ";,", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
+ std::set<std::string> archs(archTok.begin(), archTok.end());
|
|
|
+
|
|
|
+ for (const auto& arch: archs)
|
|
|
{
|
|
|
- std::string config(*it);
|
|
|
- config += "|";
|
|
|
- config += platform;
|
|
|
- std::string condition("'$(Configuration)|$(Platform)'=='");
|
|
|
- condition += config;
|
|
|
- condition += "'";
|
|
|
- validConfigs.insert(config);
|
|
|
- validConditions.insert(condition);
|
|
|
+ for (const auto& c: configSet)
|
|
|
+ {
|
|
|
+ std::string config = c;
|
|
|
+ config += "|";
|
|
|
+ config += arch;
|
|
|
+ std::string condition("'$(Configuration)|$(Platform)'=='");
|
|
|
+ condition += config;
|
|
|
+ condition += "'";
|
|
|
+ validConfigs.insert(config);
|
|
|
+ validConditions.insert(condition);
|
|
|
+ }
|
|
|
}
|
|
|
std::vector<Poco::XML::Element*> elementsToRemove;
|
|
|
Poco::AutoPtr<Poco::XML::NodeList> pProjectConfigurationList = pProjectDoc->getElementsByTagName("ProjectConfiguration");
|
|
|
@@ -524,27 +468,18 @@ protected:
|
|
|
if (pProjectFileVersionList->length() > 0)
|
|
|
{
|
|
|
Poco::XML::Element* pPropertyGroup = static_cast<Poco::XML::Element*>(pProjectFileVersionList->item(0)->parentNode());
|
|
|
- for (std::set<std::string>::const_iterator it = configSet.begin(); it != configSet.end(); ++it)
|
|
|
+ for (const auto& arch: archs)
|
|
|
{
|
|
|
- Poco::AutoPtr<Poco::XML::Element> pTargetName = pProjectDoc->createElement("TargetName");
|
|
|
- pTargetName->setAttribute("Condition", Poco::format("'$(Configuration)|$(Platform)'=='%s|%s'", *it, platform));
|
|
|
- std::string target = projectProps.getString("project.target");
|
|
|
- target += templateProps.getString(Poco::format("project.targetSuffix.%s", *it), "");
|
|
|
- Poco::AutoPtr<Poco::XML::Text> pText = pProjectDoc->createTextNode(target);
|
|
|
- pTargetName->appendChild(pText);
|
|
|
- pPropertyGroup->appendChild(pTargetName);
|
|
|
- }
|
|
|
- }
|
|
|
- if (platform == "x64")
|
|
|
- {
|
|
|
- Poco::AutoPtr<Poco::XML::NodeList> pLibs = pProjectDoc->getElementsByTagName("Lib");
|
|
|
- for (unsigned long i = 0; i < pLibs->length(); i++)
|
|
|
- {
|
|
|
- Poco::XML::Element* pLib = static_cast<Poco::XML::Element*>(pLibs->item(i));
|
|
|
- Poco::AutoPtr<Poco::XML::Element> pTargetMachine = pProjectDoc->createElement("TargetMachine");
|
|
|
- Poco::AutoPtr<Poco::XML::Text> pText = pProjectDoc->createTextNode("MachineX64");
|
|
|
- pTargetMachine->appendChild(pText);
|
|
|
- pLib->appendChild(pTargetMachine);
|
|
|
+ for (const auto& config: configSet)
|
|
|
+ {
|
|
|
+ Poco::AutoPtr<Poco::XML::Element> pTargetName = pProjectDoc->createElement("TargetName");
|
|
|
+ pTargetName->setAttribute("Condition", Poco::format("'$(Configuration)|$(Platform)'=='%s|%s'", config, arch));
|
|
|
+ std::string target = projectProps.getString("project.target");
|
|
|
+ target += templateProps.getString(Poco::format("project.targetSuffix.%s", config), "");
|
|
|
+ Poco::AutoPtr<Poco::XML::Text> pText = pProjectDoc->createTextNode(target);
|
|
|
+ pTargetName->appendChild(pText);
|
|
|
+ pPropertyGroup->appendChild(pTargetName);
|
|
|
+ }
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
@@ -637,6 +572,18 @@ protected:
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+ void fix2019Project(Poco::AutoPtr<Poco::XML::Document> pProjectDoc, const std::set<std::string>& configSet, const std::string& platform, const Poco::Util::AbstractConfiguration& projectProps, const Poco::Util::AbstractConfiguration& templateProps)
|
|
|
+ {
|
|
|
+ fix2010Project(pProjectDoc, configSet, platform, projectProps, templateProps);
|
|
|
+ Poco::AutoPtr<Poco::XML::NodeList> pConfigurationTypeList = pProjectDoc->getElementsByTagName("ConfigurationType");
|
|
|
+ for (unsigned long i = 0; i < pConfigurationTypeList->length(); i++)
|
|
|
+ {
|
|
|
+ Poco::XML::Element* pConfigurationTypeElem = static_cast<Poco::XML::Element*>(pConfigurationTypeList->item(i));
|
|
|
+ removeElement(pConfigurationTypeElem->parentNode(), "PlatformToolset");
|
|
|
+ appendElement(pConfigurationTypeElem->parentNode(), "PlatformToolset", "v142");
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
void appendElement(Poco::XML::Node* pParentNode, const std::string& elemName, const std::string& text)
|
|
|
{
|
|
|
Poco::AutoPtr<Poco::XML::Element> pElement = pParentNode->ownerDocument()->createElement(elemName);
|
|
|
@@ -679,6 +626,9 @@ protected:
|
|
|
|
|
|
if (projectConfig.hasProperty("vc.project.name"))
|
|
|
{
|
|
|
+ Poco::StringTokenizer archTok(pTemplateProps->getString("project.architectures"), ";,", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
+ std::set<std::string> archs(archTok.begin(), archTok.end());
|
|
|
+
|
|
|
Poco::Path prototypePath(projectPath);
|
|
|
prototypePath.setFileName(projectConfig.getString("vc.project.prototype"));
|
|
|
|
|
|
@@ -696,7 +646,6 @@ protected:
|
|
|
pProps->setString("project.outdir", projectConfig.getString("vc.project.outdir", "."));
|
|
|
pProps->setString("project.pocobase", projectConfig.getString("vc.project.pocobase", ".."));
|
|
|
pProps->setString("project.platform", pTemplateProps->getString("project.platform", platform));
|
|
|
- pProps->setString("project.targetArchitecture", pTemplateProps->getString("project.targetArchitecture", "IA32"));
|
|
|
pProps->setString("project.targetPlatform", pTemplateProps->getString("project.targetPlatform", "WINDOWS_NT"));
|
|
|
expandAttributes(pProjectDoc->documentElement(), *pProps);
|
|
|
|
|
|
@@ -704,7 +653,7 @@ protected:
|
|
|
if (!pFilesElement) throw Poco::NotFoundException("No Files element found in prototype document");
|
|
|
pFilesElement = pProjectDoc->importNode(pFilesElement, true);
|
|
|
|
|
|
- fixFileConfigurations(pFilesElement, projectConfig.getString("vc.project.configurations", ""), pTemplateProps->getString("project.platform", platform));
|
|
|
+ fixFileConfigurations(pFilesElement, projectConfig.getString("vc.project.configurations", ""), archs);
|
|
|
replaceFiles(pFilesElement, pTemplateProps->getString("project.replaceSourceFiles", ""));
|
|
|
|
|
|
Poco::XML::Node* pOldFilesElement = pProjectDoc->getNodeByPath("//Files");
|
|
|
@@ -717,64 +666,67 @@ protected:
|
|
|
|
|
|
std::set<std::string> configSet;
|
|
|
Poco::StringTokenizer configs(projectConfig.getString("vc.project.configurations", ""), ",;", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator it = configs.begin(); it != configs.end(); ++it)
|
|
|
+ for (const auto& arch: archs)
|
|
|
{
|
|
|
- std::string config = *it;
|
|
|
- configSet.insert(config);
|
|
|
- setProperty(*pProps, "configuration.compiler.includes", projectConfig, "vc.project.compiler.include", platform, config);
|
|
|
- setProperty(*pProps, "configuration.compiler.defines", projectConfig, "vc.project.compiler.defines", platform, config);
|
|
|
- setProperty(*pProps, "configuration.compiler.disableWarnings", projectConfig, "vc.project.compiler.disableWarnings", platform, config);
|
|
|
- setProperty(*pProps, "configuration.compiler.additionalOptions", projectConfig, "vc.project.compiler.additionalOptions", platform, config);
|
|
|
- setProperty(*pProps, "configuration.linker.dependencies", projectConfig, "vc.project.linker.dependencies", platform, config, " ");
|
|
|
- setProperty(*pProps, "configuration.linker.libraries", projectConfig, "vc.project.linker.libraries", platform, config);
|
|
|
- setProperty(*pProps, "configuration.linker.entry", projectConfig, "vc.project.linker.entry", platform, config);
|
|
|
- setProperty(*pProps, "configuration.linker.additionalOptions", projectConfig, "vc.project.linker.additionalOptions", platform, config);
|
|
|
- setProperty(*pProps, "configuration.prebuild", projectConfig, "vc.project.prebuild", platform, config);
|
|
|
- setProperty(*pProps, "configuration.postbuild", projectConfig, "vc.project.postbuild", platform, config);
|
|
|
- std::string libSuffix = this->config().getString("progen.libsuffix." + config, "");
|
|
|
- Poco::StringTokenizer rawDependencies(pProps->getString("configuration.linker.dependencies"), " ", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- std::string expandedDependencies;
|
|
|
- for (Poco::StringTokenizer::Iterator itd = rawDependencies.begin(); itd != rawDependencies.end(); ++itd)
|
|
|
+ pProps->setString("project.targetArchitecture", pTemplateProps->getString("project.targetArchitecture." + arch, "IA32"));
|
|
|
+ for (const auto& config: configs)
|
|
|
{
|
|
|
- std::string lib(*itd);
|
|
|
- if (lib.find('.') == std::string::npos)
|
|
|
+ configSet.insert(config);
|
|
|
+ setProperty(*pProps, "configuration.compiler.includes", projectConfig, "vc.project.compiler.include", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.compiler.defines", projectConfig, "vc.project.compiler.defines", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.compiler.disableWarnings", projectConfig, "vc.project.compiler.disableWarnings", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.compiler.additionalOptions", projectConfig, "vc.project.compiler.additionalOptions", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.linker.dependencies", projectConfig, "vc.project.linker.dependencies", platform, arch, config, " ");
|
|
|
+ setProperty(*pProps, "configuration.linker.libraries", projectConfig, "vc.project.linker.libraries", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.linker.entry", projectConfig, "vc.project.linker.entry", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.linker.additionalOptions", projectConfig, "vc.project.linker.additionalOptions", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.prebuild", projectConfig, "vc.project.prebuild", platform, arch, config);
|
|
|
+ setProperty(*pProps, "configuration.postbuild", projectConfig, "vc.project.postbuild", platform, arch, config);
|
|
|
+ std::string libSuffix = this->config().getString("progen.libsuffix." + config, "");
|
|
|
+ Poco::StringTokenizer rawDependencies(pProps->getString("configuration.linker.dependencies"), " ", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
+ std::string expandedDependencies;
|
|
|
+ for (Poco::StringTokenizer::Iterator itd = rawDependencies.begin(); itd != rawDependencies.end(); ++itd)
|
|
|
{
|
|
|
- lib += libSuffix;
|
|
|
+ std::string lib(*itd);
|
|
|
+ if (lib.find('.') == std::string::npos)
|
|
|
+ {
|
|
|
+ lib += libSuffix;
|
|
|
+ }
|
|
|
+ if (!expandedDependencies.empty()) expandedDependencies += ' ';
|
|
|
+ expandedDependencies += lib;
|
|
|
}
|
|
|
- if (!expandedDependencies.empty()) expandedDependencies += ' ';
|
|
|
- expandedDependencies += lib;
|
|
|
- }
|
|
|
- pProps->setString("configuration.linker.dependencies", expandedDependencies);
|
|
|
+ pProps->setString("configuration.linker.dependencies", expandedDependencies);
|
|
|
|
|
|
- Poco::Path configPath(templatePath);
|
|
|
- configPath.setBaseName(config);
|
|
|
- configPath.setExtension("template");
|
|
|
- Poco::AutoPtr<Poco::XML::Document> pConfigDoc = domParser.parse(configPath.toString());
|
|
|
- Poco::XML::Element* pConfigElem = pConfigDoc->documentElement();
|
|
|
+ Poco::Path configPath(templatePath);
|
|
|
+ configPath.setBaseName(config + "-" + arch);
|
|
|
+ configPath.setExtension("template");
|
|
|
+ Poco::AutoPtr<Poco::XML::Document> pConfigDoc = domParser.parse(configPath.toString());
|
|
|
+ Poco::XML::Element* pConfigElem = pConfigDoc->documentElement();
|
|
|
|
|
|
- std::string prebuild = pProps->getString("configuration.prebuild", "");
|
|
|
- if (!prebuild.empty())
|
|
|
- {
|
|
|
- Poco::XML::Node* pPreBuildNode = pConfigElem->getNodeByPath("Tool[@Name=VCPreBuildEventTool]");
|
|
|
- if (pPreBuildNode)
|
|
|
+ std::string prebuild = pProps->getString("configuration.prebuild", "");
|
|
|
+ if (!prebuild.empty())
|
|
|
{
|
|
|
- static_cast<Poco::XML::Element*>(pPreBuildNode)->setAttribute("CommandLine", prebuild);
|
|
|
+ Poco::XML::Node* pPreBuildNode = pConfigElem->getNodeByPath("Tool[@Name=VCPreBuildEventTool]");
|
|
|
+ if (pPreBuildNode)
|
|
|
+ {
|
|
|
+ static_cast<Poco::XML::Element*>(pPreBuildNode)->setAttribute("CommandLine", prebuild);
|
|
|
+ }
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- std::string postbuild = pProps->getString("configuration.postbuild", "");
|
|
|
- if (!postbuild.empty())
|
|
|
- {
|
|
|
- Poco::XML::Node* pPostBuildNode = pConfigElem->getNodeByPath("Tool[@Name=VCPostBuildEventTool]");
|
|
|
- if (pPostBuildNode)
|
|
|
+ std::string postbuild = pProps->getString("configuration.postbuild", "");
|
|
|
+ if (!postbuild.empty())
|
|
|
{
|
|
|
- static_cast<Poco::XML::Element*>(pPostBuildNode)->setAttribute("CommandLine", postbuild);
|
|
|
+ Poco::XML::Node* pPostBuildNode = pConfigElem->getNodeByPath("Tool[@Name=VCPostBuildEventTool]");
|
|
|
+ if (pPostBuildNode)
|
|
|
+ {
|
|
|
+ static_cast<Poco::XML::Element*>(pPostBuildNode)->setAttribute("CommandLine", postbuild);
|
|
|
+ }
|
|
|
}
|
|
|
- }
|
|
|
|
|
|
- expandAttributes(pConfigElem, *pProps);
|
|
|
- pConfigElem = static_cast<Poco::XML::Element*>(pProjectDoc->importNode(pConfigElem, true));
|
|
|
- pConfigurationsElement->appendChild(pConfigElem);
|
|
|
+ expandAttributes(pConfigElem, *pProps);
|
|
|
+ pConfigElem = static_cast<Poco::XML::Element*>(pProjectDoc->importNode(pConfigElem, true));
|
|
|
+ pConfigurationsElement->appendChild(pConfigElem);
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
std::string vcprojName = projectConfig.getString("vc.project.name");
|
|
|
@@ -814,12 +766,12 @@ protected:
|
|
|
{
|
|
|
Poco::Process::Args args;
|
|
|
Poco::StringTokenizer argsTokenizer(config().getString("progen.postprocess." + postprocess + ".args", ""), ";,", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator itArgs = argsTokenizer.begin(); itArgs != argsTokenizer.end(); ++itArgs)
|
|
|
+ for (const auto& arg: argsTokenizer)
|
|
|
{
|
|
|
- if (*itArgs == "%")
|
|
|
+ if (arg == "%")
|
|
|
args.push_back("\"" + vcprojPath.toString() + "\"");
|
|
|
else
|
|
|
- args.push_back(*itArgs);
|
|
|
+ args.push_back(arg);
|
|
|
}
|
|
|
Poco::Path vcxprojPath(vcprojPath);
|
|
|
vcxprojPath.setExtension("vcxproj");
|
|
|
@@ -900,16 +852,26 @@ protected:
|
|
|
writeProject(pProjectDoc, vcxprojPath.toString());
|
|
|
}
|
|
|
}
|
|
|
+ if (config().getBool("progen.postprocess." + postprocess + ".fix2019ProjectFile", false))
|
|
|
+ {
|
|
|
+ if (projectFile.exists())
|
|
|
+ {
|
|
|
+ logger().information("Fixing Visual Studio 2019 project file: " + vcxprojPath.toString());
|
|
|
+ Poco::AutoPtr<Poco::XML::Document> pProjectDoc = domParser.parse(vcxprojPath.toString());
|
|
|
+ fix2019Project(pProjectDoc, configSet, pTemplateProps->getString("project.platform", platform), *pProps, *pTemplateProps);
|
|
|
+ writeProject(pProjectDoc, vcxprojPath.toString());
|
|
|
+ }
|
|
|
+ }
|
|
|
if (config().getBool("progen.postprocess." + postprocess + ".deleteOriginalFile", false))
|
|
|
{
|
|
|
Poco::File projectFile(vcprojPath.toString());
|
|
|
projectFile.remove();
|
|
|
}
|
|
|
Poco::StringTokenizer filesTokenizer(config().getString("progen.postprocess." + postprocess + ".deleteFiles", ""), ";,", Poco::StringTokenizer::TOK_TRIM | Poco::StringTokenizer::TOK_IGNORE_EMPTY);
|
|
|
- for (Poco::StringTokenizer::Iterator itFiles = filesTokenizer.begin(); itFiles != filesTokenizer.end(); ++itFiles)
|
|
|
+ for (const auto& file: filesTokenizer)
|
|
|
{
|
|
|
Poco::Path p(vcprojPath);
|
|
|
- p.setFileName(*itFiles);
|
|
|
+ p.setFileName(file);
|
|
|
Poco::File f(p.toString());
|
|
|
if (f.exists())
|
|
|
{
|
|
|
@@ -961,14 +923,12 @@ protected:
|
|
|
std::vector<std::string> tools;
|
|
|
templateDir.list(tools);
|
|
|
|
|
|
- for (std::vector<std::string>::const_iterator itTools = tools.begin(); itTools != tools.end(); ++itTools)
|
|
|
+ for (const auto& tool: tools)
|
|
|
{
|
|
|
- const std::string& tool = *itTools;
|
|
|
if (_tools.empty() || _tools.find(tool) != _tools.end())
|
|
|
{
|
|
|
- for (Poco::StringTokenizer::Iterator itPlatforms = platforms.begin(); itPlatforms != platforms.end(); ++itPlatforms)
|
|
|
+ for (const auto& platform: platforms)
|
|
|
{
|
|
|
- const std::string& platform = *itPlatforms;
|
|
|
if (_platforms.empty() || _platforms.find(platform) != _platforms.end())
|
|
|
{
|
|
|
std::string projectType = pProjectConfig->getString("vc.project.type", "executable");
|
|
|
@@ -976,17 +936,6 @@ protected:
|
|
|
templatePath.pushDirectory(tool);
|
|
|
templatePath.pushDirectory(platform);
|
|
|
templatePath.pushDirectory(projectType);
|
|
|
- if ((platform == "Win32") || (platform == "WinCE"))
|
|
|
- {
|
|
|
- pProjectConfig->setString("vc.project.platform.bits", "32");
|
|
|
- pProjectConfig->setString("vc.project.platform.bindir.suffix", "");
|
|
|
- }
|
|
|
- else if (platform == "x64")
|
|
|
- {
|
|
|
- pProjectConfig->setString("vc.project.platform.bits", "64");
|
|
|
- pProjectConfig->setString("vc.project.platform.bindir.suffix", "64");
|
|
|
- }
|
|
|
- else throw Poco::NotFoundException(Poco::format("Unknown platform: %s", platform));
|
|
|
generateProject(*pProjectConfig, projectPath, templatePath, platform, tool);
|
|
|
}
|
|
|
}
|
|
|
@@ -1014,6 +963,7 @@ private:
|
|
|
bool _helpRequested;
|
|
|
std::string _outputDir;
|
|
|
std::set<std::string> _platforms;
|
|
|
+ std::set<std::string> _architectures;
|
|
|
std::set<std::string> _tools;
|
|
|
};
|
|
|
|