diff options
Diffstat (limited to 'src/Configuration.cpp')
-rw-r--r-- | src/Configuration.cpp | 119 |
1 files changed, 69 insertions, 50 deletions
diff --git a/src/Configuration.cpp b/src/Configuration.cpp index 5b5d75bd..9abdc288 100644 --- a/src/Configuration.cpp +++ b/src/Configuration.cpp @@ -14,26 +14,34 @@ along with Ingen. If not, see <http://www.gnu.org/licenses/>. */ -#include "ingen/Configuration.hpp" -#include "ingen/Forge.hpp" -#include "ingen/URIMap.hpp" -#include "ingen/filesystem.hpp" -#include "ingen/fmt.hpp" -#include "ingen/ingen.h" -#include "ingen/runtime_paths.hpp" -#include "lv2/urid/urid.h" -#include "serd/serd.h" -#include "sord/sord.h" -#include "sord/sordmm.hpp" -#include "sratom/sratom.h" +#include <ingen/Atom.hpp> +#include <ingen/Configuration.hpp> +#include <ingen/FilePath.hpp> +#include <ingen/Forge.hpp> +#include <ingen/URIMap.hpp> +#include <ingen/fmt.hpp> +#include <ingen/ingen.h> +#include <ingen/runtime_paths.hpp> +#include <lv2/urid/urid.h> +#include <serd/serd.h> +#include <sord/sord.h> +#include <sord/sordmm.hpp> +#include <sratom/sratom.h> #include <algorithm> #include <cassert> #include <cerrno> #include <cstdint> +#include <cstdio> #include <cstdlib> #include <cstring> +#include <filesystem> +#include <list> +#include <map> #include <memory> +#include <ostream> +#include <string> +#include <system_error> #include <thread> #include <utility> #include <vector> @@ -54,8 +62,9 @@ Configuration::Configuration(Forge& forge) " ingen -g # Run GUI, connect to running engine\n" " ingen -eg # Run engine and GUI in one process\n" " ingen -eg foo.ingen # Run engine and GUI and load a graph") - , _max_name_length(0) { + static const auto default_n_threads = static_cast<int32_t>(std::max(std::thread::hardware_concurrency(), 1U)); + add("atomicBundles", "atomic-bundles", 'a', "Execute bundles atomically", GLOBAL, forge.Bool, forge.make(false)); add("bufferSize", "buffer-size", 'b', "Buffer size in samples", GLOBAL, forge.Int, forge.make(1024)); add("clientPort", "client-port", 'C', "Client port", GLOBAL, forge.Int, Atom()); @@ -78,7 +87,7 @@ Configuration::Configuration(Forge& forge) add("flushLog", "flush-log", 'f', "Flush logs after every entry", GLOBAL, forge.Bool, forge.make(false)); add("dump", "dump", 'd', "Print debug output", SESSION, forge.Bool, forge.make(false)); add("trace", "trace", 't', "Show LV2 plugin trace messages", SESSION, forge.Bool, forge.make(false)); - add("threads", "threads", 'p', "Number of processing threads", GLOBAL, forge.Int, forge.make(int32_t(std::max(std::thread::hardware_concurrency(), 1U)))); + add("threads", "threads", 'p', "Number of processing threads", GLOBAL, forge.Int, forge.make(default_n_threads)); add("humanNames", "human-names", 0, "Show human names in GUI", GUI, forge.Bool, forge.make(true)); add("portLabels", "port-labels", 0, "Show port labels in GUI", GUI, forge.Bool, forge.make(true)); add("graphDirectory", "graph-directory", 0, "Default directory for opening graphs", GUI, forge.String, Atom()); @@ -110,19 +119,22 @@ Configuration::variable_string(LV2_URID type) const { if (type == _forge.String) { return "=STRING"; - } else if (type == _forge.Int) { + } + + if (type == _forge.Int) { return "=INT"; } + return ""; } void Configuration::print_usage(const std::string& program, std::ostream& os) { - os << "Usage: " << program << " [OPTION]... [GRAPH]" << std::endl; - os << _shortdesc << std::endl << std::endl; - os << _desc << std::endl << std::endl; - os << "Options:" << std::endl; + os << "Usage: " << program << " [OPTION]... [GRAPH]\n"; + os << _shortdesc << "\n\n"; + os << _desc << "\n\n"; + os << "Options:\n"; for (const auto& o : _options) { const Option& option = o.second; os << " "; @@ -131,10 +143,10 @@ Configuration::print_usage(const std::string& program, std::ostream& os) } else { os << " "; } - os.width(_max_name_length + 11); + os.width(static_cast<std::streamsize>(_max_name_length + 11)); os << std::left; os << (std::string("--") + o.first + variable_string(option.type)); - os << option.desc << std::endl; + os << option.desc << "\n"; } } @@ -143,8 +155,8 @@ Configuration::set_value_from_string(Configuration::Option& option, const std::string& value) { if (option.type == _forge.Int) { - char* endptr = nullptr; - int intval = static_cast<int>(strtol(value.c_str(), &endptr, 10)); + char* endptr = nullptr; + const int intval = static_cast<int>(strtol(value.c_str(), &endptr, 10)); if (endptr && *endptr == '\0') { option.value = _forge.make(intval); } else { @@ -155,7 +167,7 @@ Configuration::set_value_from_string(Configuration::Option& option, option.value = _forge.alloc(value.c_str()); assert(option.value.type() == _forge.String); } else if (option.type == _forge.Bool) { - option.value = _forge.make(bool(!strcmp(value.c_str(), "true"))); + option.value = _forge.make(!strcmp(value.c_str(), "true")); assert(option.value.type() == _forge.Bool); } else { throw OptionError(fmt("Bad option type `%1%'", option.name)); @@ -170,7 +182,7 @@ Configuration::parse(int argc, char** argv) for (int i = 1; i < argc; ++i) { if (argv[i][0] != '-' || !strcmp(argv[i], "-")) { // File argument - const Options::iterator o = _options.find("load"); + const auto o = _options.find("load"); if (!o->second.value.is_valid()) { _options.find("load")->second.value = _forge.alloc(argv[i]); } else { @@ -181,17 +193,19 @@ Configuration::parse(int argc, char** argv) std::string name = std::string(argv[i]).substr(2); const char* equals = strchr(argv[i], '='); if (equals) { - name = name.substr(0, name.find('=')); + name.resize(name.find('=')); } - const Options::iterator o = _options.find(name); + const auto o = _options.find(name); if (o == _options.end()) { throw OptionError(fmt("Unrecognized option `%1%'", name)); - } else if (o->second.type == _forge.Bool) { // --flag + } + + if (o->second.type == _forge.Bool) { // --flag o->second.value = _forge.make(true); - } else if (equals) { // --opt=val + } else if (equals) { // --opt=val set_value_from_string(o->second, equals + 1); - } else if (++i < argc) { // --opt val + } else if (++i < argc) { // --opt val set_value_from_string(o->second, argv[i]); } else { throw OptionError(fmt("Missing value for `%1%'", name)); @@ -200,22 +214,22 @@ Configuration::parse(int argc, char** argv) // Short option const size_t len = strlen(argv[i]); for (size_t j = 1; j < len; ++j) { - const char letter = argv[i][j]; - const ShortNames::iterator n = _short_names.find(letter); + const char letter = argv[i][j]; + const auto n = _short_names.find(letter); if (n == _short_names.end()) { throw OptionError(fmt("Unrecognized option `%1%'", letter)); } - const Options::iterator o = _options.find(n->second); - if (j < len - 1) { // Non-final POSIX style flag + const auto o = _options.find(n->second); + if (j < len - 1) { // Non-final POSIX style flag if (o->second.type != _forge.Bool) { throw OptionError( fmt("Missing value for `%1%'", letter)); } o->second.value = _forge.make(true); - } else if (o->second.type == _forge.Bool) { // -f + } else if (o->second.type == _forge.Bool) { // -f o->second.value = _forge.make(true); - } else if (++i < argc) { // -v val + } else if (++i < argc) { // -v val set_value_from_string(o->second, argv[i]); } else { throw OptionError(fmt("Missing value for `%1%'", letter)); @@ -228,7 +242,7 @@ Configuration::parse(int argc, char** argv) bool Configuration::load(const FilePath& path) { - if (!filesystem::exists(path)) { + if (!std::filesystem::exists(path)) { return false; } @@ -242,14 +256,17 @@ Configuration::load(const FilePath& path) SerdEnv* env = serd_env_new(&node); model.load_file(env, SERD_TURTLE, uri, uri); - Sord::Node nodemm(world, Sord::Node::URI, reinterpret_cast<const char*>(node.buf)); - Sord::Node nil; - for (Sord::Iter i = model.find(nodemm, nil, nil); !i.end(); ++i) { - const Sord::Node& pred = i.get_predicate(); - const Sord::Node& obj = i.get_object(); + const Sord::Node nodemm{world, + Sord::Node::URI, + reinterpret_cast<const char*>(node.buf)}; + + const Sord::Node nil; + for (auto i = model.find(nodemm, nil, nil); !i.end(); ++i) { + const auto& pred = i.get_predicate(); + const auto& obj = i.get_object(); if (pred.to_string().substr(0, sizeof(INGEN_NS) - 1) == INGEN_NS) { const std::string key = pred.to_string().substr(sizeof(INGEN_NS) - 1); - const Keys::iterator k = _keys.find(key); + const auto k = _keys.find(key); if (k != _keys.end() && obj.type() == Sord::Node::LITERAL) { set_value_from_string(_options.find(k->second)->second, obj.to_string()); @@ -275,15 +292,17 @@ Configuration::save(URIMap& uri_map, } // Create parent directories if necessary - const FilePath dir = path.parent_path(); - if (!filesystem::create_directories(dir)) { + const FilePath dir = path.parent_path(); + std::error_code ec; + std::filesystem::create_directories(dir, ec); + if (ec) { throw FileError(fmt("Error creating directory %1% (%2%)", dir, strerror(errno))); } // Attempt to open file for writing - std::unique_ptr<FILE, decltype(&fclose)> file{fopen(path.c_str(), "w"), - &fclose}; + const std::unique_ptr<FILE, int (*)(FILE*)> file{ + fopen(path.c_str(), "w"), &fclose}; if (!file) { throw FileError(fmt("Failed to open file %1% (%2%)", path, strerror(errno))); @@ -338,7 +357,7 @@ Configuration::save(URIMap& uri_map, } const std::string key(std::string("ingen:") + o.second.key); - SerdNode pred = serd_node_from_string( + const SerdNode pred = serd_node_from_string( SERD_CURIE, reinterpret_cast<const uint8_t*>(key.c_str())); sratom_write(sratom, &uri_map.urid_unmap(), 0, &base, &pred, value.type(), value.size(), value.get_body()); @@ -380,9 +399,9 @@ Configuration::option(const std::string& long_name) const auto o = _options.find(long_name); if (o == _options.end()) { return nil; - } else { - return o->second.value; } + + return o->second.value; } bool |