Skip to content

Commit 60d9d14

Browse files
committed
Add suport for Visual Studio 2026 slnx importing.
1 parent 1964001 commit 60d9d14

5 files changed

Lines changed: 63 additions & 6 deletions

File tree

cli/cmdlineparser.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1184,7 +1184,7 @@ CmdLineParser::Result CmdLineParser::parseFromArgs(int argc, const char* const a
11841184
}
11851185
if (projectType == ImportProject::Type::COMPILE_DB)
11861186
mSettings.maxConfigsProject = 1;
1187-
if (projectType == ImportProject::Type::VS_SLN || projectType == ImportProject::Type::VS_VCXPROJ) {
1187+
if (projectType == ImportProject::Type::VS_SLN || projectType == ImportProject::Type::VS_SLNX || projectType == ImportProject::Type::VS_VCXPROJ) {
11881188
mSettings.libraries.emplace_back("windows");
11891189
}
11901190
for (const auto &error : project.errors)
@@ -1210,7 +1210,7 @@ CmdLineParser::Result CmdLineParser::parseFromArgs(int argc, const char* const a
12101210
mLogger.printError("--project-configuration parameter is empty.");
12111211
return Result::Fail;
12121212
}
1213-
if (projectType != ImportProject::Type::VS_SLN && projectType != ImportProject::Type::VS_VCXPROJ) {
1213+
if (projectType != ImportProject::Type::VS_SLN && projectType != ImportProject::Type::VS_SLN && projectType != ImportProject::Type::VS_VCXPROJ) {
12141214
mLogger.printError("--project-configuration has no effect - no Visual Studio project provided.");
12151215
return Result::Fail;
12161216
}
@@ -1645,7 +1645,7 @@ CmdLineParser::Result CmdLineParser::parseFromArgs(int argc, const char* const a
16451645
mSettings.platform.defaultSign = defaultSign;
16461646

16471647
if (!mSettings.analyzeAllVsConfigs) {
1648-
if (projectType != ImportProject::Type::VS_SLN && projectType != ImportProject::Type::VS_VCXPROJ) {
1648+
if (projectType != ImportProject::Type::VS_SLN && projectType != ImportProject::Type::VS_SLNX && projectType != ImportProject::Type::VS_VCXPROJ) {
16491649
if (mAnalyzeAllVsConfigsSetOnCmdLine) {
16501650
mLogger.printError("--no-analyze-all-vs-configs has no effect - no Visual Studio project provided.");
16511651
return Result::Fail;

gui/mainwindow.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1969,6 +1969,7 @@ void MainWindow::analyzeProject(const ProjectFile *projectFile, const QStringLis
19691969
switch (result) {
19701970
case ImportProject::Type::COMPILE_DB:
19711971
case ImportProject::Type::VS_SLN:
1972+
case ImportProject::Type::VS_SLNX:
19721973
case ImportProject::Type::VS_VCXPROJ:
19731974
case ImportProject::Type::BORLAND:
19741975
case ImportProject::Type::CPPCHECK_GUI:

gui/projectfiledialog.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -112,7 +112,7 @@ static std::string suppressionAsText(const SuppressionList::Suppression& s)
112112

113113
QStringList ProjectFileDialog::getProjectConfigs(const QString &fileName)
114114
{
115-
if (!fileName.endsWith(".sln") && !fileName.endsWith(".vcxproj"))
115+
if (!fileName.endsWith(".sln") && !fileName.endsWith(".slnx") && !fileName.endsWith(".vcxproj"))
116116
return QStringList();
117117
QStringList ret;
118118
ImportProject importer;
@@ -612,7 +612,7 @@ void ProjectFileDialog::updatePathsAndDefines()
612612
{
613613
const QString &fileName = mUI->mEditImportProject->text();
614614
const bool importProject = !fileName.isEmpty();
615-
const bool hasConfigs = fileName.endsWith(".sln") || fileName.endsWith(".vcxproj");
615+
const bool hasConfigs = fileName.endsWith(".sln") || fileName.endsWith(".slnx") || fileName.endsWith(".vcxproj");
616616
mUI->mBtnClearImportProject->setEnabled(importProject);
617617
mUI->mListCheckPaths->setEnabled(!importProject);
618618
mUI->mListIncludeDirs->setEnabled(!importProject);
@@ -642,7 +642,7 @@ void ProjectFileDialog::browseImportProject()
642642
const QFileInfo inf(mProjectFile->getFilename());
643643
const QDir &dir = inf.absoluteDir();
644644
QMap<QString,QString> filters;
645-
filters[tr("Visual Studio")] = "*.sln *.vcxproj";
645+
filters[tr("Visual Studio")] = "*.sln *.slnx *.vcxproj";
646646
filters[tr("Compile database")] = "compile_commands.json";
647647
filters[tr("Borland C++ Builder 6")] = "*.bpr";
648648
QString fileName = QFileDialog::getOpenFileName(this, tr("Import Project"),

lib/importproject.cpp

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -187,6 +187,12 @@ ImportProject::Type ImportProject::import(const std::string &filename, Settings
187187
setRelativePaths(filename);
188188
return ImportProject::Type::VS_SLN;
189189
}
190+
}
191+
else if (endsWith(filename, ".slnx")) {
192+
if (importSlnx(filename, fileFilters)) {
193+
setRelativePaths(filename);
194+
return ImportProject::Type::VS_SLNX;
195+
}
190196
} else if (endsWith(filename, ".vcxproj")) {
191197
std::map<std::string, std::string, cppcheck::stricmp> variables;
192198
std::vector<SharedItemsProject> sharedItemsProjects;
@@ -488,6 +494,54 @@ bool ImportProject::importSln(std::istream &istr, const std::string &path, const
488494
return true;
489495
}
490496

497+
bool ImportProject::importSlnx(const std::string& filename, const std::vector<std::string>& fileFilters)
498+
{
499+
tinyxml2::XMLDocument doc;
500+
const tinyxml2::XMLError error = doc.LoadFile(filename.c_str());
501+
if (error != tinyxml2::XML_SUCCESS) {
502+
errors.emplace_back(std::string("Visual Studio project file is not a valid XML - ") + tinyxml2::XMLDocument::ErrorIDToName(error));
503+
return false;
504+
}
505+
506+
const tinyxml2::XMLElement* const rootnode = doc.FirstChildElement();
507+
if (rootnode == nullptr) {
508+
errors.emplace_back("Visual Studio project file has no XML root node");
509+
return false;
510+
}
511+
512+
std::map<std::string, std::string, cppcheck::stricmp> variables;
513+
variables["SolutionDir"] = Path::simplifyPath(Path::getPathFromFilename(filename));
514+
515+
bool found = false;
516+
std::vector<SharedItemsProject> sharedItemsProjects;
517+
518+
for (const tinyxml2::XMLElement* node = rootnode->FirstChildElement(); node; node = node->NextSiblingElement()) {
519+
const char* name = node->Name();
520+
if (std::strcmp(name, "Project") == 0) {
521+
const char* labelAttribute = node->Attribute("Path");
522+
if (labelAttribute) {
523+
std::string vcxproj(labelAttribute);
524+
vcxproj = Path::toNativeSeparators(std::move(vcxproj));
525+
if (!Path::isAbsolute(vcxproj))
526+
vcxproj = variables["SolutionDir"] + vcxproj;
527+
vcxproj = Path::fromNativeSeparators(std::move(vcxproj));
528+
if (!importVcxproj(vcxproj, variables, "", fileFilters, sharedItemsProjects)) {
529+
errors.emplace_back("failed to load '" + vcxproj + "' from Visual Studio solution");
530+
return false;
531+
}
532+
found = true;
533+
}
534+
}
535+
}
536+
537+
if (!found) {
538+
errors.emplace_back("no projects found in Visual Studio solution file");
539+
return false;
540+
}
541+
542+
return true;
543+
}
544+
491545
namespace {
492546
struct ProjectConfiguration {
493547
explicit ProjectConfiguration(const tinyxml2::XMLElement *cfg) {

lib/importproject.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ class CPPCHECKLIB WARN_UNUSED ImportProject {
6464
FAILURE,
6565
COMPILE_DB,
6666
VS_SLN,
67+
VS_SLNX,
6768
VS_VCXPROJ,
6869
BORLAND,
6970
CPPCHECK_GUI
@@ -113,6 +114,7 @@ class CPPCHECKLIB WARN_UNUSED ImportProject {
113114
};
114115

115116
bool importSln(std::istream &istr, const std::string &path, const std::vector<std::string> &fileFilters);
117+
bool importSlnx(const std::string& filename, const std::vector<std::string>& fileFilters);
116118
SharedItemsProject importVcxitems(const std::string &filename, const std::vector<std::string> &fileFilters, std::vector<SharedItemsProject> &cache);
117119
bool importVcxproj(const std::string &filename, std::map<std::string, std::string, cppcheck::stricmp> &variables, const std::string &additionalIncludeDirectories, const std::vector<std::string> &fileFilters, std::vector<SharedItemsProject> &cache);
118120
bool importVcxproj(const std::string &filename, const tinyxml2::XMLDocument &doc, std::map<std::string, std::string, cppcheck::stricmp> &variables, const std::string &additionalIncludeDirectories, const std::vector<std::string> &fileFilters, std::vector<SharedItemsProject> &cache);

0 commit comments

Comments
 (0)