1 | // Copyright (c) 2001-2011 Hartmut Kaiser |
2 | // |
3 | // Distributed under the Boost Software License, Version 1.0. (See accompanying |
4 | // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) |
5 | |
6 | #include <boost/spirit/include/lex_lexertl.hpp> |
7 | #include <boost/spirit/include/qi_parse.hpp> |
8 | #include <boost/spirit/include/qi_operator.hpp> |
9 | #include "test_parser.hpp" |
10 | |
11 | #include <boost/core/lightweight_test.hpp> |
12 | |
13 | /////////////////////////////////////////////////////////////////////////////// |
14 | // Token definition |
15 | /////////////////////////////////////////////////////////////////////////////// |
16 | template <typename Lexer> |
17 | struct switch_state_tokens : boost::spirit::lex::lexer<Lexer> |
18 | { |
19 | switch_state_tokens() |
20 | { |
21 | // define tokens and associate them with the lexer |
22 | identifier = "[a-zA-Z_][a-zA-Z0-9_]*" ; |
23 | this->self = identifier; |
24 | |
25 | // any token definition to be used as the skip parser during parsing |
26 | // has to be associated with a separate lexer state (here 'WS') |
27 | white_space = "[ \\t\\n]+" ; |
28 | this->self("WS" ) = white_space; |
29 | |
30 | separators = "[,;]" ; |
31 | this->self("SEP" ) = separators; |
32 | } |
33 | |
34 | boost::spirit::lex::token_def<> identifier, white_space, separators; |
35 | }; |
36 | |
37 | /////////////////////////////////////////////////////////////////////////////// |
38 | int main() |
39 | { |
40 | using namespace boost::spirit; |
41 | using namespace boost::spirit::qi; |
42 | using namespace spirit_test; |
43 | |
44 | typedef std::string::iterator base_iterator_type; |
45 | typedef boost::spirit::lex::lexertl::token<base_iterator_type> token_type; |
46 | typedef boost::spirit::lex::lexertl::lexer<token_type> lexer_type; |
47 | |
48 | { |
49 | // the tokens class will be initialized inside the test_parser function |
50 | switch_state_tokens<lexer_type> lex; |
51 | |
52 | BOOST_TEST(test_parser("ident" , lex.identifier, lex)); |
53 | BOOST_TEST(!test_parser("ident" , set_state("WS" ) >> lex.identifier, lex)); |
54 | BOOST_TEST(!test_parser("ident" , in_state("WS" )[lex.identifier], lex)); |
55 | |
56 | BOOST_TEST(test_parser("\t \n" , set_state("WS" ) >> lex.white_space, lex)); |
57 | BOOST_TEST(test_parser("\t \n" , in_state("WS" )[lex.white_space], lex)); |
58 | BOOST_TEST(!test_parser("\t \n" , lex.white_space, lex)); |
59 | } |
60 | |
61 | { |
62 | // the tokens class will be initialized inside the test_parser function |
63 | switch_state_tokens<lexer_type> lex; |
64 | |
65 | BOOST_TEST(test_parser(",ident" , lex.identifier, lex, |
66 | in_state("SEP" )[lex.separators])); |
67 | BOOST_TEST(!test_parser(";ident" , set_state("WS" ) >> lex.identifier, |
68 | lex, in_state("SEP" )[lex.separators])); |
69 | BOOST_TEST(!test_parser(",ident" , in_state("WS" )[lex.identifier], |
70 | lex, in_state("SEP" )[lex.separators])); |
71 | |
72 | BOOST_TEST(test_parser(",\t \n" , set_state("WS" ) >> lex.white_space, |
73 | lex, in_state("SEP" )[lex.separators])); |
74 | BOOST_TEST(test_parser(";\t \n" , in_state("WS" )[lex.white_space], |
75 | lex, in_state("SEP" )[lex.separators])); |
76 | BOOST_TEST(!test_parser(",\t \n" , lex.white_space, lex, |
77 | in_state("SEP" )[lex.separators])); |
78 | } |
79 | |
80 | { |
81 | // the tokens class will be initialized inside the test_parser function |
82 | switch_state_tokens<lexer_type> lex; |
83 | |
84 | BOOST_TEST(test_parser("ident\t \n" , |
85 | lex.identifier >> set_state("WS" ) >> lex.white_space, lex)); |
86 | BOOST_TEST(test_parser("\t \nident" , |
87 | in_state("WS" )[lex.white_space] >> lex.identifier, lex)); |
88 | } |
89 | |
90 | return boost::report_errors(); |
91 | } |
92 | |
93 | |