Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-19 09:47:45

0001 /*=============================================================================
0002     Copyright (c) 2001-2011 Joel de Guzman
0003 
0004     Distributed under the Boost Software License, Version 1.0. (See accompanying
0005     file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
0006 ==============================================================================*/
0007 #if !defined(BOOST_SPIRIT_DEBUG_HANDLER_DECEMBER_05_2008_0734PM)
0008 #define BOOST_SPIRIT_DEBUG_HANDLER_DECEMBER_05_2008_0734PM
0009 
0010 #if defined(_MSC_VER)
0011 #pragma once
0012 #endif
0013 
0014 #include <boost/spirit/home/qi/nonterminal/rule.hpp>
0015 #include <boost/spirit/home/qi/nonterminal/debug_handler_state.hpp>
0016 #include <boost/spirit/home/qi/detail/expectation_failure.hpp>
0017 #include <boost/function.hpp>
0018 #include <string>
0019 
0020 namespace boost { namespace spirit { namespace qi
0021 {
0022     template <
0023         typename Iterator, typename Context
0024       , typename Skipper, typename F>
0025     struct debug_handler
0026     {
0027         typedef function<
0028             bool(Iterator& first, Iterator const& last
0029               , Context& context
0030               , Skipper const& skipper
0031             )>
0032         function_type;
0033 
0034         debug_handler(
0035             function_type subject_
0036           , F f_
0037           , std::string const& rule_name_)
0038           : subject(subject_)
0039           , f(f_)
0040           , rule_name(rule_name_)
0041         {
0042         }
0043 
0044         bool operator()(
0045             Iterator& first, Iterator const& last
0046           , Context& context, Skipper const& skipper) const
0047         {
0048             f(first, last, context, pre_parse, rule_name);
0049             try // subject might throw an exception
0050             {
0051                 if (subject(first, last, context, skipper))
0052                 {
0053                     f(first, last, context, successful_parse, rule_name);
0054                     return true;
0055                 }
0056                 f(first, last, context, failed_parse, rule_name);
0057             }
0058             catch (expectation_failure<Iterator> const& e)
0059             {
0060                 f(first, last, context, failed_parse, rule_name);
0061                 boost::throw_exception(e);
0062             }
0063             return false;
0064         }
0065 
0066         function_type subject;
0067         F f;
0068         std::string rule_name;
0069     };
0070 
0071     template <typename Iterator
0072       , typename T1, typename T2, typename T3, typename T4, typename F>
0073     void debug(rule<Iterator, T1, T2, T3, T4>& r, F f)
0074     {
0075         typedef rule<Iterator, T1, T2, T3, T4> rule_type;
0076 
0077         typedef
0078             debug_handler<
0079                 Iterator
0080               , typename rule_type::context_type
0081               , typename rule_type::skipper_type
0082               , F>
0083         debug_handler;
0084         r.f = debug_handler(r.f, f, r.name());
0085     }
0086 
0087     struct simple_trace;
0088 
0089     namespace detail
0090     {
0091         // This class provides an extra level of indirection through a
0092         // template to produce the simple_trace type. This way, the use
0093         // of simple_trace below is hidden behind a dependent type, so
0094         // that compilers eagerly type-checking template definitions
0095         // won't complain that simple_trace is incomplete.
0096         template<typename T>
0097         struct get_simple_trace
0098         {
0099             typedef simple_trace type;
0100         };
0101     }
0102 
0103     template <typename Iterator
0104       , typename T1, typename T2, typename T3, typename T4>
0105     void debug(rule<Iterator, T1, T2, T3, T4>& r)
0106     {
0107         typedef rule<Iterator, T1, T2, T3, T4> rule_type;
0108 
0109         typedef
0110             debug_handler<
0111                 Iterator
0112               , typename rule_type::context_type
0113               , typename rule_type::skipper_type
0114               , simple_trace>
0115         debug_handler;
0116 
0117         typedef typename qi::detail::get_simple_trace<Iterator>::type trace;
0118         r.f = debug_handler(r.f, trace(), r.name());
0119     }
0120 
0121 }}}
0122 
0123 ///////////////////////////////////////////////////////////////////////////////
0124 //  Utility macro for easy enabling of rule and grammar debugging
0125 #if !defined(BOOST_SPIRIT_DEBUG_NODE)
0126   #if defined(BOOST_SPIRIT_DEBUG) || defined(BOOST_SPIRIT_QI_DEBUG)
0127     #define BOOST_SPIRIT_DEBUG_NODE(r)  r.name(#r); debug(r)
0128   #else
0129     #define BOOST_SPIRIT_DEBUG_NODE(r)  r.name(#r)
0130   #endif
0131 #endif
0132 
0133 #define BOOST_SPIRIT_DEBUG_NODE_A(r, _, name)                                   \
0134     BOOST_SPIRIT_DEBUG_NODE(name);                                              \
0135     /***/
0136 
0137 #define BOOST_SPIRIT_DEBUG_NODES(seq)                                           \
0138     BOOST_PP_SEQ_FOR_EACH(BOOST_SPIRIT_DEBUG_NODE_A, _, seq)                    \
0139     /***/
0140 
0141 #endif