]> git.proxmox.com Git - ceph.git/blob - ceph/src/boost/tools/quickbook/src/doc_info_grammar.cpp
update sources to v12.2.3
[ceph.git] / ceph / src / boost / tools / quickbook / src / doc_info_grammar.cpp
1 /*=============================================================================
2 Copyright (c) 2002 2004 2006 Joel de Guzman
3 Copyright (c) 2004 Eric Niebler
4 http://spirit.sourceforge.net/
5
6 Use, modification and distribution is subject to the Boost Software
7 License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
8 http://www.boost.org/LICENSE_1_0.txt)
9 =============================================================================*/
10
11 #include <map>
12 #include <boost/foreach.hpp>
13 #include <boost/spirit/include/classic_core.hpp>
14 #include <boost/spirit/include/classic_loops.hpp>
15 #include <boost/spirit/include/classic_symbols.hpp>
16 #include <boost/spirit/include/classic_chset.hpp>
17 #include <boost/spirit/include/classic_numerics.hpp>
18 #include <boost/spirit/include/phoenix1_primitives.hpp>
19 #include <boost/spirit/include/phoenix1_operators.hpp>
20 #include "grammar_impl.hpp"
21 #include "state.hpp"
22 #include "actions.hpp"
23 #include "doc_info_tags.hpp"
24 #include "phrase_tags.hpp"
25
26 namespace quickbook
27 {
28 namespace cl = boost::spirit::classic;
29
30 struct attribute_info
31 {
32 attribute_info(value::tag_type t, cl::rule<scanner>* r)
33 : tag(t), rule(r)
34 {}
35
36 value::tag_type tag;
37 cl::rule<scanner>* rule;
38 };
39
40 struct doc_info_grammar_local
41 {
42 struct assign_attribute_type
43 {
44 assign_attribute_type(doc_info_grammar_local& l_)
45 : l(l_)
46 {}
47
48 void operator()(value::tag_type& t) const {
49 l.attribute_rule = *l.attribute_rules[t];
50 l.attribute_tag = t;
51 }
52
53 doc_info_grammar_local& l;
54 };
55
56 struct fallback_attribute_type
57 {
58 fallback_attribute_type(doc_info_grammar_local& l_)
59 : l(l_)
60 {}
61
62 void operator()(parse_iterator, parse_iterator) const {
63 l.attribute_rule = l.doc_fallback;
64 l.attribute_tag = value::default_tag;
65 }
66
67 doc_info_grammar_local& l;
68 };
69
70 cl::rule<scanner>
71 doc_info_block, doc_attribute, doc_info_attribute,
72 doc_info_escaped_attributes,
73 doc_title, doc_simple, doc_phrase, doc_fallback,
74 doc_authors, doc_author,
75 doc_copyright, doc_copyright_holder,
76 doc_source_mode, doc_biblioid, doc_compatibility_mode,
77 quickbook_version, macro, char_;
78 cl::uint_parser<int, 10, 4, 4> doc_copyright_year;
79 cl::symbols<> doc_types;
80 cl::symbols<value::tag_type> doc_info_attributes;
81 cl::symbols<value::tag_type> doc_attributes;
82 std::map<value::tag_type, cl::rule<scanner>* > attribute_rules;
83 value::tag_type attribute_tag;
84 cl::rule<scanner> attribute_rule;
85 assign_attribute_type assign_attribute;
86 fallback_attribute_type fallback_attribute;
87
88 doc_info_grammar_local()
89 : assign_attribute(*this)
90 , fallback_attribute(*this)
91 {}
92
93 bool source_mode_unset;
94 };
95
96 void quickbook_grammar::impl::init_doc_info()
97 {
98 doc_info_grammar_local& local = cleanup_.add(
99 new doc_info_grammar_local);
100
101 typedef cl::uint_parser<int, 10, 1, 2> uint2_t;
102
103 local.doc_types =
104 "book", "article", "library", "chapter", "part"
105 , "appendix", "preface", "qandadiv", "qandaset"
106 , "reference", "set"
107 ;
108
109 BOOST_FOREACH(value::tag_type t, doc_attributes::tags()) {
110 local.doc_attributes.add(doc_attributes::name(t), t);
111 local.doc_info_attributes.add(doc_attributes::name(t), t);
112 }
113
114 BOOST_FOREACH(value::tag_type t, doc_info_attributes::tags()) {
115 local.doc_info_attributes.add(doc_info_attributes::name(t), t);
116 }
117
118 // Actions
119 error_action error(state);
120 plain_char_action plain_char(state);
121 do_macro_action do_macro(state);
122 scoped_parser<to_value_scoped_action> to_value(state);
123 member_action_value<quickbook::state, source_mode_type> change_source_mode(
124 state, &state::change_source_mode);
125 member_action_fixed_value<quickbook::state, source_mode_type> default_source_mode(
126 state, &state::change_source_mode, source_mode_tags::cpp);
127
128 doc_info_details =
129 cl::eps_p [ph::var(local.source_mode_unset) = true]
130 >> *( space
131 >> local.doc_attribute
132 )
133 >> !( space
134 >> local.doc_info_block
135 )
136 >> *eol
137 ;
138
139 local.doc_info_block =
140 '['
141 >> space
142 >> (local.doc_types >> cl::eps_p)
143 [state.values.entry(ph::arg1, ph::arg2, doc_info_tags::type)]
144 >> hard_space
145 >> to_value(doc_info_tags::title)
146 [ *( ~cl::eps_p(blank >> (cl::ch_p('[') | ']' | cl::eol_p))
147 >> local.char_
148 )
149 // Include 'blank' here so that it will be included in
150 // id generation.
151 >> blank
152 ]
153 >> space
154 >> !(qbk_ver(106u) >> cl::eps_p(ph::var(local.source_mode_unset))
155 [default_source_mode]
156 )
157 >> ( *( ( local.doc_info_attribute
158 | local.doc_info_escaped_attributes
159 )
160 >> space
161 )
162 ) [state.values.sort()]
163 >> ( ']'
164 >> (eol | cl::end_p)
165 | cl::eps_p [error]
166 )
167 ;
168
169 local.doc_attribute =
170 '['
171 >> space
172 >> local.doc_attributes [local.assign_attribute]
173 >> hard_space
174 >> state.values.list(ph::var(local.attribute_tag))
175 [ cl::eps_p [state.values.entry(ph::arg1, ph::arg2, doc_info_tags::before_docinfo)]
176 >> local.attribute_rule
177 ]
178 >> space
179 >> ']'
180 ;
181
182 local.doc_info_attribute =
183 '['
184 >> space
185 >> ( local.doc_info_attributes
186 [local.assign_attribute]
187 | (+(cl::alnum_p | '_' | '-'))
188 [local.fallback_attribute]
189 [error("Unrecognized document attribute: '%s'.")]
190 )
191 >> hard_space
192 >> state.values.list(ph::var(local.attribute_tag))
193 [local.attribute_rule]
194 >> space
195 >> ']'
196 ;
197
198 local.doc_fallback = to_value() [
199 *(~cl::eps_p(']') >> local.char_)
200 ];
201
202 local.doc_info_escaped_attributes =
203 ("'''" >> !eol)
204 >> (*(cl::anychar_p - "'''")) [state.values.entry(ph::arg1, ph::arg2, doc_info_tags::escaped_attribute)]
205 >> ( cl::str_p("'''")
206 | cl::eps_p [error("Unclosed boostbook escape.")]
207 )
208 ;
209
210 // Document Attributes
211
212 local.quickbook_version =
213 cl::uint_p [state.values.entry(ph::arg1)]
214 >> '.'
215 >> uint2_t() [state.values.entry(ph::arg1)]
216 ;
217
218 local.attribute_rules[doc_attributes::qbk_version] = &local.quickbook_version;
219
220 local.doc_compatibility_mode =
221 cl::uint_p [state.values.entry(ph::arg1)]
222 >> '.'
223 >> uint2_t() [state.values.entry(ph::arg1)]
224 ;
225
226 local.attribute_rules[doc_attributes::compatibility_mode] = &local.doc_compatibility_mode;
227
228 local.doc_source_mode = source_modes
229 [change_source_mode]
230 [ph::var(local.source_mode_unset) = false]
231 ;
232
233 local.attribute_rules[doc_attributes::source_mode] = &local.doc_source_mode;
234
235 // Document Info Attributes
236
237 local.doc_simple = to_value() [*(~cl::eps_p(']') >> local.char_)];
238 local.attribute_rules[doc_info_attributes::version] = &local.doc_simple;
239 local.attribute_rules[doc_info_attributes::id] = &local.doc_simple;
240 local.attribute_rules[doc_info_attributes::dirname] = &local.doc_simple;
241 local.attribute_rules[doc_info_attributes::category] = &local.doc_simple;
242 local.attribute_rules[doc_info_attributes::last_revision] = &local.doc_simple;
243 local.attribute_rules[doc_info_attributes::lang] = &local.doc_simple;
244 local.attribute_rules[doc_info_attributes::xmlbase] = &local.doc_simple;
245
246 local.doc_copyright_holder
247 = *( ~cl::eps_p
248 ( ']'
249 | ',' >> space >> local.doc_copyright_year
250 )
251 >> local.char_
252 );
253
254 local.doc_copyright =
255 *( +( local.doc_copyright_year
256 [state.values.entry(ph::arg1, doc_info_tags::copyright_year)]
257 >> space
258 >> !( '-'
259 >> space
260 >> local.doc_copyright_year
261 [state.values.entry(ph::arg1, doc_info_tags::copyright_year_end)]
262 >> space
263 )
264 >> !cl::ch_p(',')
265 >> space
266 )
267 >> to_value(doc_info_tags::copyright_name) [ local.doc_copyright_holder ]
268 >> !cl::ch_p(',')
269 >> space
270 )
271 ;
272
273 local.attribute_rules[doc_info_attributes::copyright] = &local.doc_copyright;
274
275 local.doc_phrase = to_value() [ nested_phrase ];
276 local.attribute_rules[doc_info_attributes::purpose] = &local.doc_phrase;
277 local.attribute_rules[doc_info_attributes::license] = &local.doc_phrase;
278
279 local.doc_author =
280 '['
281 >> space
282 >> to_value(doc_info_tags::author_surname)
283 [*(~cl::eps_p(',') >> local.char_)]
284 >> ',' >> space
285 >> to_value(doc_info_tags::author_first)
286 [*(~cl::eps_p(']') >> local.char_)]
287 >> ']'
288 ;
289
290 local.doc_authors =
291 *( local.doc_author
292 >> space
293 >> !(cl::ch_p(',') >> space)
294 )
295 ;
296
297 local.attribute_rules[doc_info_attributes::authors] = &local.doc_authors;
298
299 local.doc_biblioid =
300 (+cl::alnum_p) [state.values.entry(ph::arg1, ph::arg2, doc_info_tags::biblioid_class)]
301 >> hard_space
302 >> to_value(doc_info_tags::biblioid_value)
303 [+(~cl::eps_p(']') >> local.char_)]
304 ;
305
306 local.attribute_rules[doc_info_attributes::biblioid] = &local.doc_biblioid;
307
308 local.char_ =
309 escape
310 | local.macro
311 | cl::anychar_p[plain_char];
312 ;
313
314 local.macro =
315 cl::eps_p
316 ( ( state.macro
317 >> ~cl::eps_p(cl::alpha_p | '_')
318 // must not be followed by alpha or underscore
319 )
320 & macro_identifier // must be a valid macro for the current version
321 )
322 >> state.macro [do_macro]
323 ;
324 }
325 }