summaryrefslogtreecommitdiffstatshomepage
path: root/src/lib/util/opresolv.h
diff options
context:
space:
mode:
Diffstat (limited to 'src/lib/util/opresolv.h')
-rw-r--r--src/lib/util/opresolv.h201
1 files changed, 136 insertions, 65 deletions
diff --git a/src/lib/util/opresolv.h b/src/lib/util/opresolv.h
index 097d6e303ac..4c059a88d72 100644
--- a/src/lib/util/opresolv.h
+++ b/src/lib/util/opresolv.h
@@ -50,45 +50,79 @@
// TYPE DEFINITIONS
//**************************************************************************
-enum option_type
-{
- OPTIONTYPE_END,
- OPTIONTYPE_INT,
- OPTIONTYPE_STRING,
- OPTIONTYPE_ENUM_BEGIN,
- OPTIONTYPE_ENUM_VALUE
-};
-
-struct option_guide
-{
- enum option_type option_type;
- int parameter;
- const char *identifier;
- const char *display_name;
-};
-
#define OPTION_GUIDE_START(option_guide_) \
- const option_guide option_guide_[] = \
+ const util::option_guide option_guide_ = \
{
#define OPTION_GUIDE_END \
- { OPTIONTYPE_END } \
};
#define OPTION_GUIDE_EXTERN(option_guide_) \
- extern const option_guide option_guide_[]
+ extern const util::option_guide option_guide_
#define OPTION_INT(option_char, identifier, display_name) \
- { OPTIONTYPE_INT, (option_char), (identifier), (display_name) },
+ { util::option_guide::entry::option_type::INT, (option_char), (identifier), (display_name) },
#define OPTION_STRING(option_char, identifier, display_name) \
- { OPTIONTYPE_STRING, (option_char), (identifier), (display_name) },
+ { util::option_guide::entry::option_type::STRING, (option_char), (identifier), (display_name) },
#define OPTION_ENUM_START(option_char, identifier, display_name) \
- { OPTIONTYPE_ENUM_BEGIN, (option_char), (identifier), (display_name) },
+ { util::option_guide::entry::option_type::ENUM_BEGIN, (option_char), (identifier), (display_name) },
#define OPTION_ENUM(value, identifier, display_name) \
- { OPTIONTYPE_ENUM_VALUE, (value), (identifier), (display_name) },
+ { util::option_guide::entry::option_type::ENUM_VALUE, (value), (identifier), (display_name) },
#define OPTION_ENUM_END
namespace util {
+
+// ======================> option_guide
+
+class option_guide
+{
+public:
+ class entry
+ {
+ public:
+ enum class option_type
+ {
+ INT,
+ STRING,
+ ENUM_BEGIN,
+ ENUM_VALUE
+ };
+
+ constexpr entry(option_type type, int parameter = 0, const char *identifier = nullptr, const char *display_name = nullptr)
+ : m_type(type), m_parameter(parameter), m_identifier(identifier), m_display_name(display_name)
+ {
+ }
+
+ // accessors
+ const option_type type() const { return m_type; }
+ int parameter() const { return m_parameter; }
+ const char *identifier() const { return m_identifier; }
+ const char *display_name() const { return m_display_name; }
+
+ private:
+ option_type m_type;
+ int m_parameter;
+ const char *m_identifier;
+ const char *m_display_name;
+ };
+
+ typedef std::vector<option_guide::entry> entrylist;
+
+ option_guide(std::initializer_list<entry> entries)
+ : m_entries(entries)
+ {
+ }
+
+ // methods
+ const entrylist &entries() const { return m_entries; }
+
+private:
+ entrylist m_entries;
+};
+
+// ======================> option_resolution
+
class option_resolution
{
public:
+ // TODO - audit unused parameters
enum class error
{
SUCCESS,
@@ -102,61 +136,98 @@ public:
INTERNAL
};
+ template<typename T>
struct range
{
- int min, max;
+ range() { min = -1; max = -1; }
+ T min, max;
};
- option_resolution(const option_guide *guide, const char *specification);
- ~option_resolution();
-
- // processing options with option_resolution objects
- error add_param(const char *param, const std::string &value);
- error finish();
- int lookup_int(int option_char) const;
- const char *lookup_string(int option_char) const;
+ // class to represent specific entry
+ class entry
+ {
+ friend class option_resolution;
+
+ public:
+ typedef std::vector<range<int> > rangelist;
+
+ // ctor
+ entry(const option_guide::entry &guide_entry);
+
+ // returns true if this entry is subject to range constraints
+ bool is_ranged() const { return !m_ranges.empty(); }
+
+ // accessors
+ bool is_pertinent() const { return m_is_pertinent; }
+ const std::string &value() const;
+ int value_int() const;
+ const std::string &default_value() const { return m_default_value; }
+ const rangelist &ranges() const { return m_ranges; }
+ const option_guide::entrylist::const_iterator enum_value_begin() const { return m_enum_value_begin; }
+ const option_guide::entrylist::const_iterator enum_value_end() const { return m_enum_value_end; }
+
+ // accessors for guide data
+ option_guide::entry::option_type option_type() const { return m_guide_entry.type(); }
+ const char *display_name() const { return m_guide_entry.display_name(); }
+ const char *identifier() const { return m_guide_entry.identifier(); }
+ int parameter() const { return m_guide_entry.parameter(); }
+
+
+ // mutators
+ bool set_value(const std::string &value);
+ bool set_value(int value) { return set_value(numeric_value(value)); }
+
+ // higher level operations
+ bool can_bump_lower() const;
+ bool can_bump_higher() const;
+ bool bump_lower();
+ bool bump_higher();
+
+ private:
+ // references to the option guide
+ const option_guide::entry & m_guide_entry;
+ option_guide::entrylist::const_iterator m_enum_value_begin;
+ option_guide::entrylist::const_iterator m_enum_value_end;
+
+ // runtime state
+ bool m_is_pertinent;
+ std::string m_value;
+ std::string m_default_value;
+ rangelist m_ranges;
+
+ // methods
+ void parse_specification(const char *specification);
+ void set_enum_value_range(option_guide::entrylist::const_iterator begin, option_guide::entrylist::const_iterator end);
+ static std::string numeric_value(int value);
+ rangelist::const_iterator find_in_ranges(int value) const;
+ };
- // accessors
- const char *specification() const { return m_specification; }
- const option_guide *find_option(int option_char) const;
- const option_guide *index_option(int indx) const;
+ // ctor/dtor
+ option_resolution(const option_guide &guide);
+ ~option_resolution();
- // processing option guides
- static size_t count_options(const option_guide *guide, const char *specification);
+ // sets a specification
+ void set_specification(const std::string &specification);
- // processing option specifications
- static error list_ranges(const char *specification, int option_char,
- range *range, size_t range_count);
- static error get_default(const char *specification, int option_char, int *val);
- static error is_valid_value(const char *specification, int option_char, int val);
- static bool contains(const char *specification, int option_char);
+ // entry lookup - note that we're not exposing m_entries directly because we don't really
+ // have a way of making the list be immutable but the members be mutable at the same time
+ std::vector<entry>::iterator entries_begin() { return m_entries.begin(); }
+ std::vector<entry>::iterator entries_end() { return m_entries.end(); }
+ entry *find(int parameter);
+ entry *find(const std::string &identifier);
+ int lookup_int(int parameter);
+ const std::string &lookup_string(int parameter);
// misc
static const char *error_string(error err);
+ static error get_default(const char *specification, int option_char, int *val);
private:
- enum class entry_state
- {
- UNSPECIFIED,
- SPECIFIED
- };
-
- struct entry
- {
- const option_guide *guide_entry;
- entry_state state;
- std::string value;
-
- int int_value() const;
- void set_int_value(int i);
- };
-
- const char *m_specification;
std::vector<entry> m_entries;
- static error resolve_single_param(const char *specification, entry *param_value,
- struct range *range, size_t range_count);
- static const char *lookup_in_specification(const char *specification, const option_guide *option);
+ error set_parameter(std::vector<entry>::iterator iter, const std::string &value);
+
+ static const char *lookup_in_specification(const char *specification, const option_guide::entry &option);
const entry *lookup_entry(int option_char) const;
};