Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: downloads/boost_1_34_1/tools/quickbook/syntax_highlight.hpp @ 45

Last change on this file since 45 was 29, checked in by landauf, 17 years ago

updated boost from 1_33_1 to 1_34_1

File size: 11.0 KB
Line 
1/*=============================================================================
2    Copyright (c) 2002 2004 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#if !defined(BOOST_SPIRIT_QUICKBOOK_SYNTAX_HIGHLIGHT_HPP)
11#define BOOST_SPIRIT_QUICKBOOK_SYNTAX_HIGHLIGHT_HPP
12
13#include <boost/spirit/core.hpp>
14#include <boost/spirit/utility/confix.hpp>
15#include <boost/spirit/utility/chset.hpp>
16#include <boost/spirit/symbols/symbols.hpp>
17#include <boost/spirit/utility/escape_char.hpp>
18#include "./phrase.hpp"
19
20namespace quickbook
21{
22    using namespace boost::spirit;
23
24    // Grammar for C++ highlighting
25    template <
26        typename Process
27      , typename Space
28      , typename Macro
29      , typename DoMacro
30      , typename PreEscape
31      , typename PostEscape
32      , typename EscapeActions
33      , typename Unexpected
34      , typename Out>
35    struct cpp_highlight
36    : public grammar<cpp_highlight<Process, Space, Macro, DoMacro, PreEscape, PostEscape, EscapeActions, Unexpected, Out> >
37    {
38        cpp_highlight(Out& out, Macro const& macro, DoMacro do_macro, EscapeActions& escape_actions)
39        : out(out), macro(macro), do_macro(do_macro), escape_actions(escape_actions) {}
40
41        template <typename Scanner>
42        struct definition
43        {
44            definition(cpp_highlight const& self)
45                : common(self.escape_actions, unused)
46                , unused(false)
47            {
48                program
49                    =
50                    *(  (+space_p)      [Space(self.out)]
51                    |   self.macro      [self.do_macro]
52                    |   escape
53                    |   preprocessor    [Process("preprocessor", self.out)]
54                    |   comment         [Process("comment", self.out)]
55                    |   keyword         [Process("keyword", self.out)]
56                    |   identifier      [Process("identifier", self.out)]
57                    |   special         [Process("special", self.out)]
58                    |   string_         [Process("string", self.out)]
59                    |   char_           [Process("char", self.out)]
60                    |   number          [Process("number", self.out)]
61                    |   anychar_p       [Unexpected(self.out)]
62                    )
63                    ;
64
65                qbk_phrase =
66                   *(   common
67                    |   (anychar_p - str_p("``"))   [self.escape_actions.plain_char]
68                    )
69                    ;
70
71                escape
72                    = str_p("``")           [PreEscape(self.escape_actions, save)]
73                    >>  (
74                            (+(anychar_p - "``") >> eps_p("``"))
75                            & qbk_phrase
76                        )
77                    >> str_p("``")          [PostEscape(self.out, self.escape_actions, save)]
78                    ;
79
80                preprocessor
81                    =   '#' >> ((alpha_p | '_') >> *(alnum_p | '_'))
82                    ;
83
84                comment
85                    =   comment_p("//") | comment_p("/*", "*/")
86                    ;
87
88                keyword
89                    =   keyword_ >> (eps_p - (alnum_p | '_'))
90                    ;   // make sure we recognize whole words only
91
92                keyword_
93                    =   "and_eq", "and", "asm", "auto", "bitand", "bitor",
94                        "bool", "break", "case", "catch", "char", "class",
95                        "compl", "const_cast", "const", "continue", "default",
96                        "delete", "do", "double", "dynamic_cast",  "else",
97                        "enum", "explicit", "export", "extern", "false",
98                        "float", "for", "friend", "goto", "if", "inline",
99                        "int", "long", "mutable", "namespace", "new", "not_eq",
100                        "not", "operator", "or_eq", "or", "private",
101                        "protected", "public", "register", "reinterpret_cast",
102                        "return", "short", "signed", "sizeof", "static",
103                        "static_cast", "struct", "switch", "template", "this",
104                        "throw", "true", "try", "typedef", "typeid",
105                        "typename", "union", "unsigned", "using", "virtual",
106                        "void", "volatile", "wchar_t", "while", "xor_eq", "xor"
107                    ;
108
109                special
110                    =   +chset_p("~!%^&*()+={[}]:;,<.>?/|\\-")
111                    ;
112
113                string_
114                    =   !as_lower_d['l'] >> confix_p('"', *c_escape_ch_p, '"')
115                    ;
116
117                char_
118                    =   !as_lower_d['l'] >> confix_p('\'', *c_escape_ch_p, '\'')
119                    ;
120
121                number
122                    =   (
123                            as_lower_d["0x"] >> hex_p
124                        |   '0' >> oct_p
125                        |   real_p
126                        )
127                        >>  *as_lower_d[chset_p("ldfu")]
128                    ;
129
130                identifier
131                    =   (alpha_p | '_') >> *(alnum_p | '_')
132                    ;
133            }
134
135            rule<Scanner>   program, macro, preprocessor, comment, special, string_, 
136                            char_, number, identifier, keyword, qbk_phrase, escape;
137
138            symbols<> keyword_;
139            phrase_grammar<EscapeActions> common;
140            std::string save;
141            bool unused;
142
143            rule<Scanner> const&
144            start() const { return program; }
145        };
146
147        Out& out;
148        Macro const& macro;
149        DoMacro do_macro;
150        EscapeActions& escape_actions;
151    };
152
153    // Grammar for Python highlighting
154    // See also: The Python Reference Manual
155    // http://docs.python.org/ref/ref.html
156    template <
157        typename Process
158      , typename Space
159      , typename Macro
160      , typename DoMacro
161      , typename PreEscape
162      , typename PostEscape
163      , typename EscapeActions
164      , typename Unexpected
165      , typename Out>
166    struct python_highlight
167    : public grammar<python_highlight<Process, Space, Macro, DoMacro, PreEscape, PostEscape, EscapeActions, Unexpected, Out> >
168    {
169        python_highlight(Out& out, Macro const& macro, DoMacro do_macro, EscapeActions& escape_actions)
170        : out(out), macro(macro), do_macro(do_macro), escape_actions(escape_actions) {}
171
172        template <typename Scanner>
173        struct definition
174        {
175            definition(python_highlight const& self)
176                : common(self.escape_actions, unused)
177                , unused(false)
178            {
179                program
180                    =
181                    *(  (+space_p)      [Space(self.out)]
182                    |   self.macro      [self.do_macro]
183                    |   escape         
184                    |   comment         [Process("comment", self.out)]
185                    |   keyword         [Process("keyword", self.out)]
186                    |   identifier      [Process("identifier", self.out)]
187                    |   special         [Process("special", self.out)]
188                    |   string_         [Process("string", self.out)]
189                    |   number          [Process("number", self.out)]
190                    |   anychar_p       [Unexpected(self.out)]
191                    )
192                    ;
193
194                qbk_phrase =
195                   *(   common
196                    |   (anychar_p - str_p("``"))   [self.escape_actions.plain_char]
197                    )
198                    ;
199
200                escape
201                    = str_p("``")           [PreEscape(self.escape_actions, save)]
202                    >>  (
203                            (+(anychar_p - "``") >> eps_p("``"))
204                            & qbk_phrase
205                        )
206                    >> str_p("``")          [PostEscape(self.out, self.escape_actions, save)]
207                    ;
208
209                comment
210                    =   comment_p("#")
211                    ;
212
213                keyword
214                    =   keyword_ >> (eps_p - (alnum_p | '_'))
215                    ;   // make sure we recognize whole words only
216
217                keyword_
218                    =
219                    "and",       "del",       "for",       "is",        "raise",   
220                    "assert",    "elif",      "from",      "lambda",    "return",   
221                    "break",     "else",      "global",    "not",       "try", 
222                    "class",     "except",    "if",        "or",        "while",   
223                    "continue",  "exec",      "import",    "pass",      "yield",   
224                    "def",       "finally",   "in",        "print",
225
226                    // Technically "as" and "None" are not yet keywords (at Python
227                    // 2.4). They are destined to become keywords, and we treat them
228                    // as such for syntax highlighting purposes.
229                   
230                    "as", "None"
231                    ;
232
233                special
234                    =   +chset_p("~!%^&*()+={[}]:;,<.>/|\\-")
235                    ;
236
237                string_prefix
238                    =    as_lower_d[str_p("u") >> ! str_p("r")]
239                    ;
240               
241                string_
242                    =   ! string_prefix >> (long_string | short_string)
243                    ;
244
245                short_string
246                    =   confix_p('\'', * c_escape_ch_p, '\'') |
247                        confix_p('"', * c_escape_ch_p, '"')   
248                    ;
249           
250                long_string
251                    // Note: the "str_p" on the next two lines work around
252                    // an INTERNAL COMPILER ERROR when using VC7.1
253                    =   confix_p(str_p("'''"), * lex_escape_ch_p, "'''") |
254                        confix_p(str_p("\"\"\""), * lex_escape_ch_p, "\"\"\"")
255                    ;
256               
257                number
258                    =   (
259                            as_lower_d["0x"] >> hex_p
260                        |   '0' >> oct_p
261                        |   real_p
262                        )
263                        >>  *as_lower_d[chset_p("lj")]
264                    ;
265
266                identifier
267                    =   (alpha_p | '_') >> *(alnum_p | '_')
268                    ;
269            }
270
271            rule<Scanner>   program, macro, comment, special, string_, string_prefix, 
272                            short_string, long_string, number, identifier, keyword, 
273                            qbk_phrase, escape;
274
275            symbols<> keyword_;
276            phrase_grammar<EscapeActions> common;
277            std::string save;
278            bool unused;
279
280            rule<Scanner> const&
281            start() const { return program; }
282        };
283
284        Out& out;
285        Macro const& macro;
286        DoMacro do_macro;
287        EscapeActions& escape_actions;
288    };
289}
290
291#endif // BOOST_SPIRIT_QUICKBOOK_SYNTAX_HIGHLIGHT_HPP
Note: See TracBrowser for help on using the repository browser.