46int Recognizer::nextToken()
57 int token = ch.unicode ();
63 while (!ch.isNull () && ch != u'"')
77 qerr() << _M_input_file <<
":" << _M_line <<
": Warning. Expected `\"'" << Qt::endl;
79 _M_current_value = text;
80 return (token = STRING_LITERAL);
83 else if (ch.isLetterOrNumber () || ch == u'_')
86 do { text += ch; inp (); }
87 while (ch.isLetterOrNumber () || ch == u'_' || ch == u'.');
88 _M_current_value = text;
92 else if (token ==
'%')
97 while (ch.isSpace ());
99 do { text += ch; inp (); }
100 while (ch.isLetterOrNumber () || ch == u'_' || ch == u'-');
102 if (text ==
"token_prefix"_L1)
103 return (token = TOKEN_PREFIX);
104 else if (text ==
"merged_output"_L1)
105 return (token = MERGED_OUTPUT);
106 else if (text ==
"token"_L1)
107 return (token = TOKEN);
108 else if (text ==
"start"_L1)
109 return (token = START);
110 else if (text ==
"parser"_L1)
111 return (token = PARSER);
112 else if (text ==
"decl"_L1)
113 return (token = DECL_FILE);
114 else if (text ==
"impl"_L1)
115 return (token = IMPL_FILE);
116 else if (text ==
"expect"_L1)
117 return (token = EXPECT);
118 else if (text ==
"expect-rr"_L1)
119 return (token = EXPECT_RR);
120 else if (text ==
"left"_L1)
121 return (token = LEFT);
122 else if (text ==
"right"_L1)
123 return (token = RIGHT);
124 else if (text ==
"nonassoc"_L1)
125 return (token = NONASSOC);
126 else if (text ==
"prec"_L1)
127 return (token = PREC);
130 qerr() << _M_input_file <<
":" << _M_line <<
": Unknown keyword `" << text <<
"'" << Qt::endl;
132 return (token = ERROR);
138 if (token ==
'-' && ch == u'-')
141 while (!ch.isNull () && ch != u'\n');
145 else if (token ==
':' && ch == u':')
149 return (token = ERROR);
151 return (token = COLON);
154 else if (token ==
'/' && ch == u':')
156 _M_action_line = _M_line;
160 text +=
"\n#line "_L1 + QString::number(_M_action_line) +
161 " \""_L1 + QDir::fromNativeSeparators(_M_input_file) +
"\"\n"_L1;
166 while (! ch.isNull ())
168 token = ch.unicode ();
171 if (token ==
':' && ch == u'/')
174 text += QLatin1Char (token);
178 return (token = ERROR);
182 if (ch.isNull () || ch.isSpace ())
184 _M_current_value = text;
185 return (token = DECL);
192 else if (token ==
'/' && ch == u'.')
194 _M_action_line = _M_line;
198 text +=
"\n#line "_L1 + QString::number(_M_action_line) +
199 " \""_L1 + QDir::fromNativeSeparators(_M_input_file) +
"\"\n"_L1;
205 while (! ch.isNull ())
207 token = ch.unicode ();
210 if (token ==
'.' && ch == u'/')
213 text += QLatin1Char (token);
217 return (token = ERROR);
221 if (ch.isNull () || ch.isSpace ())
223 _M_current_value = text;
224 return (token = IMPL);
233 return (token = COLON);
236 return (token = SEMICOLON);
248bool Recognizer::parse (
const QString &input_file)
250 _M_input_file = input_file;
252 QFile file(_M_input_file);
253 if (! file.open(QFile::ReadOnly))
255 qerr() <<
"qlalr: no input file\n";
259 QString _M_contents = QTextStream(&file).readAll();
260 _M_firstChar = _M_contents.constBegin();
261 _M_lastChar = _M_contents.constEnd();
262 _M_currentChar = _M_firstChar;
270 _M_current_rule = _M_grammar
->rules.end ();
275 state_stack[++tos] = 0;
279 if (yytoken == -1 && - TERMINAL_COUNT != action_index [state_stack [tos]])
280 yytoken = nextToken();
282 int act = t_action (state_stack [tos], yytoken);
284 if (act == ACCEPT_STATE)
289 if (++tos == stack_size)
292 sym_stack [tos] = _M_current_value;
293 state_stack [tos] = act;
302 act = state_stack [tos++];
307 Name name = _M_grammar->intern (sym(2));
313 _M_grammar->table_name = sym(2);
317 _M_grammar->merged_output = sym(2);
321 _M_grammar->decl_file_name = sym(2);
325 _M_grammar->impl_file_name = sym(2);
329 _M_grammar->expected_shift_reduce = sym(2).toInt();
333 _M_grammar->expected_reduce_reduce = sym(2).toInt();
337 _M_grammar->token_prefix = sym(2);
340 Name name = _M_grammar->intern (sym(1));
342 _M_grammar->spells.insert (name, sym(2));
361 Name name = _M_grammar->intern (sym(1));
367 _M_grammar->token_info.insert (name, info);
371 _M_decls += expand (sym(1));
375 _M_impls += expand (sym(1));
380 _M_current_rule->lhs = _M_grammar->intern (sym(1));
385 qerr() << _M_input_file <<
":" << _M_line <<
": Invalid non terminal `" << *_M_current_rule->lhs <<
"'" << Qt::endl;
393 Name lhs = _M_current_rule->lhs;
395 _M_current_rule->lhs = lhs;
400 qerr() << _M_input_file <<
":" << _M_line <<
": Invalid non terminal `" << *_M_current_rule->lhs <<
"'" << Qt::endl;
408 _M_current_rule->prec = _M_grammar->names.end ();
410 for (NameList::iterator it = _M_current_rule->rhs.begin (); it != _M_current_rule->rhs.end (); ++it)
415 _M_current_rule->prec = *it;
420 Name tok = _M_grammar->intern (sym(2));
423 qerr() << _M_input_file <<
":" << _M_line <<
": `" << *tok <<
" is not a terminal symbol" << Qt::endl;
424 _M_current_rule->prec = _M_grammar->names.end ();
427 _M_current_rule->prec = tok;
431 Name name = _M_grammar->intern (sym(2));
436 _M_current_rule->rhs.push_back (name);
445 state_stack [tos] = nt_action (act, lhs [r] - TERMINAL_COUNT);
454 qerr() << _M_input_file <<
":" << _M_line <<
": Syntax error" << Qt::endl;