Search:

SENF Extensible Network Framework

  • Home
  • Download
  • Wiki
  • BerliOS
  • ChangeLog
  • Browse SVN
  • Bug Tracker
  • Overview
  • Examples
  • HowTos
  • Glossary
  • PPI
  • Packets
  • Scheduler
  • Socket
  • Utils
  • Console
  • Daemon
  • Logger
  • Termlib
  • Main Page
  • Related Pages
  • Modules
  • Namespaces
  • Classes
  • Files
  • File List
  • File Members

Parse.hh

Go to the documentation of this file.
00001 // $Id: Parse.hh 1742 2010-11-04 14:51:56Z g0dil $
00002 //
00003 // Copyright (C) 2008
00004 // Fraunhofer (FOKUS)
00005 // Competence Center NETwork research (NET), St. Augustin, GERMANY
00006 //     Stefan Bund <g0dil@berlios.de>
00007 //
00008 // This program is free software; you can redistribute it and/or modify
00009 // it under the terms of the GNU General Public License as published by
00010 // the Free Software Foundation; either version 2 of the License, or
00011 // (at your option) any later version.
00012 //
00013 // This program is distributed in the hope that it will be useful,
00014 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00015 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00016 // GNU General Public License for more details.
00017 //
00018 // You should have received a copy of the GNU General Public License
00019 // along with this program; if not, write to the
00020 // Free Software Foundation, Inc.,
00021 // 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
00022 
00026 #ifndef HH_SENF_Scheduler_Console_Parse_
00027 #define HH_SENF_Scheduler_Console_Parse_ 1
00028 
00192 // Custom includes
00193 #include <string>
00194 #include <vector>
00195 #include <boost/utility.hpp>
00196 #include <boost/scoped_ptr.hpp>
00197 #include <boost/range/iterator_range.hpp>
00198 #include <boost/iterator/iterator_facade.hpp>
00199 #include <boost/function.hpp>
00200 #include <senf/Utils/safe_bool.hh>
00201 #include <senf/Utils/Exception.hh>
00202 
00203 //#include "Parse.mpp"
00204 //-/////////////////////////////////////////////////////////////////////////////////////////////////
00205 
00206 namespace senf {
00207 namespace console {
00208 
00209     namespace detail { class FilePositionWithIndex; }
00210 
00211     namespace detail { struct ParserAccess; }
00212 
00220     class Token
00221     {
00222     public:
00223         enum TokenType {
00224             None                = 0,
00225             PathSeparator       = 0x0001, // '/'
00226             ArgumentGroupOpen   = 0x0002, // '('
00227             ArgumentGroupClose  = 0x0004, // ')'
00228             DirectoryGroupOpen  = 0x0008, // '{'
00229             DirectoryGroupClose = 0x0010, // '}'
00230             CommandTerminator   = 0x0020, // ';'
00231             OtherPunctuation    = 0x0040,
00232             BasicString         = 0x0080,
00233             HexString           = 0x0100,
00234             Word                = 0x0200
00235         };
00236 
00237         enum TokenGroup {
00238             ArgumentGrouper     = ArgumentGroupOpen
00239                                 | ArgumentGroupClose,
00240 
00241             DirectoryGrouper    = DirectoryGroupOpen
00242                                 | DirectoryGroupClose,
00243 
00244             Punctuation         = DirectoryGroupOpen
00245                                 | DirectoryGroupClose
00246                                 | PathSeparator
00247                                 | CommandTerminator
00248                                 | OtherPunctuation,
00249 
00250             String              = BasicString
00251                                 | HexString,
00252 
00253             SimpleArgument      = Word
00254                                 | BasicString
00255                                 | HexString
00256         };
00257 
00258         Token();                        
00259         Token(TokenType type, std::string token);
00261         Token(TokenType type, std::string token, detail::FilePositionWithIndex const & pos);
00263 
00264 
00265         std::string const & value() const; 
00266 
00268         TokenType type() const;         
00269 
00270         unsigned line() const;          
00271         unsigned column() const;        
00272         unsigned index() const;         
00273 
00274         bool is(unsigned tokens) const; 
00275 
00277         bool operator==(Token const & other) const;
00278         bool operator!=(Token const & other) const;
00279 
00280     protected:
00281 
00282     private:
00283         TokenType type_;
00284         std::string token_;
00285         unsigned line_;
00286         unsigned column_;
00287         unsigned index_;
00288     };
00289 
00290     std::ostream & operator<<(std::ostream & os, Token const & token);
00291 
00294     Token NoneToken();
00295 
00298     Token PathSeparatorToken();
00299 
00302     Token ArgumentGroupOpenToken();
00303 
00306     Token ArgumentGroupCloseToken();
00307 
00310     Token DirectoryGroupOpenToken();
00311 
00314     Token DirectoryGroupCloseToken();
00315 
00318     Token CommandTerminatorToken();
00319 
00322     Token OtherPunctuationToken(std::string const & value);
00323 
00326     Token BasicStringToken(std::string const & value);
00327 
00330     Token HexStringToken(std::string const & value);
00331 
00334     Token WordToken(std::string const & value);
00335 
00349     class ParseCommandInfo
00350     {
00351         typedef std::vector<Token> Tokens;
00352         typedef std::vector<std::string> CommandPath;
00353 
00354     public:
00355         class ArgumentIterator;
00356 
00357         typedef CommandPath::const_iterator path_iterator;
00358         typedef Tokens::const_iterator token_iterator;
00359         typedef ArgumentIterator argument_iterator;
00360         typedef Tokens::size_type size_type;
00361 
00362         typedef boost::iterator_range<path_iterator> CommandPathRange;
00363         typedef boost::iterator_range<argument_iterator> ArgumentsRange;
00364         typedef boost::iterator_range<token_iterator> TokensRange;
00365 
00366         enum BuiltinCommand { NoBuiltin,
00367                               BuiltinCD,
00368                               BuiltinLS,
00369                               BuiltinLL,
00370                               BuiltinLR,
00371                               BuiltinPUSHD,
00372                               BuiltinPOPD,
00373                               BuiltinEXIT,
00374                               BuiltinHELP };
00375 
00376         ParseCommandInfo();
00377 
00378         BuiltinCommand builtin() const; 
00379 
00381         TokensRange commandPath() const; 
00382 
00388         ArgumentsRange arguments() const; 
00389 
00391         TokensRange tokens() const;     
00392 
00395         void clear();                   
00396         bool empty();                   
00397 
00398         void builtin(BuiltinCommand builtin); 
00399         void command(std::vector<Token> & commandPath); 
00400 
00401         void addToken(Token const & token); 
00402 
00407     protected:
00408 
00409     private:
00410         struct MakeRange;
00411 
00412         std::vector<Token> commandPath_;
00413         BuiltinCommand builtin_;
00414         Tokens tokens_;
00415     };
00416 
00427     class ParseCommandInfo::ArgumentIterator
00428         : public boost::iterator_facade< ParseCommandInfo::ArgumentIterator,
00429                                          ParseCommandInfo::TokensRange,
00430                                          boost::bidirectional_traversal_tag,
00431                                          ParseCommandInfo::TokensRange >
00432     {
00433     public:
00434         ArgumentIterator();
00435         explicit ArgumentIterator(ParseCommandInfo::TokensRange::iterator i);
00436 
00437     private:
00438         reference dereference() const;
00439         bool equal(ArgumentIterator const & other) const;
00440         void increment();
00441         void decrement();
00442 
00443         mutable ParseCommandInfo::TokensRange::iterator b_;
00444         mutable ParseCommandInfo::TokensRange::iterator e_;
00445 
00446         void setRange() const;
00447 
00448         friend class boost::iterator_core_access;
00449         friend class ParseCommandInfo;
00450     };
00451 
00457     struct SyntaxErrorException : public senf::Exception
00458     { explicit SyntaxErrorException(std::string const & msg = "syntax error")
00459           : senf::Exception(msg) {} };
00460 
00493     class CheckedArgumentIteratorWrapper
00494         : boost::noncopyable,
00495           public boost::iterator_facade< CheckedArgumentIteratorWrapper,
00496                                          ParseCommandInfo::TokensRange,
00497                                          boost::forward_traversal_tag,
00498                                          ParseCommandInfo::TokensRange >,
00499           public senf::safe_bool<CheckedArgumentIteratorWrapper>
00500 
00501     {
00502         typedef boost::iterator_facade< CheckedArgumentIteratorWrapper,
00503                                         ParseCommandInfo::TokensRange,
00504                                         boost::forward_traversal_tag,
00505                                         ParseCommandInfo::TokensRange > IteratorFacade;
00506 
00507     public:
00508         explicit CheckedArgumentIteratorWrapper(
00509             ParseCommandInfo::ArgumentsRange const & range,
00510             std::string const & msg = "invalid number of arguments");
00512 
00516         explicit CheckedArgumentIteratorWrapper(
00517             ParseCommandInfo::TokensRange const & range,
00518             std::string const & msg = "invalid number of arguments");
00520 
00527         ~CheckedArgumentIteratorWrapper(); 
00528 
00536         operator ParseCommandInfo::ArgumentIterator();
00538 
00539         bool boolean_test() const;      
00540         bool done() const;              
00541 
00542         void clear();                   
00543 
00547         bool operator==(ParseCommandInfo::ArgumentIterator const & other) const;
00549         bool operator!=(ParseCommandInfo::ArgumentIterator const & other) const;
00551 
00552         using IteratorFacade::operator++;
00553         ParseCommandInfo::ArgumentIterator operator++(int);
00554 
00555     private:
00556         reference dereference() const;
00557         void increment();
00558 
00559         ParseCommandInfo::ArgumentIterator i_;
00560         ParseCommandInfo::ArgumentIterator e_;
00561         std::string msg_;
00562 
00563         friend class boost::iterator_core_access;
00564     };
00565 
00569     std::ostream & operator<<(std::ostream & stream, ParseCommandInfo const & info);
00570 
00586     class CommandParser
00587         : boost::noncopyable
00588     {
00589     public:
00590         //-////////////////////////////////////////////////////////////////////////
00591         // Types
00592 
00593         typedef boost::function<void (ParseCommandInfo const &)> Callback;
00594 
00595         //-////////////////////////////////////////////////////////////////////////
00597         //\{
00598 
00599         CommandParser();
00600         ~CommandParser();
00601 
00602         //\}
00603         //-////////////////////////////////////////////////////////////////////////
00604 
00605         void parse(std::string const & command, Callback cb); 
00606         void parseFile(std::string const & filename, Callback cb); 
00607 
00610         void parseArguments(std::string const & arguments, ParseCommandInfo & info);
00612 
00617         void parsePath(std::string const & path, ParseCommandInfo & info);
00619 
00622         std::string::size_type parseIncremental(std::string const & commands, Callback cb);
00624 
00633         static bool isSpecialChar(char ch); 
00634         static bool isPunctuationChar(char ch); 
00635         static bool isSpaceChar(char ch); 
00636         static bool isInvalidChar(char ch); 
00637         static bool isWordChar(char ch); 
00638 
00640         struct ParserErrorException : public SyntaxErrorException
00641         { explicit ParserErrorException(std::string const & msg) : SyntaxErrorException(msg) {} };
00642 
00643     private:
00644         struct Impl;
00645         struct SetIncremental;
00646 
00647         template <class Iterator>
00648         Iterator parseLoop(Iterator b, Iterator e, std::string const & source, Callback cb);
00649 
00650         Impl & impl();
00651 
00652         boost::scoped_ptr<Impl> impl_;
00653 
00654         friend class SetIncremental;
00655     };
00656 
00657 }}
00658 
00659 //-/////////////////////////////////////////////////////////////////////////////////////////////////
00660 #include "Parse.cci"
00661 //#include "Parse.ct"
00662 //#include "Parse.cti"
00663 #endif
00664 
00665 
00666 // Local Variables:
00667 // mode: c++
00668 // fill-column: 100
00669 // comment-column: 40
00670 // c-file-style: "senf"
00671 // indent-tabs-mode: nil
00672 // ispell-local-dictionary: "american"
00673 // compile-command: "scons -u test"
00674 // End:

Contact: senf-dev@lists.berlios.de | © 2006-2010 Fraunhofer Institute for Open Communication Systems, Network Research