diff options
Diffstat (limited to 'lib/configuration/configuration.cpp')
-rw-r--r-- | lib/configuration/configuration.cpp | 101 |
1 files changed, 67 insertions, 34 deletions
diff --git a/lib/configuration/configuration.cpp b/lib/configuration/configuration.cpp index 01a5080..75f863c 100644 --- a/lib/configuration/configuration.cpp +++ b/lib/configuration/configuration.cpp @@ -7,21 +7,17 @@ */ #include "configuration.h" -#include <QStandardPaths> #include <algorithm> #include <fstream> #include <iostream> #include <sstream> #include <stdexcept> -static std::unique_ptr<Configuration> s_conf; - -inline void strip(std::string &value) -{ - value.erase(value.begin(), std::find_if(value.begin(), value.end(), std::bind1st(std::not_equal_to<char>(), ' '))); +#ifndef NO_QT_SPEC +#include <QStandardPaths> +#endif - value.erase(std::find_if(value.rbegin(), value.rend(), std::bind1st(std::not_equal_to<char>(), ' ')).base(), value.end()); -} +static std::unique_ptr<Configuration> s_conf; Configuration::Configuration() : use_global(true) @@ -32,7 +28,9 @@ Configuration::Configuration() } Configuration::Configuration(std::initializer_list<std::pair<std::string, conf_value_t>> l) noexcept +#ifndef NO_QT_SPEC : m_homePath(QStandardPaths::writableLocation(QStandardPaths::HomeLocation).toStdString()) +#endif { for(const auto &i : l) { insert_or_assign(i.first, i.second); @@ -48,10 +46,61 @@ void Configuration::read_file(const std::string &location) } } +inline auto strip(std::string &value) +{ + value.erase(value.begin(), std::find_if(value.begin(), value.end(), std::bind1st(std::not_equal_to<char>(), ' '))); + value.erase(std::find_if(value.rbegin(), value.rend(), std::bind1st(std::not_equal_to<char>(), ' ')).base(), value.end()); + return value; +} + +inline auto parse(const std::string &line, std::string §ion) +{ + struct { + bool pair = false; + std::string key; + std::string value; + } ret; + + if(line[0] == '#' || line.length() == 0) { + return ret; + } + + if(line.front() == '[' && line.back() == ']') { + section = line.substr(1, line.length() - 2) + '/'; + return ret; + } + + const auto pos = line.find_first_of('='); + if(pos == std::string::npos) { + return ret; + } + + ret.key = line.substr(0, pos); + strip(ret.key); + if(ret.key.empty()) { + return ret; + } + ret.key = section + ret.key; + + ret.value = line.substr(pos + 1); + strip(ret.value); + + ret.pair = true; + return ret; +} + +#ifdef FUZZER +extern "C" int LLVMFuzzerTestOneInput(const char *Data, long long Size) +{ + std::string section; + parse(std::string(Data, Size), section); + return 0; +} +#endif + void Configuration::read(std::basic_istream<char> &input) { - std::string line, section, key, value; - std::istringstream is_line; + std::string line, section; while(std::getline(input, line)) { if(line.rfind("@@") == 0) { @@ -60,39 +109,23 @@ void Configuration::read(std::basic_istream<char> &input) } continue; } - if(line[0] == '#' || line.length() == 0) { - continue; - } - - if(line.front() == '[' && line.back() == ']') { - section = line.substr(1, line.length() - 2) + '/'; - continue; - } - - is_line.clear(); - is_line.str(line); - - const auto pos = line.find_first_of('='); - if(pos != std::string::npos) { - key = section + line.substr(0, pos); - value = line.substr(pos + 1); - strip(key); - strip(value); + const auto pair = parse(line, section); + if(pair.pair) { - if(this->count(key) == 0) { + if(this->count(pair.key) == 0) { // no type has been specified for this key, assuming std::string - insert(std::make_pair(key, value)); + insert(std::make_pair(pair.key, pair.value)); continue; } - auto v = at(key); + auto v = at(pair.key); if(std::holds_alternative<std::string>(v)) { - at(key) = value; + at(pair.key) = pair.value; } else if(std::holds_alternative<int>(v)) { - at(key) = std::stoi(value); + at(pair.key) = std::stoi(pair.value); } else if(std::holds_alternative<bool>(v)) { - at(key) = (value == "true"); + at(pair.key) = (pair.value == "true"); } } } |