diff --git a/plugins/custom-definesandincludes/compilerprovider/compilerprovider.cpp b/plugins/custom-definesandincludes/compilerprovider/compilerprovider.cpp --- a/plugins/custom-definesandincludes/compilerprovider/compilerprovider.cpp +++ b/plugins/custom-definesandincludes/compilerprovider/compilerprovider.cpp @@ -143,8 +143,7 @@ return {}; } - return config.compiler->defines(languageType, - languageType == Utils::C ? config.parserArguments.cArguments : config.parserArguments.cppArguments); + return config.compiler->defines(languageType, config.parserArguments[languageType]); } Path::List CompilerProvider::includes( ProjectBaseItem* item ) const @@ -159,8 +158,7 @@ return {}; } - return config.compiler->includes(languageType, - languageType == Utils::C ? config.parserArguments.cArguments : config.parserArguments.cppArguments); + return config.compiler->includes(languageType, config.parserArguments[languageType]); } Path::List CompilerProvider::frameworkDirectories( ProjectBaseItem* /* item */ ) const diff --git a/plugins/custom-definesandincludes/compilerprovider/icompiler.h b/plugins/custom-definesandincludes/compilerprovider/icompiler.h --- a/plugins/custom-definesandincludes/compilerprovider/icompiler.h +++ b/plugins/custom-definesandincludes/compilerprovider/icompiler.h @@ -39,7 +39,7 @@ Cuda, ObjC, - Other = 100 + Other }; } diff --git a/plugins/custom-definesandincludes/compilerprovider/settingsmanager.h b/plugins/custom-definesandincludes/compilerprovider/settingsmanager.h --- a/plugins/custom-definesandincludes/compilerprovider/settingsmanager.h +++ b/plugins/custom-definesandincludes/compilerprovider/settingsmanager.h @@ -38,10 +38,26 @@ struct ParserArguments { - QString cArguments; - QString cppArguments; - QString openClArguments; - QString cudaArguments; +public: + const QString& operator[](Utils::LanguageType languageType) const + { + Q_ASSERT(languageType >= Utils::C && languageType < Utils::Other); + return arguments[languageType]; + } + + QString& operator[](Utils::LanguageType languageType) + { + Q_ASSERT(languageType >= Utils::C && languageType < Utils::Other); + return arguments[languageType]; + } + + /// Is any of the arguments empty? + bool isAnyEmpty() const; + +private: + QString arguments[Utils::Other]; + +public: bool parseAmbiguousAsCPP; }; diff --git a/plugins/custom-definesandincludes/compilerprovider/settingsmanager.cpp b/plugins/custom-definesandincludes/compilerprovider/settingsmanager.cpp --- a/plugins/custom-definesandincludes/compilerprovider/settingsmanager.cpp +++ b/plugins/custom-definesandincludes/compilerprovider/settingsmanager.cpp @@ -34,11 +34,16 @@ #include #include +#include + #include "compilerprovider.h" using namespace KDevelop; namespace { +constexpr Utils::LanguageType configurableLanguageTypes[] = + { Utils::C, Utils::Cpp, Utils::OpenCl, Utils::Cuda }; + namespace ConfigConstants { const QString configKey = QStringLiteral( "CustomDefinesAndIncludes" ); const QString definesKey = QStringLiteral( "Defines" ); @@ -54,14 +59,22 @@ const QString compilerPathKey = QStringLiteral( "Path" ); const QString compilerTypeKey = QStringLiteral( "Type" ); -QString parserArgumentsCPP() -{ - return QStringLiteral("parserArguments"); -} - -QString parserArgumentsC() +QString parserArgumentsKey(Utils::LanguageType languageType) { - return QStringLiteral("parserArgumentsC"); + switch (languageType) { + case Utils::C: + return QStringLiteral("parserArgumentsC"); + case Utils::Cpp: + return QStringLiteral("parserArguments"); + case Utils::OpenCl: + return QStringLiteral("parserArgumentsOpenCL"); + case Utils::Cuda: + return QStringLiteral("parserArgumentsCuda"); + case Utils::ObjC: + case Utils::Other: + break; + } + Q_UNREACHABLE(); } QString parseAmbiguousAsCPP() @@ -78,16 +91,22 @@ return list; } -ParserArguments defaultArguments() +ParserArguments createDefaultArguments() { - const static ParserArguments arguments{ - QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c99"), - QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c++11"), - QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=CL1.1"), - QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c++11"), - true - }; + ParserArguments arguments; + arguments[Utils::C] = QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c99"); + arguments[Utils::Cpp] = QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c++11"); + arguments[Utils::OpenCl] = QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -cl-std=CL1.1"); + arguments[Utils::Cuda] = QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c++11"); + arguments[Utils::ObjC] = QStringLiteral("-ferror-limit=100 -fspell-checking -Wdocumentation -Wunused-parameter -Wunreachable-code -Wall -std=c99"); + arguments.parseAmbiguousAsCPP = true; + + return arguments; +} +const ParserArguments& defaultArguments() +{ + static ParserArguments arguments = createDefaultArguments(); return arguments; } @@ -124,8 +143,9 @@ for ( const auto& path : paths ) { KConfigGroup pathgrp = grp.group( ConfigConstants::projectPathPrefix + QString::number( pathIndex++ ) ); pathgrp.writeEntry(ConfigConstants::projectPathKey, path.path); - pathgrp.writeEntry(ConfigConstants::parserArgumentsCPP(), path.parserArguments.cppArguments); - pathgrp.writeEntry(ConfigConstants::parserArgumentsC(), path.parserArguments.cArguments); + for (auto type : configurableLanguageTypes) { + pathgrp.writeEntry(ConfigConstants::parserArgumentsKey(type), path.parserArguments[type]); + } pathgrp.writeEntry(ConfigConstants::parseAmbiguousAsCPP(), path.parserArguments.parseAmbiguousAsCPP); { @@ -158,16 +178,15 @@ ConfigEntry path; path.path = pathgrp.readEntry( ConfigConstants::projectPathKey, "" ); - path.parserArguments.cppArguments = pathgrp.readEntry(ConfigConstants::parserArgumentsCPP(), defaultArguments().cppArguments); - path.parserArguments.cArguments = pathgrp.readEntry(ConfigConstants::parserArgumentsC(), defaultArguments().cArguments); - path.parserArguments.parseAmbiguousAsCPP = pathgrp.readEntry(ConfigConstants::parseAmbiguousAsCPP(), defaultArguments().parseAmbiguousAsCPP); - - if (path.parserArguments.cppArguments.isEmpty()) { - path.parserArguments.cppArguments = defaultArguments().cppArguments; + for (auto type : configurableLanguageTypes) { + path.parserArguments[type] = pathgrp.readEntry(ConfigConstants::parserArgumentsKey(type), defaultArguments()[type]); } + path.parserArguments.parseAmbiguousAsCPP = pathgrp.readEntry(ConfigConstants::parseAmbiguousAsCPP(), defaultArguments().parseAmbiguousAsCPP); - if (path.parserArguments.cArguments.isEmpty()) { - path.parserArguments.cArguments = defaultArguments().cArguments; + for (auto type : configurableLanguageTypes) { + if (path.parserArguments[type].isEmpty()) { + path.parserArguments[type] = defaultArguments()[type]; + } } { // defines @@ -223,8 +242,7 @@ pathgrp.deleteGroup(); } - Q_ASSERT(!path.parserArguments.cppArguments.isEmpty()); - Q_ASSERT(!path.parserArguments.cArguments.isEmpty()); + Q_ASSERT(!path.parserArguments.isAnyEmpty()); paths << path; } @@ -429,3 +447,10 @@ return Other; } } + +bool ParserArguments::isAnyEmpty() const +{ + return std::any_of(std::begin(arguments), std::end(arguments), + [](const QString& args) { return args.isEmpty(); } + ); +} diff --git a/plugins/custom-definesandincludes/definesandincludesmanager.cpp b/plugins/custom-definesandincludes/definesandincludesmanager.cpp --- a/plugins/custom-definesandincludes/definesandincludesmanager.cpp +++ b/plugins/custom-definesandincludes/definesandincludesmanager.cpp @@ -81,8 +81,7 @@ } ret.includes.removeDuplicates(); - Q_ASSERT(!ret.parserArguments.cppArguments.isEmpty()); - Q_ASSERT(!ret.parserArguments.cArguments.isEmpty()); + Q_ASSERT(!ret.parserArguments.isAnyEmpty()); return ret; } @@ -102,22 +101,10 @@ QString argumentsForPath(const Path& path, const ParserArguments& arguments) { auto languageType = Utils::languageType(path, arguments.parseAmbiguousAsCPP); - switch (languageType) { - case Utils::C: - return arguments.cArguments; - case Utils::Cpp: - return arguments.cppArguments; - case Utils::OpenCl: - return arguments.openClArguments; - case Utils::Cuda: - return arguments.cudaArguments; - case Utils::ObjC: - return QString(); - case Utils::Other: - return QString(); - } - Q_UNREACHABLE(); - return QString(); + if (languageType != Utils::Other) + return arguments[languageType]; + else + return {}; } } diff --git a/plugins/custom-definesandincludes/kcm_widget/parserwidget.cpp b/plugins/custom-definesandincludes/kcm_widget/parserwidget.cpp --- a/plugins/custom-definesandincludes/kcm_widget/parserwidget.cpp +++ b/plugins/custom-definesandincludes/kcm_widget/parserwidget.cpp @@ -44,16 +44,35 @@ return arguments.mid(idx, end - idx); } -bool isCustomParserArguments(const QString& arguments, const QStringList& standards) +QString languageDefaultStandard(Utils::LanguageType languageType) +{ + switch (languageType) { + case Utils::C: + return QLatin1String("c99"); + case Utils::Cpp: + return QLatin1String("c++11"); + case Utils::OpenCl: + return QLatin1String("CL1.1"); + case Utils::Cuda: + return QLatin1String("c++11"); + case Utils::ObjC: + return QLatin1String("c99"); + case Utils::Other: + break; + } + Q_UNREACHABLE(); +} + +bool isCustomParserArguments(Utils::LanguageType languageType, const QString& arguments, const QStringList& standards) { const auto defaultArguments = SettingsManager::globalInstance()->defaultParserArguments(); auto standard = languageStandard(arguments); auto tmpArgs(arguments); - tmpArgs.replace(standard, QLatin1String("c++11")); + tmpArgs.replace(standard, languageDefaultStandard(languageType)); - if (tmpArgs == defaultArguments.cppArguments && standards.contains(standard)) { + if (tmpArgs == defaultArguments[languageType] && standards.contains(standard)) { return false; } @@ -96,9 +115,9 @@ void ParserWidget::languageStandardChangedC(const QString& standard) { if (m_ui->languageStandardsC->currentIndex() == customProfileIdx) { - m_ui->parserOptionsC->setText(SettingsManager::globalInstance()->defaultParserArguments().cArguments); + m_ui->parserOptionsC->setText(SettingsManager::globalInstance()->defaultParserArguments()[Utils::C]); } else { - auto text = SettingsManager::globalInstance()->defaultParserArguments().cArguments; + auto text = SettingsManager::globalInstance()->defaultParserArguments()[Utils::C]; auto currentStandard = languageStandard(text); m_ui->parserOptionsC->setText(text.replace(currentStandard, standard)); } @@ -110,9 +129,9 @@ void ParserWidget::languageStandardChangedCpp(const QString& standard) { if (m_ui->languageStandardsCpp->currentIndex() == customProfileIdx) { - m_ui->parserOptionsCpp->setText(SettingsManager::globalInstance()->defaultParserArguments().cppArguments); + m_ui->parserOptionsCpp->setText(SettingsManager::globalInstance()->defaultParserArguments()[Utils::Cpp]); } else { - auto text = SettingsManager::globalInstance()->defaultParserArguments().cppArguments; + auto text = SettingsManager::globalInstance()->defaultParserArguments()[Utils::Cpp]; auto currentStandard = languageStandard(text); m_ui->parserOptionsCpp->setText(text.replace(currentStandard, standard)); } @@ -124,9 +143,9 @@ void ParserWidget::languageStandardChangedOpenCl(const QString& standard) { if (m_ui->languageStandardsOpenCl->currentIndex() == customProfileIdx) { - m_ui->parserOptionsOpenCl->setText(SettingsManager::globalInstance()->defaultParserArguments().openClArguments); + m_ui->parserOptionsOpenCl->setText(SettingsManager::globalInstance()->defaultParserArguments()[Utils::OpenCl]); } else { - auto text = SettingsManager::globalInstance()->defaultParserArguments().openClArguments; + auto text = SettingsManager::globalInstance()->defaultParserArguments()[Utils::OpenCl]; auto currentStandard = languageStandard(text); m_ui->parserOptionsOpenCl->setText(text.replace(currentStandard, standard)); } @@ -138,9 +157,9 @@ void ParserWidget::languageStandardChangedCuda(const QString& standard) { if (m_ui->languageStandardsCuda->currentIndex() == customProfileIdx) { - m_ui->parserOptionsCuda->setText(SettingsManager::globalInstance()->defaultParserArguments().cudaArguments); + m_ui->parserOptionsCuda->setText(SettingsManager::globalInstance()->defaultParserArguments()[Utils::Cuda]); } else { - auto text = SettingsManager::globalInstance()->defaultParserArguments().cudaArguments; + auto text = SettingsManager::globalInstance()->defaultParserArguments()[Utils::Cuda]; auto currentStandard = languageStandard(text); m_ui->parserOptionsCuda->setText(text.replace(currentStandard, standard)); } @@ -151,42 +170,43 @@ void ParserWidget::setParserArguments(const ParserArguments& arguments) { - auto setArguments = [](QComboBox* languageStandards, QLineEdit* parserOptions, const QString& arguments) { + auto setArguments = [arguments](QComboBox* languageStandards, QLineEdit* parserOptions, Utils::LanguageType languageType) { QStringList standards; const int languageStandardsCount = languageStandards->count(); standards.reserve(languageStandardsCount-1); for (int i = 1; i < languageStandardsCount; ++i) { standards << languageStandards->itemText(i); } - if (isCustomParserArguments(arguments, standards)) { + const QString& arg = arguments[languageType]; + if (isCustomParserArguments(languageType, arg, standards)) { languageStandards->setCurrentIndex(customProfileIdx); } else { - languageStandards->setCurrentText(languageStandard(arguments)); + languageStandards->setCurrentText(languageStandard(arg)); } - parserOptions->setText(arguments); + parserOptions->setText(arg); }; - setArguments(m_ui->languageStandardsCpp, m_ui->parserOptionsCpp, arguments.cppArguments); - setArguments(m_ui->languageStandardsC, m_ui->parserOptionsC, arguments.cArguments); - setArguments(m_ui->languageStandardsOpenCl, m_ui->parserOptionsOpenCl, arguments.openClArguments); - setArguments(m_ui->languageStandardsCuda, m_ui->parserOptionsCuda, arguments.cudaArguments); + setArguments(m_ui->languageStandardsCpp, m_ui->parserOptionsCpp, Utils::Cpp); + setArguments(m_ui->languageStandardsC, m_ui->parserOptionsC, Utils::C); + setArguments(m_ui->languageStandardsOpenCl, m_ui->parserOptionsOpenCl, Utils::OpenCl); + setArguments(m_ui->languageStandardsCuda, m_ui->parserOptionsCuda, Utils::Cuda); m_ui->parseHeadersInPlainC->setChecked(!arguments.parseAmbiguousAsCPP); updateEnablements(); } ParserArguments ParserWidget::parserArguments() const { - return { - m_ui->parserOptionsC->text(), - m_ui->parserOptionsCpp->text(), - m_ui->parserOptionsOpenCl->text(), - m_ui->parserOptionsCuda->text(), - !m_ui->parseHeadersInPlainC->isChecked() - }; + ParserArguments arguments; + arguments[Utils::C] = m_ui->parserOptionsC->text(); + arguments[Utils::Cpp] = m_ui->parserOptionsCpp->text(); + arguments[Utils::OpenCl] = m_ui->parserOptionsOpenCl->text(); + arguments[Utils::Cuda] = m_ui->parserOptionsCuda->text(); + arguments.parseAmbiguousAsCPP = !m_ui->parseHeadersInPlainC->isChecked(); + return arguments; } void ParserWidget::updateEnablements() diff --git a/plugins/custom-definesandincludes/kcm_widget/projectpathsmodel.cpp b/plugins/custom-definesandincludes/kcm_widget/projectpathsmodel.cpp --- a/plugins/custom-definesandincludes/kcm_widget/projectpathsmodel.cpp +++ b/plugins/custom-definesandincludes/kcm_widget/projectpathsmodel.cpp @@ -196,8 +196,7 @@ void ProjectPathsModel::addPathInternal( const ConfigEntry& config, bool prepend ) { - Q_ASSERT(!config.parserArguments.cppArguments.isEmpty()); - Q_ASSERT(!config.parserArguments.cArguments.isEmpty()); + Q_ASSERT(!config.parserArguments.isAnyEmpty()); // Do not allow duplicates foreach( const ConfigEntry& existingConfig, projectPaths ) {