diff options
author | 2007-05-26 16:02:17 +0000 | |
---|---|---|
committer | 2007-05-26 16:02:17 +0000 | |
commit | f8241e85c77382c4560ad2c39a86d98587492715 (patch) | |
tree | d6e02a5a1674f83b3409dfc87b1484f93226495c /paludis/args | |
parent | 9b7bfeac95df0cbe76fbf60976e789fae2890c5e (diff) | |
download | paludis-f8241e85c77382c4560ad2c39a86d98587492715.tar.gz paludis-f8241e85c77382c4560ad2c39a86d98587492715.tar.xz |
New type safe visitor framework
Diffstat (limited to 'paludis/args')
-rw-r--r-- | paludis/args/args_dumper.cc | 61 | ||||
-rw-r--r-- | paludis/args/args_dumper.hh | 19 | ||||
-rw-r--r-- | paludis/args/args_handler.cc | 8 | ||||
-rw-r--r-- | paludis/args/args_option.cc | 1 | ||||
-rw-r--r-- | paludis/args/args_option.hh | 17 | ||||
-rw-r--r-- | paludis/args/args_visitor.cc | 96 | ||||
-rw-r--r-- | paludis/args/args_visitor.hh | 33 | ||||
-rw-r--r-- | paludis/args/man.cc | 29 |
8 files changed, 164 insertions, 100 deletions
diff --git a/paludis/args/args_dumper.cc b/paludis/args/args_dumper.cc index 5c0e0ac87..66f9e5027 100644 --- a/paludis/args/args_dumper.cc +++ b/paludis/args/args_dumper.cc @@ -19,6 +19,7 @@ #include <paludis/args/args_dumper.hh> #include <paludis/args/args_option.hh> +#include <paludis/util/visitor-impl.hh> #include <sstream> @@ -36,34 +37,26 @@ ArgsDumper::ArgsDumper(std::ostream & os) : { } -void ArgsDumper::visit(const ArgsOption * const a) +void ArgsDumper::generic_visit(const ArgsOption & a) { std::stringstream p; - p << " --" << a->long_name(); - if (a->short_name()) - p << ", -" << a->short_name(); + p << " --" << a.long_name(); + if (a.short_name()) + p << ", -" << a.short_name(); if (p.str().length() < 24) p << std::string(24 - p.str().length(), ' '); else p << std::endl << std::string(24, ' '); _os << p.str(); - _os << " " << a->description() << std::endl; + _os << " " << a.description() << std::endl; } -#define VISIT(type) void ArgsDumper::visit(const type * const a) \ - { visit(static_cast<const ArgsOption *>(a)); } - -VISIT(SwitchArg) -VISIT(StringArg) -VISIT(IntegerArg) -VISIT(AliasArg) - -void ArgsDumper::visit(const StringSetArg * const a) +void ArgsDumper::visit(const StringSetArg & a) { - visit(static_cast<const ArgsOption *>(a)); + generic_visit(a); - if (a->begin_allowed_args() != a->end_allowed_args()) - for (StringSetArg::AllowedArgIterator it = a->begin_allowed_args(), it_end = a->end_allowed_args(); + if (a.begin_allowed_args() != a.end_allowed_args()) + for (StringSetArg::AllowedArgIterator it = a.begin_allowed_args(), it_end = a.end_allowed_args(); it != it_end; ++it) { std::stringstream p; @@ -76,10 +69,11 @@ void ArgsDumper::visit(const StringSetArg * const a) } } -void ArgsDumper::visit(const EnumArg * const a) +void ArgsDumper::visit(const EnumArg & a) { - visit(static_cast<const ArgsOption *>(a)); - for (EnumArg::AllowedArgIterator it = a->begin_allowed_args(), it_end = a->end_allowed_args(); + generic_visit(a); + + for (EnumArg::AllowedArgIterator it = a.begin_allowed_args(), it_end = a.end_allowed_args(); it != it_end; ++it) { std::stringstream p; @@ -88,8 +82,33 @@ void ArgsDumper::visit(const EnumArg * const a) p << std::string(26 - p.str().length(), ' '); _os << p.str(); _os << " " << (*it).second; - if ((*it).first == a->default_arg()) + if ((*it).first == a.default_arg()) _os << " (default)"; _os << std::endl; } } + +void +ArgsDumper::visit(const SwitchArg & a) +{ + generic_visit(a); +} + +void +ArgsDumper::visit(const StringArg & a) +{ + generic_visit(a); +} + +void +ArgsDumper::visit(const IntegerArg & a) +{ + generic_visit(a); +} + +void +ArgsDumper::visit(const AliasArg & a) +{ + generic_visit(a); +} + diff --git a/paludis/args/args_dumper.hh b/paludis/args/args_dumper.hh index c1cd9c151..c0fa70ef5 100644 --- a/paludis/args/args_dumper.hh +++ b/paludis/args/args_dumper.hh @@ -41,37 +41,36 @@ namespace paludis * \ingroup grplibpaludisargs */ class PALUDIS_VISIBLE ArgsDumper : - public ArgsVisitorTypes::ConstVisitor + public ConstVisitor<ArgsVisitorTypes> { private: std::ostream & _os; + void generic_visit(const ArgsOption &); + public: /** * Constructor. */ ArgsDumper(std::ostream & os); - /// Visit an ArgsOption. - void visit(const ArgsOption * const); - /// Visit a SwitchArg. - void visit(const SwitchArg * const); + void visit(const SwitchArg &); /// Visit a StringArg. - void visit(const StringArg * const); + void visit(const StringArg &); /// Visit an IntegerArg. - void visit(const IntegerArg * const); + void visit(const IntegerArg &); /// Visit an AliasArg. - void visit(const AliasArg * const); + void visit(const AliasArg &); /// Visit an EnumArg. - void visit(const EnumArg * const); + void visit(const EnumArg &); /// Visit a StringSetArg. - void visit(const StringSetArg * const); + void visit(const StringSetArg &); }; } } diff --git a/paludis/args/args_handler.cc b/paludis/args/args_handler.cc index f1287c127..341154bd8 100644 --- a/paludis/args/args_handler.cc +++ b/paludis/args/args_handler.cc @@ -21,6 +21,8 @@ #include "args_dumper.hh" #include <paludis/util/system.hh> #include <paludis/util/join.hh> +#include <paludis/util/iterator.hh> +#include <paludis/util/visitor-impl.hh> #include <algorithm> #include <sstream> #include <list> @@ -133,7 +135,7 @@ ArgsHandler::run(const int argc, const char * const * const argv, std::map<std::string, ArgsOption *>::iterator it = _imp->longopts.find(arg); if (it == _imp->longopts.end()) throw BadArgument("--" + arg); - (*it).second->accept(&visitor); + it->second->accept(visitor); } else if (arg[0] == '-') { @@ -145,7 +147,7 @@ ArgsHandler::run(const int argc, const char * const * const argv, { throw BadArgument(std::string("-") + *c); } - (*it).second->accept(&visitor); + it->second->accept(visitor); } } else @@ -171,7 +173,7 @@ ArgsHandler::dump_to_stream(std::ostream & s) const { s << (*g)->name() << ":" << std::endl; - std::for_each((*g)->begin(), (*g)->end(), accept_visitor(&dump)); + std::for_each(indirect_iterator((*g)->begin()), indirect_iterator((*g)->end()), accept_visitor(dump)); s << std::endl; } diff --git a/paludis/args/args_option.cc b/paludis/args/args_option.cc index 6731f7407..9013499b6 100644 --- a/paludis/args/args_option.cc +++ b/paludis/args/args_option.cc @@ -29,6 +29,7 @@ * \ingroup grplibpaludisargs */ +using namespace paludis; using namespace paludis::args; namespace diff --git a/paludis/args/args_option.hh b/paludis/args/args_option.hh index f6a3a3532..d091bdba4 100644 --- a/paludis/args/args_option.hh +++ b/paludis/args/args_option.hh @@ -42,7 +42,7 @@ namespace paludis * \ingroup grplibpaludisargs */ class PALUDIS_VISIBLE ArgsOption : - public virtual VisitableInterface<ArgsVisitorTypes> + public virtual MutableAcceptInterface<ArgsVisitorTypes> { friend class ArgsHandler; @@ -68,7 +68,7 @@ namespace paludis /** * Destructor. */ - ~ArgsOption(); + virtual ~ArgsOption(); public: /** @@ -129,7 +129,7 @@ namespace paludis */ class PALUDIS_VISIBLE SwitchArg : public ArgsOption, - public Visitable<SwitchArg, ArgsVisitorTypes> + public MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, SwitchArg> { public: /** @@ -148,7 +148,7 @@ namespace paludis */ class PALUDIS_VISIBLE StringArg : public ArgsOption, - public Visitable<StringArg, ArgsVisitorTypes> + public MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, StringArg> { private: std::string _argument; @@ -187,7 +187,7 @@ namespace paludis */ class PALUDIS_VISIBLE StringSetArg : public ArgsOption, - public Visitable<StringSetArg, ArgsVisitorTypes>, + public MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, StringSetArg>, private PrivateImplementationPattern<StringSetArg> { private: @@ -285,7 +285,7 @@ namespace paludis */ class PALUDIS_VISIBLE AliasArg : public ArgsOption, - public Visitable<AliasArg, ArgsVisitorTypes> + public MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, AliasArg> { private: ArgsOption * const _other; @@ -322,7 +322,7 @@ namespace paludis */ class PALUDIS_VISIBLE IntegerArg : public ArgsOption, - public Visitable<IntegerArg, ArgsVisitorTypes> + public MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, IntegerArg> { private: int _argument; @@ -352,7 +352,7 @@ namespace paludis */ class PALUDIS_VISIBLE EnumArg : public ArgsOption, - public Visitable<EnumArg, ArgsVisitorTypes>, + public MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, EnumArg>, private PrivateImplementationPattern<EnumArg> { private: @@ -360,7 +360,6 @@ namespace paludis const std::string _default_arg; public: - /** * Helper class for passing available options and associated descriptions * to the EnumArg constructor. diff --git a/paludis/args/args_visitor.cc b/paludis/args/args_visitor.cc index 4eb20a418..37066ad6b 100644 --- a/paludis/args/args_visitor.cc +++ b/paludis/args/args_visitor.cc @@ -20,6 +20,7 @@ #include "args_error.hh" #include <paludis/util/visitor.hh> +#include <paludis/util/visitor-impl.hh> #include <paludis/util/destringify.hh> #include <paludis/util/system.hh> #include <paludis/util/join.hh> @@ -35,7 +36,31 @@ */ using namespace paludis; -using namespace args; +using namespace paludis::args; + +template class MutableVisitor<ArgsVisitorTypes>; +template class MutableAcceptInterface<ArgsVisitorTypes>; + +template class MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, IntegerArg>; +template class MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, EnumArg>; +template class MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, StringArg>; +template class MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, StringSetArg>; +template class MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, AliasArg>; +template class MutableAcceptInterfaceVisitsThis<ArgsVisitorTypes, SwitchArg>; + +template class Visits<IntegerArg>; +template class Visits<EnumArg>; +template class Visits<StringArg>; +template class Visits<StringSetArg>; +template class Visits<AliasArg>; +template class Visits<SwitchArg>; + +template class Visits<const IntegerArg>; +template class Visits<const EnumArg>; +template class Visits<const StringArg>; +template class Visits<const StringSetArg>; +template class Visits<const AliasArg>; +template class Visits<const SwitchArg>; ArgsVisitor::ArgsVisitor(libwrapiter::ForwardIterator<ArgsVisitor, std::string> * ai, libwrapiter::ForwardIterator<ArgsVisitor, std::string> ae, @@ -47,79 +72,90 @@ ArgsVisitor::ArgsVisitor(libwrapiter::ForwardIterator<ArgsVisitor, std::string> } const std::string & -ArgsVisitor::get_param(const ArgsOption * const arg) +ArgsVisitor::get_param(const ArgsOption & arg) { if (++(*_args_index) == _args_end) - throw MissingValue("--" + arg->long_name()); + throw MissingValue("--" + arg.long_name()); return **_args_index; } -void ArgsVisitor::visit(ArgsOption * const arg) +void ArgsVisitor::visit(StringArg & arg) { - arg->set_specified(true); + arg.set_specified(true); if (! _env_prefix.empty()) - setenv(env_name(arg->long_name()).c_str(), "1", 1); -} + setenv(env_name(arg.long_name()).c_str(), "1", 1); -void ArgsVisitor::visit(StringArg * const arg) -{ - visit(static_cast<ArgsOption *>(arg)); std::string p(get_param(arg)); - arg->set_argument(p); + arg.set_argument(p); if (! _env_prefix.empty()) - setenv(env_name(arg->long_name()).c_str(), p.c_str(), 1); + setenv(env_name(arg.long_name()).c_str(), p.c_str(), 1); } -void ArgsVisitor::visit(AliasArg * const arg) +void ArgsVisitor::visit(AliasArg & arg) { - arg->other()->accept(this); + arg.other()->accept(*this); } -void ArgsVisitor::visit(SwitchArg * const arg) +void ArgsVisitor::visit(SwitchArg & arg) { - visit(static_cast<ArgsOption *>(arg)); + arg.set_specified(true); + + if (! _env_prefix.empty()) + setenv(env_name(arg.long_name()).c_str(), "1", 1); } -void ArgsVisitor::visit(IntegerArg * const arg) +void ArgsVisitor::visit(IntegerArg & arg) { - visit(static_cast<ArgsOption*>(arg)); + arg.set_specified(true); + + if (! _env_prefix.empty()) + setenv(env_name(arg.long_name()).c_str(), "1", 1); + std::string param = get_param(arg); try { int a(destringify<int>(param)); - arg->set_argument(a); + arg.set_argument(a); if (! _env_prefix.empty()) - setenv(env_name(arg->long_name()).c_str(), stringify(a).c_str(), 1); + setenv(env_name(arg.long_name()).c_str(), stringify(a).c_str(), 1); } catch (const DestringifyError &) { - throw BadValue("--" + arg->long_name(), param); + throw BadValue("--" + arg.long_name(), param); } } -void ArgsVisitor::visit(EnumArg * const arg) +void ArgsVisitor::visit(EnumArg & arg) { - visit(static_cast<ArgsOption*>(arg)); + arg.set_specified(true); + + if (! _env_prefix.empty()) + setenv(env_name(arg.long_name()).c_str(), "1", 1); + std::string p(get_param(arg)); - arg->set_argument(p); + arg.set_argument(p); if (! _env_prefix.empty()) - setenv(env_name(arg->long_name()).c_str(), p.c_str(), 1); + setenv(env_name(arg.long_name()).c_str(), p.c_str(), 1); } -void ArgsVisitor::visit(StringSetArg * const arg) +void ArgsVisitor::visit(StringSetArg & arg) { - visit(static_cast<ArgsOption *>(arg)); + arg.set_specified(true); + + if (! _env_prefix.empty()) + setenv(env_name(arg.long_name()).c_str(), "1", 1); + std::string param = get_param(arg); - arg->add_argument(param); + arg.add_argument(param); if (! _env_prefix.empty()) - setenv(env_name(arg->long_name()).c_str(), join(arg->begin_args(), - arg->end_args(), " ").c_str(), 1); + setenv(env_name(arg.long_name()).c_str(), join(arg.begin_args(), + arg.end_args(), " ").c_str(), 1); } std::string diff --git a/paludis/args/args_visitor.hh b/paludis/args/args_visitor.hh index e60769ece..1d83eb800 100644 --- a/paludis/args/args_visitor.hh +++ b/paludis/args/args_visitor.hh @@ -50,8 +50,18 @@ namespace paludis * * \ingroup grplibpaludisargs */ - typedef VisitorTypes<ArgsOption *, StringArg *, AliasArg *, SwitchArg *, - IntegerArg *, EnumArg *, StringSetArg *> ArgsVisitorTypes; + struct ArgsVisitorTypes : + VisitorTypes< + ArgsVisitorTypes, + ArgsOption, + StringArg, + AliasArg, + SwitchArg, + IntegerArg, + EnumArg, + StringSetArg> + { + }; /** * Visitor class. Processes command-line options as they are found. @@ -59,13 +69,13 @@ namespace paludis * \ingroup grplibpaludisargs */ class PALUDIS_VISIBLE ArgsVisitor : - public ArgsVisitorTypes::Visitor + public MutableVisitor<ArgsVisitorTypes> { private: libwrapiter::ForwardIterator<ArgsVisitor, std::string> * _args_index, _args_end; std::string _env_prefix; - const std::string & get_param(const ArgsOption * const); + const std::string & get_param(const ArgsOption &); std::string env_name(const std::string & long_name) const; @@ -77,26 +87,23 @@ namespace paludis libwrapiter::ForwardIterator<ArgsVisitor, std::string>, const std::string & env_prefix = ""); - /// Visit an ArgsOption. - void visit(ArgsOption * const); - /// Visit a StringArg. - void visit(StringArg * const); + void visit(StringArg &); /// Visit an AliasArg. - void visit(AliasArg * const); + void visit(AliasArg &); /// Visit a SwitchArg. - void visit(SwitchArg * const); + void visit(SwitchArg &); /// Visit an IntegerArg. - void visit(IntegerArg * const); + void visit(IntegerArg &); /// Visit an EnumArg. - void visit(EnumArg * const); + void visit(EnumArg &); /// Visit a StringSetArg. - void visit(StringSetArg * const); + void visit(StringSetArg &); }; } } diff --git a/paludis/args/man.cc b/paludis/args/man.cc index 13ccc32ce..121e796bb 100644 --- a/paludis/args/man.cc +++ b/paludis/args/man.cc @@ -18,6 +18,7 @@ */ #include "man.hh" +#include <paludis/util/visitor-impl.hh> #include <ostream> #include <sstream> @@ -28,7 +29,7 @@ using std::endl; namespace { struct ExtraText : - ArgsVisitorTypes::ConstVisitor + ConstVisitor<ArgsVisitorTypes> { DocWriter & _dw; @@ -37,50 +38,50 @@ namespace { } - void visit(const ArgsOption * const) + void visit(const ArgsOption &) { } - void visit(const StringArg * const) + void visit(const StringArg &) { } - void visit(const AliasArg * const) + void visit(const AliasArg &) { } - void visit(const SwitchArg * const) + void visit(const SwitchArg &) { } - void visit(const IntegerArg * const) + void visit(const IntegerArg &) { } - void visit(const EnumArg * const e) + void visit(const EnumArg & e) { - if (e->begin_allowed_args() == e->end_allowed_args()) + if (e.begin_allowed_args() == e.end_allowed_args()) return; _dw.start_extra_arg(); - for (EnumArg::AllowedArgIterator a(e->begin_allowed_args()), a_end(e->end_allowed_args()) ; + for (EnumArg::AllowedArgIterator a(e.begin_allowed_args()), a_end(e.end_allowed_args()) ; a != a_end ; ++a) { - _dw.extra_arg_enum(a->first, a->second, e->default_arg()); + _dw.extra_arg_enum(a->first, a->second, e.default_arg()); } _dw.end_extra_arg(); } - void visit(const StringSetArg * const e) + void visit(const StringSetArg & e) { - if (e->begin_allowed_args() == e->end_allowed_args()) + if (e.begin_allowed_args() == e.end_allowed_args()) return; _dw.start_extra_arg(); - for (EnumArg::AllowedArgIterator a(e->begin_allowed_args()), a_end(e->end_allowed_args()) ; + for (EnumArg::AllowedArgIterator a(e.begin_allowed_args()), a_end(e.end_allowed_args()) ; a != a_end ; ++a) { _dw.extra_arg_string_set(a->first, a->second); @@ -116,7 +117,7 @@ paludis::args::generate_doc(DocWriter & dw, const ArgsHandler * const h) dw.arg_group_item((*b)->short_name(), (*b)->long_name(), (*b)->description()); ExtraText t(dw); - (*b)->accept(&t); + (*b)->accept(t); dw.end_arg_group(); } |