]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/libs/spirit/include/boost/spirit/home/classic/core/non_terminal/parser_context.hpp
add subtree-ish sources for 12.0.3
[ceph.git] / ceph / src / boost / libs / spirit / include / boost / spirit / home / classic / core / non_terminal / parser_context.hpp
1 /*=============================================================================
2 Copyright (c) 2002-2003 Joel de Guzman
3 Copyright (c) 2002-2003 Hartmut Kaiser
4 http://spirit.sourceforge.net/
5
6 Distributed under the Boost Software License, Version 1.0. (See accompanying
7 file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
8 =============================================================================*/
9 #if !defined(BOOST_SPIRIT_PARSER_CONTEXT_HPP)
10 #define BOOST_SPIRIT_PARSER_CONTEXT_HPP
11
12 ///////////////////////////////////////////////////////////////////////////////
13 namespace boost
14 {
15 namespace spirit
16 {
17 BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
18
19
20 ///////////////////////////////////////////////////////////////////////////
21 //
22 // default_parser_context_base class { default context base }
23 //
24 ///////////////////////////////////////////////////////////////////////////
25 struct default_parser_context_base
26 {
27 template <typename DerivedT>
28 struct aux {};
29 };
30
31 ///////////////////////////////////////////////////////////////////////////
32 //
33 // parser_context_base class { base class of all context classes }
34 //
35 ///////////////////////////////////////////////////////////////////////////
36 struct parser_context_base {};
37
38 ///////////////////////////////////////////////////////////////////////////
39 //
40 // parser_context class { default context }
41 //
42 ///////////////////////////////////////////////////////////////////////////
43 struct nil_t;
44 template<typename ContextT> struct parser_context_linker;
45
46 template<typename AttrT = nil_t>
47 struct parser_context : parser_context_base
48 {
49 typedef AttrT attr_t;
50 typedef default_parser_context_base base_t;
51 typedef parser_context_linker<parser_context<AttrT> > context_linker_t;
52
53 template <typename ParserT>
54 parser_context(ParserT const&) {}
55
56 template <typename ParserT, typename ScannerT>
57 void
58 pre_parse(ParserT const&, ScannerT const&) {}
59
60 template <typename ResultT, typename ParserT, typename ScannerT>
61 ResultT&
62 post_parse(ResultT& hit, ParserT const&, ScannerT const&)
63 { return hit; }
64 };
65
66 ///////////////////////////////////////////////////////////////////////////
67 //
68 // context_aux class
69 //
70 // context_aux<ContextT, DerivedT> is a class derived from the
71 // ContextT's nested base_t::base<DerivedT> template class. (see
72 // default_parser_context_base::aux for an example).
73 //
74 // Basically, this class provides ContextT dependent optional
75 // functionality to the derived class DerivedT through the CRTP
76 // idiom (Curiously recurring template pattern).
77 //
78 ///////////////////////////////////////////////////////////////////////////
79 template <typename ContextT, typename DerivedT>
80 struct context_aux : public ContextT::base_t::template aux<DerivedT> {};
81
82 ///////////////////////////////////////////////////////////////////////////
83 //
84 // parser_scanner_linker and parser_scanner_linker classes
85 // { helper templates for the rule extensibility }
86 //
87 // This classes can be 'overloaded' (defined elsewhere), to plug
88 // in additional functionality into the non-terminal parsing process.
89 //
90 ///////////////////////////////////////////////////////////////////////////
91 #if !defined(BOOST_SPIRIT_PARSER_SCANNER_LINKER_DEFINED)
92 #define BOOST_SPIRIT_PARSER_SCANNER_LINKER_DEFINED
93
94 template<typename ScannerT>
95 struct parser_scanner_linker : public ScannerT
96 {
97 parser_scanner_linker(ScannerT const scan_) : ScannerT(scan_) {}
98 };
99
100 #endif // !defined(BOOST_SPIRIT_PARSER_SCANNER_LINKER_DEFINED)
101
102 //////////////////////////////////
103 #if !defined(BOOST_SPIRIT_PARSER_CONTEXT_LINKER_DEFINED)
104 #define BOOST_SPIRIT_PARSER_CONTEXT_LINKER_DEFINED
105
106 template<typename ContextT>
107 struct parser_context_linker : public ContextT
108 {
109 template <typename ParserT>
110 parser_context_linker(ParserT const& p)
111 : ContextT(p) {}
112
113 template <typename ParserT, typename ScannerT>
114 void pre_parse(ParserT const& p, ScannerT const& scan)
115 { ContextT::pre_parse(p, scan); }
116
117 template <typename ResultT, typename ParserT, typename ScannerT>
118 ResultT&
119 post_parse(ResultT& hit, ParserT const& p, ScannerT const& scan)
120 { return ContextT::post_parse(hit, p, scan); }
121 };
122
123 #endif // !defined(BOOST_SPIRIT_PARSER_CONTEXT_LINKER_DEFINED)
124
125 ///////////////////////////////////////////////////////////////////////////
126 //
127 // BOOST_SPIRIT_CONTEXT_PARSE helper macro
128 //
129 // The original implementation uses a template class. However, we
130 // need to lessen the template instantiation depth to help inferior
131 // compilers that sometimes choke on deep template instantiations.
132 // The objective is to avoid code redundancy. A macro, in this case
133 // is an obvious solution. Sigh!
134 //
135 // WARNING: INTERNAL USE ONLY. NOT FOR PUBLIC CONSUMPTION.
136 //
137 ///////////////////////////////////////////////////////////////////////////
138 #define BOOST_SPIRIT_CONTEXT_PARSE(scan, this_, scanner_t, context_t, result_t) \
139 scanner_t scan_wrap(scan); \
140 context_t context_wrap(this_); \
141 context_wrap.pre_parse(this_, scan_wrap); \
142 result_t hit = parse_main(scan); \
143 return context_wrap.post_parse(hit, this_, scan_wrap);
144
145 BOOST_SPIRIT_CLASSIC_NAMESPACE_END
146
147 } // namespace spirit
148 } // namespace boost
149
150 #endif