bool* arguments can be used by wrappers
[lqt.git] / cpptoxml / parser / lexer.cpp
blob76591c0c557f76667b5f28e6dc317bd91ab34f4f
1 /****************************************************************************
2 **
3 ** Copyright (C) 1992-2008 Trolltech ASA. All rights reserved.
4 ** Copyright (C) 2002-2005 Roberto Raggi <roberto@kdevelop.org>
5 **
6 ** This file is part of the Qt Script Generator project on Trolltech Labs.
7 **
8 ** This file may be used under the terms of the GNU General Public
9 ** License version 2.0 as published by the Free Software Foundation
10 ** and appearing in the file LICENSE.GPL included in the packaging of
11 ** this file. Please review the following information to ensure GNU
12 ** General Public Licensing requirements will be met:
13 ** http://www.trolltech.com/products/qt/opensource.html
15 ** If you are unsure which license is appropriate for your use, please
16 ** review the following information:
17 ** http://www.trolltech.com/products/qt/licensing.html or contact the
18 ** sales department at sales@trolltech.com.
20 ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
21 ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
23 ****************************************************************************/
26 #include "lexer.h"
27 #include "tokens.h"
28 #include "control.h"
30 #include <cctype>
31 #include <iostream>
33 scan_fun_ptr Lexer::s_scan_keyword_table[] = {
34 &Lexer::scanKeyword0, &Lexer::scanKeyword0,
35 &Lexer::scanKeyword2, &Lexer::scanKeyword3,
36 &Lexer::scanKeyword4, &Lexer::scanKeyword5,
37 &Lexer::scanKeyword6, &Lexer::scanKeyword7,
38 &Lexer::scanKeyword8, &Lexer::scanKeyword9,
39 &Lexer::scanKeyword10, &Lexer::scanKeyword11,
40 &Lexer::scanKeyword12, &Lexer::scanKeyword13,
41 &Lexer::scanKeyword14, &Lexer::scanKeyword0,
42 &Lexer::scanKeyword16
45 void LocationManager::extract_line(int offset, int *line, QString *filename) const
47 *line = 0;
48 if (token_stream.size () < 1)
49 return;
51 const unsigned char *begin_buffer = reinterpret_cast<const unsigned char *>(token_stream[0].text);
52 const unsigned char *cursor = begin_buffer + offset;
54 ++cursor; // skip '#'
55 if (std::isspace(*cursor) && std::isdigit(*(cursor + 1)))
57 ++cursor;
58 char buffer[1024], *cp = buffer;
59 do {
60 *cp++ = *cursor++;
61 } while (std::isdigit(*cursor));
62 *cp = '\0';
63 int l = std::strtol(buffer, 0, 0);
65 Q_ASSERT(std::isspace(*cursor));
66 ++cursor;
68 Q_ASSERT(*cursor == '"');
69 ++cursor;
71 cp = buffer;
72 while (*cursor && *cursor != '"') {
73 *cp++ = *cursor++;
75 *cp = '\0';
76 Q_ASSERT(*cursor == '"');
77 ++cursor;
79 *filename = buffer;
80 *line = l;
81 // printf("filename: %s line: %d\n", buffer, line);
85 void LocationManager::positionAt(std::size_t offset, int *line, int *column,
86 QString *filename) const
88 int ppline, ppcolumn;
89 line_table.positionAt(offset, &ppline, &ppcolumn);
91 int base_line;
92 extract_line((int) line_table[ppline-1], &base_line, filename);
94 int line2, column2;
95 location_table.positionAt((int) line_table[ppline-1], &line2, &column2);
97 location_table.positionAt(offset, line, column);
98 *line = base_line + *line - line2 - 1;
101 scan_fun_ptr Lexer::s_scan_table[256];
102 bool Lexer::s_initialized = false;
104 void Lexer::tokenize(const char *contents, std::size_t size)
106 if (!s_initialized)
107 initialize_scan_table();
109 token_stream.resize(1024);
110 token_stream[0].kind = Token_EOF;
111 token_stream[0].text = contents;
113 index = 1;
115 cursor = (const unsigned char *) contents;
116 begin_buffer = (const unsigned char *) contents;
117 end_buffer = cursor + size;
119 location_table.resize(1024);
120 location_table[0] = 0;
121 location_table.current_line = 1;
123 line_table.resize(1024);
124 line_table[0] = 0;
125 line_table.current_line = 1;
127 do {
128 if (index == token_stream.size())
129 token_stream.resize(token_stream.size() * 2);
131 Token *current_token = &token_stream[(int) index];
132 current_token->text = reinterpret_cast<const char*>(begin_buffer);
133 current_token->position = cursor - begin_buffer;
134 (this->*s_scan_table[*cursor])();
135 current_token->size = cursor - begin_buffer - current_token->position;
136 } while (cursor < end_buffer);
138 if (index == token_stream.size())
139 token_stream.resize(token_stream.size() * 2);
141 Q_ASSERT(index < token_stream.size());
142 token_stream[(int) index].position = cursor - begin_buffer;
143 token_stream[(int) index].kind = Token_EOF;
146 void Lexer::reportError(const QString& msg)
148 int line, column;
149 QString fileName;
151 std::size_t tok = token_stream.cursor();
152 _M_location.positionAt(token_stream.position(tok),
153 &line, &column, &fileName);
155 Control::ErrorMessage errmsg;
156 errmsg.setLine(line + 1);
157 errmsg.setColumn(column);
158 errmsg.setFileName(fileName);
159 errmsg.setMessage(QLatin1String("** LEXER ERROR ") + msg);
160 control->reportError(errmsg);
163 void Lexer::initialize_scan_table()
165 s_initialized = true;
167 for (int i=0; i<256; ++i)
169 if (isspace(i))
170 s_scan_table[i] = &Lexer::scan_white_spaces;
171 else if (isalpha(i) || i == '_')
172 s_scan_table[i] = &Lexer::scan_identifier_or_keyword;
173 else if (isdigit(i))
174 s_scan_table[i] = &Lexer::scan_int_constant;
175 else
176 s_scan_table[i] = &Lexer::scan_invalid_input;
179 s_scan_table[int('L')] = &Lexer::scan_identifier_or_literal;
180 s_scan_table[int('\n')] = &Lexer::scan_newline;
181 s_scan_table[int('#')] = &Lexer::scan_preprocessor;
183 s_scan_table[int('\'')] = &Lexer::scan_char_constant;
184 s_scan_table[int('"')] = &Lexer::scan_string_constant;
186 s_scan_table[int('.')] = &Lexer::scan_int_constant;
188 s_scan_table[int('!')] = &Lexer::scan_not;
189 s_scan_table[int('%')] = &Lexer::scan_remainder;
190 s_scan_table[int('&')] = &Lexer::scan_and;
191 s_scan_table[int('(')] = &Lexer::scan_left_paren;
192 s_scan_table[int(')')] = &Lexer::scan_right_paren;
193 s_scan_table[int('*')] = &Lexer::scan_star;
194 s_scan_table[int('+')] = &Lexer::scan_plus;
195 s_scan_table[int(',')] = &Lexer::scan_comma;
196 s_scan_table[int('-')] = &Lexer::scan_minus;
197 s_scan_table[int('/')] = &Lexer::scan_divide;
198 s_scan_table[int(':')] = &Lexer::scan_colon;
199 s_scan_table[int(';')] = &Lexer::scan_semicolon;
200 s_scan_table[int('<')] = &Lexer::scan_less;
201 s_scan_table[int('=')] = &Lexer::scan_equal;
202 s_scan_table[int('>')] = &Lexer::scan_greater;
203 s_scan_table[int('?')] = &Lexer::scan_question;
204 s_scan_table[int('[')] = &Lexer::scan_left_bracket;
205 s_scan_table[int(']')] = &Lexer::scan_right_bracket;
206 s_scan_table[int('^')] = &Lexer::scan_xor;
207 s_scan_table[int('{')] = &Lexer::scan_left_brace;
208 s_scan_table[int('|')] = &Lexer::scan_or;
209 s_scan_table[int('}')] = &Lexer::scan_right_brace;
210 s_scan_table[int('~')] = &Lexer::scan_tilde;
212 s_scan_table[0] = &Lexer::scan_EOF;
215 void Lexer::scan_preprocessor()
217 if (line_table.current_line == line_table.size())
218 line_table.resize(line_table.current_line * 2);
220 line_table[(int) line_table.current_line++] = (cursor - begin_buffer);
222 while (*cursor && *cursor != '\n')
223 ++cursor;
225 if (*cursor != '\n')
226 reportError("expected newline");
229 void Lexer::scan_char_constant()
231 const unsigned char *begin = cursor;
233 ++cursor;
234 while (*cursor && *cursor != '\'')
236 if (*cursor == '\n')
237 reportError("did not expect newline");
239 if (*cursor == '\\')
240 ++cursor;
241 ++cursor;
244 if (*cursor != '\'')
245 reportError("expected \'");
247 ++cursor;
249 token_stream[(int) index].extra.symbol =
250 control->findOrInsertName((const char*) begin, cursor - begin);
252 token_stream[(int) index++].kind = Token_char_literal;
255 void Lexer::scan_string_constant()
257 const unsigned char *begin = cursor;
259 ++cursor;
260 while (*cursor && *cursor != '"')
262 if (*cursor == '\n')
263 reportError("did not expect newline");
265 if (*cursor == '\\')
266 ++cursor;
267 ++cursor;
270 if (*cursor != '"')
271 reportError("expected \"");
273 ++cursor;
275 token_stream[(int) index].extra.symbol =
276 control->findOrInsertName((const char*) begin, cursor - begin);
278 token_stream[(int) index++].kind = Token_string_literal;
281 void Lexer::scan_newline()
283 if (location_table.current_line == location_table.size())
284 location_table.resize(location_table.current_line * 2);
286 location_table[(int) location_table.current_line++] = (cursor - begin_buffer);
287 ++cursor;
290 void Lexer::scan_white_spaces()
292 while (isspace(*cursor))
294 if (*cursor == '\n')
295 scan_newline();
296 else
297 ++cursor;
301 void Lexer::scan_identifier_or_literal()
303 switch (*(cursor + 1))
305 case '\'':
306 ++cursor;
307 scan_char_constant();
308 break;
310 case '\"':
311 ++cursor;
312 scan_string_constant();
313 break;
315 default:
316 scan_identifier_or_keyword();
317 break;
321 void Lexer::scan_identifier_or_keyword()
323 const unsigned char *skip = cursor;
324 while (isalnum(*skip) || *skip== '_')
325 ++skip;
327 int n = skip - cursor;
328 Token *current_token = &token_stream[(int) index];
329 (this->*s_scan_keyword_table[n < 17 ? n : 0])();
331 if (current_token->kind == Token_identifier)
333 current_token->extra.symbol =
334 control->findOrInsertName((const char*) cursor, n);
337 cursor = skip;
340 void Lexer::scan_int_constant()
342 if (*cursor == '.' && !std::isdigit(*(cursor + 1)))
344 scan_dot();
345 return;
348 const unsigned char *begin = cursor;
350 while (isalnum(*cursor) || *cursor == '.')
351 ++cursor;
353 token_stream[(int) index].extra.symbol =
354 control->findOrInsertName((const char*) begin, cursor - begin);
356 token_stream[(int) index++].kind = Token_number_literal;
359 void Lexer::scan_not()
362 '!' ::= not
363 '!=' ::= not_equal
366 ++cursor;
368 if (*cursor == '=')
370 ++cursor;
371 token_stream[(int) index++].kind = Token_not_eq;
373 else
375 token_stream[(int) index++].kind = '!';
379 void Lexer::scan_remainder()
382 '%' ::= remainder
383 '%=' ::= remainder_equal
386 ++cursor;
388 if (*cursor == '=')
390 ++cursor;
391 token_stream[(int) index++].kind = Token_assign;
393 else
395 token_stream[(int) index++].kind = '%';
399 void Lexer::scan_and()
402 '&&' ::= and_and
403 '&' ::= and
404 '&=' ::= and_equal
407 ++cursor;
408 if (*cursor == '=')
410 ++cursor;
411 token_stream[(int) index++].kind = Token_assign;
413 else if (*cursor == '&')
415 ++cursor;
416 token_stream[(int) index++].kind = Token_and;
418 else
420 token_stream[(int) index++].kind = '&';
424 void Lexer::scan_left_paren()
426 ++cursor;
427 token_stream[(int) index++].kind = '(';
430 void Lexer::scan_right_paren()
432 ++cursor;
433 token_stream[(int) index++].kind = ')';
436 void Lexer::scan_star()
439 '*' ::= star
440 '*=' ::= star_equal
443 ++cursor;
445 if (*cursor == '=')
447 ++cursor;
448 token_stream[(int) index++].kind = Token_assign;
450 else
452 token_stream[(int) index++].kind = '*';
456 void Lexer::scan_plus()
459 '+' ::= plus
460 '++' ::= incr
461 '+=' ::= plus_equal
464 ++cursor;
465 if (*cursor == '=')
467 ++cursor;
468 token_stream[(int) index++].kind = Token_assign;
470 else if (*cursor == '+')
472 ++cursor;
473 token_stream[(int) index++].kind = Token_incr;
475 else
477 token_stream[(int) index++].kind = '+';
481 void Lexer::scan_comma()
483 ++cursor;
484 token_stream[(int) index++].kind = ',';
487 void Lexer::scan_minus()
490 '-' ::= minus
491 '--' ::= decr
492 '-=' ::= minus_equal
493 '->' ::= left_arrow
496 ++cursor;
497 if (*cursor == '=')
499 ++cursor;
500 token_stream[(int) index++].kind = Token_assign;
502 else if (*cursor == '-')
504 ++cursor;
505 token_stream[(int) index++].kind = Token_decr;
507 else if (*cursor == '>')
509 ++cursor;
510 token_stream[(int) index++].kind = Token_arrow;
511 if (*cursor == '*')
513 ++cursor;
514 token_stream[(int) index++].kind = Token_ptrmem;
517 else
519 token_stream[(int) index++].kind = '-';
523 void Lexer::scan_dot()
526 '.' ::= dot
527 '...' ::= ellipsis
530 ++cursor;
531 if (*cursor == '.' && *(cursor + 1) == '.')
533 cursor += 2;
534 token_stream[(int) index++].kind = Token_ellipsis;
536 else if (*cursor == '.' && *(cursor + 1) == '*')
538 cursor += 2;
539 token_stream[(int) index++].kind = Token_ptrmem;
541 else
542 token_stream[(int) index++].kind = '.';
545 void Lexer::scan_divide()
548 '/' ::= divide
549 '/=' ::= divide_equal
552 ++cursor;
554 if (*cursor == '=')
556 ++cursor;
557 token_stream[(int) index++].kind = Token_assign;
559 else
561 token_stream[(int) index++].kind = '/';
565 void Lexer::scan_colon()
567 ++cursor;
568 if (*cursor == ':')
570 ++cursor;
571 token_stream[(int) index++].kind = Token_scope;
573 else
575 token_stream[(int) index++].kind = ':';
579 void Lexer::scan_semicolon()
581 ++cursor;
582 token_stream[(int) index++].kind = ';';
585 void Lexer::scan_less()
588 '<' ::= less
589 '<<' ::= left_shift
590 '<<=' ::= left_shift_equal
591 '<=' ::= less_equal
594 ++cursor;
595 if (*cursor == '=')
597 ++cursor;
598 token_stream[(int) index++].kind = Token_leq;
600 else if (*cursor == '<')
602 ++cursor;
603 if (*cursor == '=')
605 ++cursor;
606 token_stream[(int) index++].kind = Token_assign;
608 else
610 token_stream[(int) index++].kind = Token_shift;
613 else
615 token_stream[(int) index++].kind = '<';
619 void Lexer::scan_equal()
622 '=' ::= equal
623 '==' ::= equal_equal
625 ++cursor;
627 if (*cursor == '=')
629 ++cursor;
630 token_stream[(int) index++].kind = Token_eq;
632 else
634 token_stream[(int) index++].kind = '=';
638 void Lexer::scan_greater()
641 '>' ::= greater
642 '>=' ::= greater_equal
643 '>>' ::= right_shift
644 '>>=' ::= right_shift_equal
647 ++cursor;
648 if (*cursor == '=')
650 ++cursor;
651 token_stream[(int) index++].kind = Token_geq;
653 else if (*cursor == '>')
655 ++cursor;
656 if (*cursor == '=')
658 ++cursor;
659 token_stream[(int) index++].kind = Token_assign;
661 else
663 token_stream[(int) index++].kind = Token_shift;
666 else
668 token_stream[(int) index++].kind = '>';
672 void Lexer::scan_question()
674 ++cursor;
675 token_stream[(int) index++].kind = '?';
678 void Lexer::scan_left_bracket()
680 ++cursor;
681 token_stream[(int) index++].kind = '[';
684 void Lexer::scan_right_bracket()
686 ++cursor;
687 token_stream[(int) index++].kind = ']';
690 void Lexer::scan_xor()
693 '^' ::= xor
694 '^=' ::= xor_equal
696 ++cursor;
698 if (*cursor == '=')
700 ++cursor;
701 token_stream[(int) index++].kind = Token_assign;
703 else
705 token_stream[(int) index++].kind = '^';
709 void Lexer::scan_left_brace()
711 ++cursor;
712 token_stream[(int) index++].kind = '{';
715 void Lexer::scan_or()
718 '|' ::= or
719 '|=' ::= or_equal
720 '||' ::= or_or
722 ++cursor;
723 if (*cursor == '=')
725 ++cursor;
726 token_stream[(int) index++].kind = Token_assign;
728 else if (*cursor == '|')
730 ++cursor;
731 token_stream[(int) index++].kind = Token_or;
733 else
735 token_stream[(int) index++].kind = '|';
739 void Lexer::scan_right_brace()
741 ++cursor;
742 token_stream[(int) index++].kind = '}';
745 void Lexer::scan_tilde()
747 ++cursor;
748 token_stream[(int) index++].kind = '~';
751 void Lexer::scan_EOF()
753 ++cursor;
754 token_stream[(int) index++].kind = Token_EOF;
757 void Lexer::scan_invalid_input()
759 QString errmsg("invalid input: %1");
760 errmsg.arg(int(*cursor));
761 reportError(errmsg);
762 ++cursor;
765 void LocationTable::positionAt(std::size_t offset, int max_line,
766 int *line, int *column) const
768 if (!(line && column && max_line != 0))
769 return;
771 int first = 0;
772 int len = max_line;
773 int half;
774 int middle;
776 while (len > 0)
778 half = len >> 1;
779 middle = first;
781 middle += half;
783 if (lines[middle] < offset)
785 first = middle;
786 ++first;
787 len = len - half - 1;
789 else
790 len = half;
793 *line = std::max(first, 1);
794 *column = (int) (offset - lines[*line - 1] - 1);
796 if (*column < 0)
798 *column = 0;
802 void Lexer::scanKeyword0()
804 token_stream[(int) index++].kind = Token_identifier;
807 void Lexer::scanKeyword2()
809 switch (*cursor)
811 case 'i':
812 if (*(cursor + 1) == 'f')
814 token_stream[(int) index++].kind = Token_if;
815 return;
817 break;
819 case 'd':
820 if (*(cursor + 1) == 'o')
822 token_stream[(int) index++].kind = Token_do;
823 return;
825 break;
827 case 'o':
828 if (*(cursor + 1) == 'r')
830 token_stream[(int) index++].kind = Token_or;
831 return;
833 break;
836 token_stream[(int) index++].kind = Token_identifier;
839 void Lexer::scanKeyword3()
841 switch (*cursor)
843 case 'a':
844 if (*(cursor + 1) == 'n' &&
845 *(cursor + 2) == 'd')
847 token_stream[(int) index++].kind = Token_and;
848 return;
850 if (*(cursor + 1) == 's' &&
851 *(cursor + 2) == 'm')
853 token_stream[(int) index++].kind = Token_asm;
854 return;
856 break;
858 case 'f':
859 if (*(cursor + 1) == 'o' &&
860 *(cursor + 2) == 'r')
862 token_stream[(int) index++].kind = Token_for;
863 return;
865 break;
867 case 'i':
868 if (*(cursor + 1) == 'n' &&
869 *(cursor + 2) == 't')
871 token_stream[(int) index++].kind = Token_int;
872 return;
874 break;
876 case 'n':
877 if (*(cursor + 1) == 'e' &&
878 *(cursor + 2) == 'w')
880 token_stream[(int) index++].kind = Token_new;
881 return;
883 if (*(cursor + 1) == 'o' &&
884 *(cursor + 2) == 't')
886 token_stream[(int) index++].kind = Token_not;
887 return;
889 break;
891 case 't':
892 if (*(cursor + 1) == 'r' &&
893 *(cursor + 2) == 'y')
895 token_stream[(int) index++].kind = Token_try;
896 return;
898 break;
900 case 'x':
901 if (*(cursor + 1) == 'o' &&
902 *(cursor + 2) == 'r')
904 token_stream[(int) index++].kind = Token_xor;
905 return;
907 break;
910 token_stream[(int) index++].kind = Token_identifier;
913 void Lexer::scanKeyword4()
915 switch (*cursor)
917 case 'a':
918 if (*(cursor + 1) == 'u' &&
919 *(cursor + 2) == 't' &&
920 *(cursor + 3) == 'o')
922 token_stream[(int) index++].kind = Token_auto;
923 return;
925 break;
927 case 'c':
928 if (*(cursor + 1) == 'a' &&
929 *(cursor + 2) == 's' &&
930 *(cursor + 3) == 'e')
932 token_stream[(int) index++].kind = Token_case;
933 return;
935 if (*(cursor + 1) == 'h' &&
936 *(cursor + 2) == 'a' &&
937 *(cursor + 3) == 'r')
939 token_stream[(int) index++].kind = Token_char;
940 return;
942 break;
944 case 'b':
945 if (*(cursor + 1) == 'o' &&
946 *(cursor + 2) == 'o' &&
947 *(cursor + 3) == 'l')
949 token_stream[(int) index++].kind = Token_bool;
950 return;
952 break;
954 case 'e':
955 if (*(cursor + 1) == 'l' &&
956 *(cursor + 2) == 's' &&
957 *(cursor + 3) == 'e')
959 token_stream[(int) index++].kind = Token_else;
960 return;
962 if (*(cursor + 1) == 'm' &&
963 *(cursor + 2) == 'i' &&
964 *(cursor + 3) == 't')
966 token_stream[(int) index++].kind = Token_emit;
967 return;
969 if (*(cursor + 1) == 'n' &&
970 *(cursor + 2) == 'u' &&
971 *(cursor + 3) == 'm')
973 token_stream[(int) index++].kind = Token_enum;
974 return;
976 break;
978 case 'g':
979 if (*(cursor + 1) == 'o' &&
980 *(cursor + 2) == 't' &&
981 *(cursor + 3) == 'o')
983 token_stream[(int) index++].kind = Token_goto;
984 return;
986 break;
988 case 'l':
989 if (*(cursor + 1) == 'o' &&
990 *(cursor + 2) == 'n' &&
991 *(cursor + 3) == 'g')
993 token_stream[(int) index++].kind = Token_long;
994 return;
996 break;
998 case 't':
999 if (*(cursor + 1) == 'h' &&
1000 *(cursor + 2) == 'i' &&
1001 *(cursor + 3) == 's')
1003 token_stream[(int) index++].kind = Token_this;
1004 return;
1006 break;
1008 case 'v':
1009 if (*(cursor + 1) == 'o' &&
1010 *(cursor + 2) == 'i' &&
1011 *(cursor + 3) == 'd')
1013 token_stream[(int) index++].kind = Token_void;
1014 return;
1016 break;
1019 token_stream[(int) index++].kind = Token_identifier;
1022 void Lexer::scanKeyword5()
1024 switch (*cursor)
1026 case 'c':
1027 if (*(cursor + 1) == 'a' &&
1028 *(cursor + 2) == 't' &&
1029 *(cursor + 3) == 'c' &&
1030 *(cursor + 4) == 'h')
1032 token_stream[(int) index++].kind = Token_catch;
1033 return;
1035 if (*(cursor + 1) == 'l' &&
1036 *(cursor + 2) == 'a' &&
1037 *(cursor + 3) == 's' &&
1038 *(cursor + 4) == 's')
1040 token_stream[(int) index++].kind = Token_class;
1041 return;
1043 if (*(cursor + 1) == 'o' &&
1044 *(cursor + 2) == 'm' &&
1045 *(cursor + 3) == 'p' &&
1046 *(cursor + 4) == 'l')
1048 token_stream[(int) index++].kind = Token_compl;
1049 return;
1051 if (*(cursor + 1) == 'o' &&
1052 *(cursor + 2) == 'n' &&
1053 *(cursor + 3) == 's' &&
1054 *(cursor + 4) == 't')
1056 token_stream[(int) index++].kind = Token_const;
1057 return;
1059 break;
1061 case 'b':
1062 if (*(cursor + 1) == 'i' &&
1063 *(cursor + 2) == 't' &&
1064 *(cursor + 3) == 'o' &&
1065 *(cursor + 4) == 'r')
1067 token_stream[(int) index++].kind = Token_bitor;
1068 return;
1070 if (*(cursor + 1) == 'r' &&
1071 *(cursor + 2) == 'e' &&
1072 *(cursor + 3) == 'a' &&
1073 *(cursor + 4) == 'k')
1075 token_stream[(int) index++].kind = Token_break;
1076 return;
1078 break;
1080 case 'f':
1081 if (*(cursor + 1) == 'l' &&
1082 *(cursor + 2) == 'o' &&
1083 *(cursor + 3) == 'a' &&
1084 *(cursor + 4) == 't')
1086 token_stream[(int) index++].kind = Token_float;
1087 return;
1089 break;
1091 case 'o':
1092 if (*(cursor + 1) == 'r' &&
1093 *(cursor + 2) == '_' &&
1094 *(cursor + 3) == 'e' &&
1095 *(cursor + 4) == 'q')
1097 token_stream[(int) index++].kind = Token_or_eq;
1098 return;
1100 break;
1102 case 's':
1103 if (*(cursor + 1) == 'h' &&
1104 *(cursor + 2) == 'o' &&
1105 *(cursor + 3) == 'r' &&
1106 *(cursor + 4) == 't')
1108 token_stream[(int) index++].kind = Token_short;
1109 return;
1111 if (*(cursor + 1) == 'l' &&
1112 *(cursor + 2) == 'o' &&
1113 *(cursor + 3) == 't' &&
1114 *(cursor + 4) == 's')
1116 token_stream[(int) index++].kind = Token_slots;
1117 return;
1119 break;
1121 case 'u':
1122 if (*(cursor + 1) == 'n' &&
1123 *(cursor + 2) == 'i' &&
1124 *(cursor + 3) == 'o' &&
1125 *(cursor + 4) == 'n')
1127 token_stream[(int) index++].kind = Token_union;
1128 return;
1130 if (*(cursor + 1) == 's' &&
1131 *(cursor + 2) == 'i' &&
1132 *(cursor + 3) == 'n' &&
1133 *(cursor + 4) == 'g')
1135 token_stream[(int) index++].kind = Token_using;
1136 return;
1138 break;
1140 case 't':
1141 if (*(cursor + 1) == 'h' &&
1142 *(cursor + 2) == 'r' &&
1143 *(cursor + 3) == 'o' &&
1144 *(cursor + 4) == 'w')
1146 token_stream[(int) index++].kind = Token_throw;
1147 return;
1149 break;
1151 case 'w':
1152 if (*(cursor + 1) == 'h' &&
1153 *(cursor + 2) == 'i' &&
1154 *(cursor + 3) == 'l' &&
1155 *(cursor + 4) == 'e')
1157 token_stream[(int) index++].kind = Token_while;
1158 return;
1160 break;
1163 token_stream[(int) index++].kind = Token_identifier;
1166 void Lexer::scanKeyword6()
1168 switch (*cursor)
1170 case 'a':
1171 if (*(cursor + 1) == 'n' &&
1172 *(cursor + 2) == 'd' &&
1173 *(cursor + 3) == '_' &&
1174 *(cursor + 4) == 'e' &&
1175 *(cursor + 5) == 'q')
1177 token_stream[(int) index++].kind = Token_and_eq;
1178 return;
1180 break;
1182 case 'b':
1183 if (*(cursor + 1) == 'i' &&
1184 *(cursor + 2) == 't' &&
1185 *(cursor + 3) == 'a' &&
1186 *(cursor + 4) == 'n' &&
1187 *(cursor + 5) == 'd')
1189 token_stream[(int) index++].kind = Token_bitand;
1190 return;
1192 break;
1194 case 'e':
1195 if (*(cursor + 1) == 'x' &&
1196 *(cursor + 2) == 'p' &&
1197 *(cursor + 3) == 'o' &&
1198 *(cursor + 4) == 'r' &&
1199 *(cursor + 5) == 't')
1201 token_stream[(int) index++].kind = Token_export;
1202 return;
1204 if (*(cursor + 1) == 'x' &&
1205 *(cursor + 2) == 't' &&
1206 *(cursor + 3) == 'e' &&
1207 *(cursor + 4) == 'r' &&
1208 *(cursor + 5) == 'n')
1210 token_stream[(int) index++].kind = Token_extern;
1211 return;
1213 break;
1215 case 'd':
1216 if (*(cursor + 1) == 'e' &&
1217 *(cursor + 2) == 'l' &&
1218 *(cursor + 3) == 'e' &&
1219 *(cursor + 4) == 't' &&
1220 *(cursor + 5) == 'e')
1222 token_stream[(int) index++].kind = Token_delete;
1223 return;
1225 if (*(cursor + 1) == 'o' &&
1226 *(cursor + 2) == 'u' &&
1227 *(cursor + 3) == 'b' &&
1228 *(cursor + 4) == 'l' &&
1229 *(cursor + 5) == 'e')
1231 token_stream[(int) index++].kind = Token_double;
1232 return;
1234 break;
1236 case 'f':
1237 if (*(cursor + 1) == 'r' &&
1238 *(cursor + 2) == 'i' &&
1239 *(cursor + 3) == 'e' &&
1240 *(cursor + 4) == 'n' &&
1241 *(cursor + 5) == 'd')
1243 token_stream[(int) index++].kind = Token_friend;
1244 return;
1246 break;
1248 case 'i':
1249 if (*(cursor + 1) == 'n' &&
1250 *(cursor + 2) == 'l' &&
1251 *(cursor + 3) == 'i' &&
1252 *(cursor + 4) == 'n' &&
1253 *(cursor + 5) == 'e')
1255 token_stream[(int) index++].kind = Token_inline;
1256 return;
1258 break;
1260 case 'K':
1261 if (*(cursor + 1) == '_' &&
1262 *(cursor + 2) == 'D' &&
1263 *(cursor + 3) == 'C' &&
1264 *(cursor + 4) == 'O' &&
1265 *(cursor + 5) == 'P')
1267 token_stream[(int) index++].kind = Token_K_DCOP;
1268 return;
1270 break;
1272 case 'n':
1273 if (*(cursor + 1) == 'o' &&
1274 *(cursor + 2) == 't' &&
1275 *(cursor + 3) == '_' &&
1276 *(cursor + 4) == 'e' &&
1277 *(cursor + 5) == 'q')
1279 token_stream[(int) index++].kind = Token_not_eq;
1280 return;
1282 break;
1284 case 'p':
1285 if (*(cursor + 1) == 'u' &&
1286 *(cursor + 2) == 'b' &&
1287 *(cursor + 3) == 'l' &&
1288 *(cursor + 4) == 'i' &&
1289 *(cursor + 5) == 'c')
1291 token_stream[(int) index++].kind = Token_public;
1292 return;
1294 break;
1296 case 's':
1297 if (*(cursor + 1) == 'i' &&
1298 *(cursor + 2) == 'g' &&
1299 *(cursor + 3) == 'n' &&
1300 *(cursor + 4) == 'e' &&
1301 *(cursor + 5) == 'd')
1303 token_stream[(int) index++].kind = Token_signed;
1304 return;
1306 if (*(cursor + 1) == 'i' &&
1307 *(cursor + 2) == 'z' &&
1308 *(cursor + 3) == 'e' &&
1309 *(cursor + 4) == 'o' &&
1310 *(cursor + 5) == 'f')
1312 token_stream[(int) index++].kind = Token_sizeof;
1313 return;
1315 if (*(cursor + 1) == 't' &&
1316 *(cursor + 2) == 'a' &&
1317 *(cursor + 3) == 't' &&
1318 *(cursor + 4) == 'i' &&
1319 *(cursor + 5) == 'c')
1321 token_stream[(int) index++].kind = Token_static;
1322 return;
1324 if (*(cursor + 1) == 't' &&
1325 *(cursor + 2) == 'r' &&
1326 *(cursor + 3) == 'u' &&
1327 *(cursor + 4) == 'c' &&
1328 *(cursor + 5) == 't')
1330 token_stream[(int) index++].kind = Token_struct;
1331 return;
1333 if (*(cursor + 1) == 'w' &&
1334 *(cursor + 2) == 'i' &&
1335 *(cursor + 3) == 't' &&
1336 *(cursor + 4) == 'c' &&
1337 *(cursor + 5) == 'h')
1339 token_stream[(int) index++].kind = Token_switch;
1340 return;
1342 break;
1344 case 'r':
1345 if (*(cursor + 1) == 'e' &&
1346 *(cursor + 2) == 't' &&
1347 *(cursor + 3) == 'u' &&
1348 *(cursor + 4) == 'r' &&
1349 *(cursor + 5) == 'n')
1351 token_stream[(int) index++].kind = Token_return;
1352 return;
1354 break;
1356 case 't':
1357 if (*(cursor + 1) == 'y' &&
1358 *(cursor + 2) == 'p' &&
1359 *(cursor + 3) == 'e' &&
1360 *(cursor + 4) == 'i' &&
1361 *(cursor + 5) == 'd')
1363 token_stream[(int) index++].kind = Token_typeid;
1364 return;
1366 break;
1368 case 'x':
1369 if (*(cursor + 1) == 'o' &&
1370 *(cursor + 2) == 'r' &&
1371 *(cursor + 3) == '_' &&
1372 *(cursor + 4) == 'e' &&
1373 *(cursor + 5) == 'q')
1375 token_stream[(int) index++].kind = Token_xor_eq;
1376 return;
1378 break;
1380 case 'k':
1381 if (*(cursor + 1) == '_' &&
1382 *(cursor + 2) == 'd' &&
1383 *(cursor + 3) == 'c' &&
1384 *(cursor + 4) == 'o' &&
1385 *(cursor + 5) == 'p')
1387 token_stream[(int) index++].kind = Token_k_dcop;
1388 return;
1390 break;
1393 token_stream[(int) index++].kind = Token_identifier;
1396 void Lexer::scanKeyword7()
1398 switch (*cursor)
1400 case 'd':
1401 if (*(cursor + 1) == 'e' &&
1402 *(cursor + 2) == 'f' &&
1403 *(cursor + 3) == 'a' &&
1404 *(cursor + 4) == 'u' &&
1405 *(cursor + 5) == 'l' &&
1406 *(cursor + 6) == 't')
1408 token_stream[(int) index++].kind = Token_default;
1409 return;
1411 break;
1413 case 'm':
1414 if (*(cursor + 1) == 'u' &&
1415 *(cursor + 2) == 't' &&
1416 *(cursor + 3) == 'a' &&
1417 *(cursor + 4) == 'b' &&
1418 *(cursor + 5) == 'l' &&
1419 *(cursor + 6) == 'e')
1421 token_stream[(int) index++].kind = Token_mutable;
1422 return;
1424 break;
1426 case 'p':
1427 if (*(cursor + 1) == 'r' &&
1428 *(cursor + 2) == 'i' &&
1429 *(cursor + 3) == 'v' &&
1430 *(cursor + 4) == 'a' &&
1431 *(cursor + 5) == 't' &&
1432 *(cursor + 6) == 'e')
1434 token_stream[(int) index++].kind = Token_private;
1435 return;
1437 break;
1438 case 's':
1439 if (*(cursor + 1) == 'i' &&
1440 *(cursor + 2) == 'g' &&
1441 *(cursor + 3) == 'n' &&
1442 *(cursor + 4) == 'a' &&
1443 *(cursor + 5) == 'l' &&
1444 *(cursor + 6) == 's')
1446 token_stream[(int) index++].kind = Token_signals;
1447 return;
1449 break;
1450 case 't':
1451 if (*(cursor + 1) == 'y' &&
1452 *(cursor + 2) == 'p' &&
1453 *(cursor + 3) == 'e' &&
1454 *(cursor + 4) == 'd' &&
1455 *(cursor + 5) == 'e' &&
1456 *(cursor + 6) == 'f')
1458 token_stream[(int) index++].kind = Token_typedef;
1459 return;
1461 break;
1463 case 'v':
1464 if (*(cursor + 1) == 'i' &&
1465 *(cursor + 2) == 'r' &&
1466 *(cursor + 3) == 't' &&
1467 *(cursor + 4) == 'u' &&
1468 *(cursor + 5) == 'a' &&
1469 *(cursor + 6) == 'l')
1471 token_stream[(int) index++].kind = Token_virtual;
1472 return;
1474 break;
1476 case 'Q':
1477 if (*(cursor + 1) == '_' &&
1478 *(cursor + 2) == 'E' &&
1479 *(cursor + 3) == 'N' &&
1480 *(cursor + 4) == 'U' &&
1481 *(cursor + 5) == 'M' &&
1482 *(cursor + 6) == 'S')
1484 token_stream[(int) index++].kind = Token_Q_ENUMS;
1485 return;
1487 break;
1490 token_stream[(int) index++].kind = Token_identifier;
1493 void Lexer::scanKeyword8()
1495 switch (*cursor)
1497 case '_':
1498 if (*(cursor + 1) == '_' &&
1499 *(cursor + 2) == 't' &&
1500 *(cursor + 3) == 'y' &&
1501 *(cursor + 4) == 'p' &&
1502 *(cursor + 5) == 'e' &&
1503 *(cursor + 6) == 'o' &&
1504 *(cursor + 7) == 'f')
1506 token_stream[(int) index++].kind = Token___typeof;
1507 return;
1509 break;
1511 case 'c':
1512 if (*(cursor + 1) == 'o' &&
1513 *(cursor + 2) == 'n' &&
1514 *(cursor + 3) == 't' &&
1515 *(cursor + 4) == 'i' &&
1516 *(cursor + 5) == 'n' &&
1517 *(cursor + 6) == 'u' &&
1518 *(cursor + 7) == 'e')
1520 token_stream[(int) index++].kind = Token_continue;
1521 return;
1523 break;
1525 case 'e':
1526 if (*(cursor + 1) == 'x' &&
1527 *(cursor + 2) == 'p' &&
1528 *(cursor + 3) == 'l' &&
1529 *(cursor + 4) == 'i' &&
1530 *(cursor + 5) == 'c' &&
1531 *(cursor + 6) == 'i' &&
1532 *(cursor + 7) == 't')
1534 token_stream[(int) index++].kind = Token_explicit;
1535 return;
1537 break;
1539 case 'o':
1540 if (*(cursor + 1) == 'p' &&
1541 *(cursor + 2) == 'e' &&
1542 *(cursor + 3) == 'r' &&
1543 *(cursor + 4) == 'a' &&
1544 *(cursor + 5) == 't' &&
1545 *(cursor + 6) == 'o' &&
1546 *(cursor + 7) == 'r')
1548 token_stream[(int) index++].kind = Token_operator;
1549 return;
1551 break;
1553 case 'Q':
1554 if (*(cursor + 1) == '_' &&
1555 *(cursor + 2) == 'O' &&
1556 *(cursor + 3) == 'B' &&
1557 *(cursor + 4) == 'J' &&
1558 *(cursor + 5) == 'E' &&
1559 *(cursor + 6) == 'C' &&
1560 *(cursor + 7) == 'T')
1562 token_stream[(int) index++].kind = Token_Q_OBJECT;
1563 return;
1565 break;
1567 case 'r':
1568 if (*(cursor + 1) == 'e' &&
1569 *(cursor + 2) == 'g' &&
1570 *(cursor + 3) == 'i' &&
1571 *(cursor + 4) == 's' &&
1572 *(cursor + 5) == 't' &&
1573 *(cursor + 6) == 'e' &&
1574 *(cursor + 7) == 'r')
1576 token_stream[(int) index++].kind = Token_register;
1577 return;
1579 break;
1581 case 'u':
1582 if (*(cursor + 1) == 'n' &&
1583 *(cursor + 2) == 's' &&
1584 *(cursor + 3) == 'i' &&
1585 *(cursor + 4) == 'g' &&
1586 *(cursor + 5) == 'n' &&
1587 *(cursor + 6) == 'e' &&
1588 *(cursor + 7) == 'd')
1590 token_stream[(int) index++].kind = Token_unsigned;
1591 return;
1593 break;
1595 case 't':
1596 if (*(cursor + 1) == 'e' &&
1597 *(cursor + 2) == 'm' &&
1598 *(cursor + 3) == 'p' &&
1599 *(cursor + 4) == 'l' &&
1600 *(cursor + 5) == 'a' &&
1601 *(cursor + 6) == 't' &&
1602 *(cursor + 7) == 'e')
1604 token_stream[(int) index++].kind = Token_template;
1605 return;
1607 if (*(cursor + 1) == 'y' &&
1608 *(cursor + 2) == 'p' &&
1609 *(cursor + 3) == 'e' &&
1610 *(cursor + 4) == 'n' &&
1611 *(cursor + 5) == 'a' &&
1612 *(cursor + 6) == 'm' &&
1613 *(cursor + 7) == 'e')
1615 token_stream[(int) index++].kind = Token_typename;
1616 return;
1618 break;
1620 case 'v':
1621 if (*(cursor + 1) == 'o' &&
1622 *(cursor + 2) == 'l' &&
1623 *(cursor + 3) == 'a' &&
1624 *(cursor + 4) == 't' &&
1625 *(cursor + 5) == 'i' &&
1626 *(cursor + 6) == 'l' &&
1627 *(cursor + 7) == 'e')
1629 token_stream[(int) index++].kind = Token_volatile;
1630 return;
1632 break;
1635 token_stream[(int) index++].kind = Token_identifier;
1638 void Lexer::scanKeyword9()
1640 switch (*cursor)
1642 case 'p':
1643 if (*(cursor + 1) == 'r' &&
1644 *(cursor + 2) == 'o' &&
1645 *(cursor + 3) == 't' &&
1646 *(cursor + 4) == 'e' &&
1647 *(cursor + 5) == 'c' &&
1648 *(cursor + 6) == 't' &&
1649 *(cursor + 7) == 'e' &&
1650 *(cursor + 8) == 'd')
1652 token_stream[(int) index++].kind = Token_protected;
1653 return;
1655 break;
1657 case 'n':
1658 if (*(cursor + 1) == 'a' &&
1659 *(cursor + 2) == 'm' &&
1660 *(cursor + 3) == 'e' &&
1661 *(cursor + 4) == 's' &&
1662 *(cursor + 5) == 'p' &&
1663 *(cursor + 6) == 'a' &&
1664 *(cursor + 7) == 'c' &&
1665 *(cursor + 8) == 'e')
1667 token_stream[(int) index++].kind = Token_namespace;
1668 return;
1670 break;
1673 token_stream[(int) index++].kind = Token_identifier;
1676 void Lexer::scanKeyword10()
1678 switch (*cursor)
1680 case 'c':
1681 if (*(cursor + 1) == 'o' &&
1682 *(cursor + 2) == 'n' &&
1683 *(cursor + 3) == 's' &&
1684 *(cursor + 4) == 't' &&
1685 *(cursor + 5) == '_' &&
1686 *(cursor + 6) == 'c' &&
1687 *(cursor + 7) == 'a' &&
1688 *(cursor + 8) == 's' &&
1689 *(cursor + 9) == 't')
1691 token_stream[(int) index++].kind = Token_const_cast;
1692 return;
1694 break;
1696 case 'Q':
1697 if (*(cursor + 1) == '_' &&
1698 *(cursor + 2) == 'P' &&
1699 *(cursor + 3) == 'R' &&
1700 *(cursor + 4) == 'O' &&
1701 *(cursor + 5) == 'P' &&
1702 *(cursor + 6) == 'E' &&
1703 *(cursor + 7) == 'R' &&
1704 *(cursor + 8) == 'T' &&
1705 *(cursor + 9) == 'Y')
1707 token_stream[(int) index++].kind = Token_Q_PROPERTY;
1708 return;
1711 break;
1714 token_stream[(int) index++].kind = Token_identifier;
1717 void Lexer::scanKeyword11()
1719 switch (*cursor)
1721 case 'Q':
1722 if (*(cursor + 1) == '_' &&
1723 *(cursor + 2) == 'I' &&
1724 *(cursor + 3) == 'N' &&
1725 *(cursor + 4) == 'V' &&
1726 *(cursor + 5) == 'O' &&
1727 *(cursor + 6) == 'K' &&
1728 *(cursor + 7) == 'A' &&
1729 *(cursor + 8) == 'B' &&
1730 *(cursor + 9) == 'L' &&
1731 *(cursor + 10) == 'E')
1733 token_stream[(int) index++].kind = Token_Q_INVOKABLE;
1734 return;
1736 break;
1738 case 's':
1739 if (*(cursor + 1) == 't' &&
1740 *(cursor + 2) == 'a' &&
1741 *(cursor + 3) == 't' &&
1742 *(cursor + 4) == 'i' &&
1743 *(cursor + 5) == 'c' &&
1744 *(cursor + 6) == '_' &&
1745 *(cursor + 7) == 'c' &&
1746 *(cursor + 8) == 'a' &&
1747 *(cursor + 9) == 's' &&
1748 *(cursor + 10) == 't')
1750 token_stream[(int) index++].kind = Token_static_cast;
1751 return;
1753 break;
1756 token_stream[(int) index++].kind = Token_identifier;
1759 void Lexer::scanKeyword12()
1761 switch (*cursor)
1763 case 'd':
1764 if (*(cursor + 1) == 'y' &&
1765 *(cursor + 2) == 'n' &&
1766 *(cursor + 3) == 'a' &&
1767 *(cursor + 4) == 'm' &&
1768 *(cursor + 5) == 'i' &&
1769 *(cursor + 6) == 'c' &&
1770 *(cursor + 7) == '_' &&
1771 *(cursor + 8) == 'c' &&
1772 *(cursor + 9) == 'a' &&
1773 *(cursor + 10) == 's' &&
1774 *(cursor + 11) == 't')
1776 token_stream[(int) index++].kind = Token_dynamic_cast;
1777 return;
1779 break;
1782 token_stream[(int) index++].kind = Token_identifier;
1785 void Lexer::scanKeyword13()
1787 switch (*cursor)
1789 case '_':
1790 if (*(cursor + 1) == '_' &&
1791 *(cursor + 2) == 'a' &&
1792 *(cursor + 3) == 't' &&
1793 *(cursor + 4) == 't' &&
1794 *(cursor + 5) == 'r' &&
1795 *(cursor + 6) == 'i' &&
1796 *(cursor + 7) == 'b' &&
1797 *(cursor + 8) == 'u' &&
1798 *(cursor + 9) == 't' &&
1799 *(cursor + 10) == 'e' &&
1800 *(cursor + 11) == '_' &&
1801 *(cursor + 12) == '_')
1803 token_stream[(int) index++].kind = Token___attribute__;
1804 return;
1806 break;
1808 token_stream[(int) index++].kind = Token_identifier;
1811 void Lexer::scanKeyword14()
1813 switch (*cursor)
1815 case 'k':
1816 if (*(cursor + 1) == '_' &&
1817 *(cursor + 2) == 'd' &&
1818 *(cursor + 3) == 'c' &&
1819 *(cursor + 4) == 'o' &&
1820 *(cursor + 5) == 'p' &&
1821 *(cursor + 6) == '_' &&
1822 *(cursor + 7) == 's' &&
1823 *(cursor + 8) == 'i' &&
1824 *(cursor + 9) == 'g' &&
1825 *(cursor + 10) == 'n' &&
1826 *(cursor + 11) == 'a' &&
1827 *(cursor + 12) == 'l' &&
1828 *(cursor + 13) == 's')
1830 token_stream[(int) index++].kind = Token_k_dcop_signals;
1831 return;
1833 break;
1835 token_stream[(int) index++].kind = Token_identifier;
1838 void Lexer::scanKeyword16()
1840 switch (*cursor)
1842 case 'r':
1843 if (*(cursor + 1) == 'e' &&
1844 *(cursor + 2) == 'i' &&
1845 *(cursor + 3) == 'n' &&
1846 *(cursor + 4) == 't' &&
1847 *(cursor + 5) == 'e' &&
1848 *(cursor + 6) == 'r' &&
1849 *(cursor + 7) == 'p' &&
1850 *(cursor + 8) == 'r' &&
1851 *(cursor + 9) == 'e' &&
1852 *(cursor + 10) == 't' &&
1853 *(cursor + 11) == '_' &&
1854 *(cursor + 12) == 'c' &&
1855 *(cursor + 13) == 'a' &&
1856 *(cursor + 14) == 's' &&
1857 *(cursor + 15) == 't')
1859 token_stream[(int) index++].kind = Token_reinterpret_cast;
1860 return;
1862 break;
1865 token_stream[(int) index++].kind = Token_identifier;
1868 // kate: space-indent on; indent-width 2; replace-tabs on;