X-Git-Url: http://g0dil.de/git?a=blobdiff_plain;f=Console%2FParse.cc;h=c06a2bc9b9f42a9b0f1cd47844dc765e5c2f27bf;hb=bf1d8ba5ce6fc6a169a938183f8d01c8bdbccf32;hp=1f8a6b2e82fdd010b66f3ece505d048c060b96f6;hpb=412cf8e222086fb5d89b15cb11556799e131f390;p=senf.git diff --git a/Console/Parse.cc b/Console/Parse.cc index 1f8a6b2..c06a2bc 100644 --- a/Console/Parse.cc +++ b/Console/Parse.cc @@ -27,8 +27,11 @@ #include "Parse.ih" // Custom includes -#include "../Utils/String.hh" +#include #include +#include +#include "../Utils/String.hh" +#include "../Utils/Exception.hh" //#include "Parse.mpp" #define prefix_ @@ -38,6 +41,8 @@ namespace senf { namespace console { namespace detail { +#ifndef DOXYGEN + struct ParserAccess { static void init(ParseCommandInfo & info) @@ -67,90 +72,110 @@ namespace detail { struct ParseDispatcher { - ParseDispatcher() - : info_ (0) {} - - ParseCommandInfo * info_; - - ParseCommandInfo & info() { - SENF_ASSERT( info_ ); - return *info_; - } + ParseCommandInfo info_; + CommandParser::Callback cb_; struct BindInfo { - BindInfo( ParseDispatcher & d, ParseCommandInfo & i) - : dispatcher (d) { dispatcher.info_ = &i; } - - ~BindInfo() { dispatcher.info_ = 0; } + BindInfo( ParseDispatcher & d, CommandParser::Callback cb) + : dispatcher (d) { dispatcher.cb_ = cb; } + ~BindInfo() { dispatcher.cb_ = 0; } ParseDispatcher & dispatcher; }; void beginCommand(std::vector & command) - { ParserAccess::init(info()); - ParserAccess::setCommand(info(), command); } + { ParserAccess::init(info_); + ParserAccess::setCommand(info_, command); } void endCommand() - { ParserAccess::finalize(info()); } + { ParserAccess::finalize(info_); cb_(info_); } void pushArgument(std::string const & argument) - { ParserAccess::startArgument(info()); - ParserAccess::addToken(info(), ParserAccess::makeToken(argument)); - ParserAccess::endArgument(info()); } + { ParserAccess::startArgument(info_); + ParserAccess::addToken(info_, ParserAccess::makeToken(argument)); + ParserAccess::endArgument(info_); } void openGroup() - { ParserAccess::startArgument(info()); } + { ParserAccess::startArgument(info_); } void closeGroup() - { ParserAccess::endArgument(info()); } + { ParserAccess::endArgument(info_); } void pushPunctuation(std::string const & token) - { ParserAccess::addToken(info(), ParserAccess::makeToken(token)); } + { ParserAccess::addToken(info_, ParserAccess::makeToken(token)); } void pushWord(std::string const & token) - { ParserAccess::addToken(info(), ParserAccess::makeToken(token)); } + { ParserAccess::addToken(info_, ParserAccess::makeToken(token)); } void builtin_cd(std::vector & path) - { ParserAccess::init(info()); - ParserAccess::setBuiltin(info(), ParseCommandInfo::BuiltinCD); + { ParserAccess::init(info_); + ParserAccess::setBuiltin(info_, ParseCommandInfo::BuiltinCD); setBuiltinPathArg(path); - ParserAccess::finalize(info()); } + ParserAccess::finalize(info_); cb_(info_); } void builtin_ls(std::vector & path) - { ParserAccess::init(info()); - ParserAccess::setBuiltin(info(), ParseCommandInfo::BuiltinLS); + { ParserAccess::init(info_); + ParserAccess::setBuiltin(info_, ParseCommandInfo::BuiltinLS); setBuiltinPathArg(path); - ParserAccess::finalize(info()); } + ParserAccess::finalize(info_); cb_(info_); } + + void pushDirectory(std::vector & path) + { ParserAccess::init(info_); + ParserAccess::setBuiltin(info_, ParseCommandInfo::BuiltinPUSHD); + setBuiltinPathArg(path); + ParserAccess::finalize(info_); cb_(info_); } + + void popDirectory() + { ParserAccess::init(info_); + ParserAccess::setBuiltin(info_, ParseCommandInfo::BuiltinPOPD); + ParserAccess::finalize(info_); cb_(info_); } + + void builtin_exit() + { ParserAccess::init(info_); + ParserAccess::setBuiltin(info_, ParseCommandInfo::BuiltinEXIT); + ParserAccess::finalize(info_); cb_(info_); } + + void builtin_help(std::vector & path) + { ParserAccess::init(info_); + ParserAccess::setBuiltin(info_, ParseCommandInfo::BuiltinHELP); + setBuiltinPathArg(path); + ParserAccess::finalize(info_); cb_(info_); } void setBuiltinPathArg(std::vector & path) { - ParserAccess::startArgument(info()); + ParserAccess::startArgument(info_); for (std::vector::const_iterator i (path.begin()); i != path.end(); ++i) - ParserAccess::addToken(info(), ParserAccess::makeToken(*i)); - ParserAccess::endArgument(info()); + ParserAccess::addToken(info_, ParserAccess::makeToken(*i)); + ParserAccess::endArgument(info_); } }; +#endif + }}} /////////////////////////////////////////////////////////////////////////// // senf::console::ParseCommandInfo +#ifndef DOXYGEN + struct senf::console::ParseCommandInfo::MakeRange { + typedef ParseCommandInfo::argument_value_type result_type; + MakeRange() {} MakeRange(ParseCommandInfo::token_iterator b) : b_ (b) {} - + senf::console::ParseCommandInfo::token_iterator b_; - - typedef ParseCommandInfo::argument_value_type result_type; - + result_type operator()(TempArguments::iterator::value_type const & v) const { return result_type( b_ + v.first, b_ + v.second ); } }; +#endif + prefix_ void senf::console::ParseCommandInfo::finalize() { arguments_.resize( tempArguments_.size() ); @@ -170,7 +195,7 @@ prefix_ std::ostream & senf::console::operator<<(std::ostream & stream, if (info.builtin() == ParseCommandInfo::NoBuiltin) stream << senf::stringJoin(info.commandPath(), "/"); else { - char const * builtins[] = { "", "cd", "ls" }; + char const * builtins[] = { "", "cd", "ls", "pushd", "popd", "exit", "help" }; stream << "builtin-" << builtins[info.builtin()]; } @@ -192,9 +217,11 @@ prefix_ std::ostream & senf::console::operator<<(std::ostream & stream, } /////////////////////////////////////////////////////////////////////////// -// senf::console::SingleCommandParser +// senf::console::CommandParser + +#ifndef DOXYGEN -struct senf::console::SingleCommandParser::Impl +struct senf::console::CommandParser::Impl { typedef detail::CommandGrammar Grammar; @@ -205,18 +232,32 @@ struct senf::console::SingleCommandParser::Impl Impl() : dispatcher(), context(), grammar(dispatcher, context) {} }; -prefix_ senf::console::SingleCommandParser::SingleCommandParser() +#endif + +prefix_ senf::console::CommandParser::CommandParser() : impl_ (new Impl()) {} -prefix_ senf::console::SingleCommandParser::~SingleCommandParser() +prefix_ senf::console::CommandParser::~CommandParser() {} -prefix_ bool senf::console::SingleCommandParser::parseCommand(std::string command, - ParseCommandInfo & info) +prefix_ bool senf::console::CommandParser::parse(std::string command, Callback cb) +{ + detail::ParseDispatcher::BindInfo bind (impl().dispatcher, cb); + return boost::spirit::parse( command.begin(), command.end(), + impl().grammar.use_parser(), + impl().grammar.use_parser() + ).full; +} + +prefix_ bool senf::console::CommandParser::parseFile(std::string filename, Callback cb) { - detail::ParseDispatcher::BindInfo bind (impl().dispatcher, info); - return boost::spirit::parse( command.c_str(), + detail::ParseDispatcher::BindInfo bind (impl().dispatcher, cb); + boost::spirit::file_iterator<> i (filename); + if (!i) throw SystemException(ENOENT SENF_EXC_DEBUGINFO); + boost::spirit::file_iterator<> const i_end (i.make_end()); + + return boost::spirit::parse( i, i_end, impl().grammar.use_parser(), impl().grammar.use_parser() ).full;