1
/* This file is part of KDevelop
2
Copyright (C) 2002,2003 Roberto Raggi <roberto@kdevelop.org>
4
This library is free software; you can redistribute it and/or
5
modify it under the terms of the GNU Library General Public
6
License as published by the Free Software Foundation; either
7
version 2 of the License, or (at your option) any later version.
9
This library is distributed in the hope that it will be useful,
10
but WITHOUT ANY WARRANTY; without even the implied warranty of
11
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12
Library General Public License for more details.
14
You should have received a copy of the GNU Library General Public License
15
along with this library; see the file COPYING.LIB. If not, write to
16
the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17
Boston, MA 02111-1307, USA.
28
#include <qstringlist.h>
29
#include <qasciidict.h>
36
#define ADVANCE(tk, descr) \
38
const Token& token = lex->lookAhead( 0 ); \
40
reportError( i18n("'%1' expected found '%2'").arg(descr).arg(token.text()) ); \
46
#define ADVANCE_NR(tk, descr) \
48
const Token& token = lex->lookAhead( 0 ); \
50
reportError( i18n("'%1' expected found '%2'").arg(descr).arg(token.text()) ); \
56
#define CHECK(tk, descr) \
58
const Token& token = lex->lookAhead( 0 ); \
65
#define MATCH(tk, descr) \
67
const Token& token = lex->lookAhead( 0 ); \
69
reportError( Errors::SyntaxError ); \
76
#define UPDATE_POS(node, start, end) \
79
const Token &a = lex->tokenAt(start); \
80
const Token &b = lex->tokenAt( end!=start ? end-1 : end ); \
81
a.getStartPosition( &line, &col ); \
82
(node)->setStartPosition( line, col ); \
83
b.getEndPosition( &line, &col ); \
84
(node)->setEndPosition( line, col ); \
85
if( (node)->nodeType() == NodeType_Generic ) { \
86
if ((start) == (end) || (end) == (start)+1) \
87
(node)->setSlice(lex->source(), a.position(), a.length()); \
89
(node)->setText( toString((start),(end)) ); \
93
#define AST_FROM_TOKEN(node, tk) \
94
AST::Node node = CreateNode<AST>(); \
95
UPDATE_POS( node, (tk), (tk)+1 );
106
struct ParserPrivateData
112
Parser::Parser( Driver* driver, Lexer* lexer )
113
: m_driver( driver ),
114
lex( lexer ), m_problems(0)
116
d = new ParserPrivateData();
128
bool Parser::reportError( const Error& err )
130
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::reportError()" << endl;
131
if( m_problems < m_maxProblems ){
134
const Token& token = lex->lookAhead( 0 );
135
lex->getTokenPosition( token, &line, &col );
137
QString s = lex->lookAhead(0).text();
138
s = s.left( 30 ).stripWhiteSpace();
142
m_driver->addProblem( m_driver->currentFileName(), Problem(err.text.arg(s), line, col) );
148
bool Parser::reportError( const QString& msg )
150
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::reportError()" << endl;
151
if( m_problems < m_maxProblems ){
154
const Token& token = lex->lookAhead( 0 );
155
lex->getTokenPosition( token, &line, &col );
157
m_driver->addProblem( m_driver->currentFileName(), Problem(msg, line, col) );
163
void Parser::syntaxError()
165
(void) reportError( Errors::SyntaxError );
168
bool Parser::skipUntil( int token )
170
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::skipUntil()" << endl;
171
while( !lex->lookAhead(0).isNull() ){
172
if( lex->lookAhead(0) == token )
181
bool Parser::skipUntilDeclaration()
183
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::skipUntilDeclaration()" << endl;
186
while( !lex->lookAhead(0).isNull() ){
188
switch( lex->lookAhead(0) ){
192
case Token_identifier:
206
case Token_namespace:
213
case Token_const: // cv
214
case Token_volatile: // cv
217
case Token_protected:
219
case Token_signals: // Qt
220
case Token_slots: // Qt
231
bool Parser::skipUntilStatement()
233
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::skipUntilStatement() -- token = " << lex->lookAhead(0).text() << endl;
235
while( !lex->lookAhead(0).isNull() ){
236
switch( lex->lookAhead(0) ){
242
case Token_identifier:
285
bool Parser::skip( int l, int r )
288
while( !lex->lookAhead(0).isNull() ){
289
int tk = lex->lookAhead( 0 );
295
else if( l != '{' && (tk == '{' || tk == '}' || tk == ';') )
307
bool Parser::skipCommaExpression( AST::Node& node )
309
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::skipCommaExpression()" << endl;
311
int start = lex->index();
314
if( !skipExpression(expr) )
317
while( lex->lookAhead(0) == ',' ){
320
if( !skipExpression(expr) ){
321
reportError( i18n("expression expected") );
326
AST::Node ast = CreateNode<AST>();
327
UPDATE_POS( ast, start, lex->index() );
333
bool Parser::skipExpression( AST::Node& node )
335
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::skipExpression()" << endl;
337
int start = lex->index();
339
while( !lex->lookAhead(0).isNull() ){
340
int tk = lex->lookAhead( 0 );
354
case Token_identifier:
356
if( lex->lookAhead( 0 ) == Token_identifier )
378
AST::Node ast = CreateNode<AST>();
379
UPDATE_POS( ast, start, lex->index() );
392
bool Parser::parseName( NameAST::Node& node )
394
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseName()" << endl;
396
GroupAST::Node winDeclSpec;
397
parseWinDeclSpec( winDeclSpec );
399
int start = lex->index();
401
NameAST::Node ast = CreateNode<NameAST>();
403
if( lex->lookAhead(0) == Token_scope ){
404
ast->setGlobal( true );
408
int idx = lex->index();
411
ClassOrNamespaceNameAST::Node n;
412
if( !parseUnqualifiedName(n) ) {
416
if( lex->lookAhead(0) == Token_scope ){
418
ast->addClassOrNamespaceName( n );
419
if( lex->lookAhead(0) == Token_template )
420
nextToken(); /// skip optional template #### @todo CHECK
422
ast->setUnqualifiedName( n );
427
if( idx == lex->index() )
430
UPDATE_POS( ast, start, lex->index() );
436
bool Parser::parseTranslationUnit( TranslationUnitAST::Node& node )
438
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTranslationUnit()" << endl;
440
int start = lex->index();
443
TranslationUnitAST::Node tun = CreateNode<TranslationUnitAST>();
445
if( lex->lookAhead(0) == Token_comment ) {
446
node->setComment( lex->lookAhead(0).text() );
450
while( !lex->lookAhead(0).isNull() ){
451
DeclarationAST::Node def;
452
int startDecl = lex->index();
453
if( !parseDeclaration(def) ){
455
if( startDecl == lex->index() )
456
nextToken(); // skip at least one token
457
skipUntilDeclaration();
459
node->addDeclaration( def );
462
UPDATE_POS( node, start, lex->index() );
464
// force (0,0) as start position
465
node->setStartPosition( 0, 0 );
467
return m_problems == 0;
470
bool Parser::parseDeclaration( DeclarationAST::Node& node )
472
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeclaration()" << endl;
474
int start = lex->index();
476
switch( lex->lookAhead(0) ){
483
return parseLinkageSpecification( node );
485
case Token_namespace:
486
return parseNamespace( node );
489
return parseUsing( node );
492
return parseTypedef( node );
495
return parseAsmDefinition( node );
499
return parseTemplateDeclaration( node );
503
// lex->setIndex( start );
505
if( objcp && parseObjcDef(node) )
508
lex->setIndex( start );
510
GroupAST::Node storageSpec;
511
parseStorageClassSpecifier( storageSpec );
514
parseCvQualify( cv );
516
TypeSpecifierAST::Node spec;
517
AST::Node declarator;
518
if( parseEnumSpecifier(spec) || parseClassSpecifier(spec) ) {
520
spec->getEndPosition( &line, &c );
521
spec->setCvQualify( cv );
524
parseCvQualify( cv2 );
525
spec->setCv2Qualify( cv2 );
527
InitDeclaratorListAST::Node declarators;
528
parseInitDeclaratorList(declarators);
530
SimpleDeclarationAST::Node ast = CreateNode<SimpleDeclarationAST>();
534
preparseLineComments( line );
536
ast->setComment( m_commentStore.getCommentInRange( line ) );
538
ast->setStorageSpecifier( storageSpec );
539
ast->setTypeSpec( spec );
540
ast->setInitDeclaratorList( declarators );
541
UPDATE_POS( ast, start, lex->index() );
547
lex->setIndex( start );
548
return parseDeclarationInternal( node );
554
bool Parser::parseLinkageSpecification( DeclarationAST::Node& node )
556
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseLinkageSpecification()" << endl;
558
int start = lex->index();
560
if( lex->lookAhead(0) != Token_extern ){
565
LinkageSpecificationAST::Node ast = CreateNode<LinkageSpecificationAST>();
567
int startExternType = lex->index();
568
if( lex->lookAhead(0) == Token_string_literal ){
570
AST::Node externType = CreateNode<AST>();
571
UPDATE_POS( externType, startExternType, lex->index() );
573
ast->setExternType( externType );
576
if( lex->lookAhead(0) == '{' ){
577
LinkageBodyAST::Node linkageBody;
578
parseLinkageBody( linkageBody );
579
ast->setLinkageBody( linkageBody );
581
DeclarationAST::Node decl;
582
if( !parseDeclaration(decl) ){
583
reportError( i18n("Declaration syntax error") );
585
ast->setDeclaration( decl );
588
UPDATE_POS( ast, start, lex->index() );
595
bool Parser::parseLinkageBody( LinkageBodyAST::Node& node )
597
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseLinkageBody()" << endl;
599
int start = lex->index();
601
if( lex->lookAhead(0) != '{' ){
606
LinkageBodyAST::Node lba = CreateNode<LinkageBodyAST>();
609
while( !lex->lookAhead(0).isNull() ){
610
int tk = lex->lookAhead( 0 );
615
DeclarationAST::Node def;
616
int startDecl = lex->index();
617
if( parseDeclaration(def) ){
618
node->addDeclaration( def );
621
if( startDecl == lex->index() )
622
nextToken(); // skip at least one token
623
skipUntilDeclaration();
629
if( lex->lookAhead(0) != '}' ){
630
reportError( i18n("} expected") );
634
UPDATE_POS( node, start, lex->index() );
638
bool Parser::parseNamespace( DeclarationAST::Node& node )
640
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseNamespace()" << endl;
642
int start = lex->index();
644
if( lex->lookAhead(0) != Token_namespace ){
649
int startNamespaceName = lex->index();
650
if( lex->lookAhead(0) == Token_identifier ){
653
AST::Node namespaceName = CreateNode<AST>();
654
UPDATE_POS( namespaceName, startNamespaceName, lex->index() );
656
if ( lex->lookAhead(0) == '=' ) {
661
if( parseName(name) ){
664
NamespaceAliasAST::Node ast = CreateNode<NamespaceAliasAST>();
665
ast->setNamespaceName( namespaceName );
666
ast->setAliasName( name );
667
UPDATE_POS( ast, start, lex->index() );
671
reportError( i18n("namespace expected") );
674
} else if( lex->lookAhead(0) != '{' ){
675
reportError( i18n("{ expected") );
679
NamespaceAST::Node ast = CreateNode<NamespaceAST>();
680
ast->setNamespaceName( namespaceName );
682
LinkageBodyAST::Node linkageBody;
683
parseLinkageBody( linkageBody );
685
ast->setLinkageBody( linkageBody );
686
UPDATE_POS( ast, start, lex->index() );
692
bool Parser::parseUsing( DeclarationAST::Node& node )
694
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseUsing()" << endl;
696
int start = lex->index();
698
if( lex->lookAhead(0) != Token_using ){
703
if( lex->lookAhead(0) == Token_namespace ){
704
if( !parseUsingDirective(node) ){
707
UPDATE_POS( node, start, lex->index() );
711
UsingAST::Node ast = CreateNode<UsingAST>();
713
int startTypeName = lex->index();
714
if( lex->lookAhead(0) == Token_typename ){
716
AST::Node tn = CreateNode<AST>();
717
UPDATE_POS( tn, startTypeName, lex->index() );
718
ast->setTypeName( tn );
722
if( !parseName(name) )
725
ast->setName( name );
729
UPDATE_POS( ast, start, lex->index() );
735
bool Parser::parseUsingDirective( DeclarationAST::Node& node )
737
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseUsingDirective()" << endl;
739
int start = lex->index();
741
if( lex->lookAhead(0) != Token_namespace ){
747
if( !parseName(name) ){
748
reportError( i18n("Namespace name expected") );
754
UsingDirectiveAST::Node ast = CreateNode<UsingDirectiveAST>();
755
ast->setName( name );
756
UPDATE_POS( ast, start, lex->index() );
763
bool Parser::parseOperatorFunctionId( AST::Node& node )
765
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseOperatorFunctionId()" << endl;
767
int start = lex->index();
769
if( lex->lookAhead(0) != Token_operator ){
775
if( parseOperator(op) ){
776
AST::Node asn = CreateNode<AST>();
778
UPDATE_POS( node, start, lex->index() );
781
// parse cast operator
785
TypeSpecifierAST::Node spec;
786
if( !parseSimpleTypeSpecifier(spec) ){
790
spec->setCvQualify( cv );
794
spec->setCv2Qualify( cv2 );
797
while( parsePtrOperator(ptrOp) )
800
AST::Node asn = CreateNode<AST>();
802
UPDATE_POS( node, start, lex->index() );
807
bool Parser::parseTemplateArgumentList( TemplateArgumentListAST::Node& node, bool reportError )
809
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTemplateArgumentList()" << endl;
811
int start = lex->index();
813
TemplateArgumentListAST::Node ast = CreateNode<TemplateArgumentListAST>();
816
if( !parseTemplateArgument(templArg) )
818
ast->addArgument( templArg );
820
while( lex->lookAhead(0) == ',' ){
823
if( !parseTemplateArgument(templArg) ){
830
ast->addArgument( templArg );
833
UPDATE_POS( ast, start, lex->index() );
839
bool Parser::parseTypedef( DeclarationAST::Node& node )
841
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTypedef()" << endl;
843
int start = lex->index();
845
if( lex->lookAhead(0) != Token_typedef ){
850
TypeSpecifierAST::Node spec;
851
if( !parseTypeSpecifierOrClassSpec(spec) ){
852
reportError( i18n("Need a type specifier to declare") );
856
InitDeclaratorListAST::Node declarators;
857
if( !parseInitDeclaratorList(declarators) ){
858
//reportError( i18n("Need an identifier to declare") );
862
TypedefAST::Node ast = CreateNode<TypedefAST>();
866
ast->setComment( comment() );
869
preparseLineComments( currentLine() );
872
ast->addComment( comment() );
879
ast->setTypeSpec( spec );
880
ast->setInitDeclaratorList( declarators );
881
UPDATE_POS( ast, start, lex->index() );
887
bool Parser::parseAsmDefinition( DeclarationAST::Node& /*node*/ )
889
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseAsmDefinition()" << endl;
891
ADVANCE( Token_asm, "asm" );
894
parseCvQualify( cv );
903
bool Parser::parseTemplateDeclaration( DeclarationAST::Node& node )
905
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTemplateDeclaration()" << endl;
907
int start = lex->index();
911
int startExport = lex->index();
912
if( lex->lookAhead(0) == Token_export ){
914
AST::Node n = CreateNode<AST>();
915
UPDATE_POS( n, startExport, lex->index() );
919
if( lex->lookAhead(0) != Token_template ){
924
TemplateParameterListAST::Node params;
925
if( lex->lookAhead(0) == '<' ){
927
parseTemplateParameterList( params );
932
DeclarationAST::Node def;
933
if( !parseDeclaration(def) ){
934
reportError( i18n("expected a declaration") );
937
TemplateDeclarationAST::Node ast = CreateNode<TemplateDeclarationAST>();
938
ast->setExported( exp );
939
ast->setTemplateParameterList( params );
940
ast->setDeclaration( def );
941
UPDATE_POS( ast, start, lex->index() );
947
bool Parser::parseOperator( AST::Node& /*node*/ )
949
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseOperator()" << endl;
950
QString text = lex->lookAhead(0).text();
952
switch( lex->lookAhead(0) ){
956
if( lex->lookAhead(0) == '[' && lex->lookAhead(1) == ']' ){
993
if( lex->lookAhead(0) == '(' && lex->lookAhead(1) == ')' ){
997
} else if( lex->lookAhead(0) == '[' && lex->lookAhead(1) == ']' ){
1007
bool Parser::parseCvQualify( GroupAST::Node& node )
1009
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseCvQualify()" << endl;
1011
int start = lex->index();
1013
GroupAST::Node ast = CreateNode<GroupAST>();
1016
while( !lex->lookAhead(0).isNull() ){
1017
int tk = lex->lookAhead( 0 );
1018
if( tk == Token_const || tk == Token_volatile ){
1020
int startWord = lex->index();
1022
AST::Node word = CreateNode<AST>();
1023
UPDATE_POS( word, startWord, lex->index() );
1024
ast->addNode( word );
1033
////kdDebug(9007)<< "-----------------> token = " << lex->lookAhead(0).text() << endl;
1034
UPDATE_POS( ast, start, lex->index() );
1040
bool Parser::parseSimpleTypeSpecifier( TypeSpecifierAST::Node& node )
1042
int start = lex->index();
1043
bool isIntegral = false;
1048
switch( lex->lookAhead(0) ){
1056
case Token_unsigned:
1069
TypeSpecifierAST::Node ast = CreateNode<TypeSpecifierAST>();
1071
ClassOrNamespaceNameAST::Node cl = CreateNode<ClassOrNamespaceNameAST>();
1073
AST::Node n = CreateNode<AST>();
1074
UPDATE_POS( n, start, lex->index() );
1076
UPDATE_POS( cl, start, lex->index() );
1078
NameAST::Node name = CreateNode<NameAST>();
1079
name->setUnqualifiedName( cl );
1080
UPDATE_POS( name, start, lex->index() );
1081
ast->setName( name );
1085
if( !parseName(name) ){
1086
lex->setIndex( start );
1089
ast->setName( name );
1092
UPDATE_POS( ast, start, lex->index() );
1097
bool Parser::parsePtrOperator( AST::Node& node )
1099
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parsePtrOperator()" << endl;
1101
int start = lex->index();
1103
if( lex->lookAhead(0) == '&' ){
1105
} else if( lex->lookAhead(0) == '*' ){
1108
int index = lex->index();
1110
if( !parsePtrToMember(memPtr) ){
1111
lex->setIndex( index );
1117
parseCvQualify( cv );
1119
AST::Node ast = CreateNode<AST>();
1120
UPDATE_POS( ast, start, lex->index() );
1127
bool Parser::parseTemplateArgument( AST::Node& node )
1129
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTemplateArgument()" << endl;
1131
int start = lex->index();
1132
if( parseTypeId(node) ){
1133
if( lex->lookAhead(0) == ',' || lex->lookAhead(0) == '>' )
1137
lex->setIndex( start );
1138
if( !parseLogicalOrExpression(node, true) ){
1145
bool Parser::parseTypeSpecifier( TypeSpecifierAST::Node& spec )
1147
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTypeSpecifier()" << endl;
1150
parseCvQualify( cv );
1152
if( parseElaboratedTypeSpecifier(spec) || parseSimpleTypeSpecifier(spec) ){
1153
spec->setCvQualify( cv );
1156
parseCvQualify( cv2 );
1157
spec->setCv2Qualify( cv2 );
1165
bool Parser::parseDeclarator( DeclaratorAST::Node& node )
1167
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeclarator()" << endl;
1169
int start = lex->index();
1171
DeclaratorAST::Node ast = CreateNode<DeclaratorAST>();
1173
DeclaratorAST::Node decl;
1174
NameAST::Node declId;
1177
while( parsePtrOperator(ptrOp) ){
1178
ast->addPtrOp( ptrOp );
1181
if( lex->lookAhead(0) == '(' ){
1184
if( !parseDeclarator(decl) ){
1187
ast->setSubDeclarator( decl );
1189
if( lex->lookAhead(0) != ')'){
1195
if( lex->lookAhead(0) == ':' ){
1197
} else if( parseDeclaratorId(declId) ){
1198
ast->setDeclaratorId( declId );
1200
lex->setIndex( start );
1204
if( lex->lookAhead(0) == ':' ){
1207
if( !parseConstantExpression(expr) ){
1208
reportError( i18n("Constant expression expected") );
1215
bool isVector = true;
1217
while( lex->lookAhead(0) == '[' ){
1218
int startArray = lex->index();
1221
parseCommaExpression( expr );
1223
ADVANCE( ']', "]" );
1224
AST::Node array = CreateNode<AST>();
1225
UPDATE_POS( array, startArray, lex->index() );
1226
ast->addArrayDimension( array );
1230
bool skipParen = false;
1231
if( lex->lookAhead(0) == Token_identifier && lex->lookAhead(1) == '(' && lex->lookAhead(2) == '(' ){
1237
if( ast->subDeclarator() && (!isVector || lex->lookAhead(0) != '(') ){
1238
lex->setIndex( start );
1242
int index = lex->index();
1243
if( lex->lookAhead(0) == '(' ){
1246
ParameterDeclarationClauseAST::Node params;
1247
if( !parseParameterDeclarationClause(params) ){
1248
////kdDebug(9007)<< "----------------------> not a parameter declaration, maybe an initializer!?" << endl;
1249
lex->setIndex( index );
1252
ast->setParameterDeclarationClause( params );
1254
if( lex->lookAhead(0) != ')' ){
1255
lex->setIndex( index );
1259
nextToken(); // skip ')'
1261
int startConstant = lex->index();
1262
if( lex->lookAhead(0) == Token_const ){
1264
AST::Node constant = CreateNode<AST>();
1265
UPDATE_POS( constant, startConstant, lex->index() );
1266
ast->setConstant( constant );
1269
GroupAST::Node except;
1270
if( parseExceptionSpecification(except) ){
1271
ast->setExceptionSpecification( except );
1276
if( lex->lookAhead(0) != ')' ){
1277
reportError( i18n("')' expected") );
1285
UPDATE_POS( ast, start, lex->index() );
1291
bool Parser::parseAbstractDeclarator( DeclaratorAST::Node& node )
1293
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeclarator()" << endl;
1294
int start = lex->index();
1296
DeclaratorAST::Node ast = CreateNode<DeclaratorAST>();
1298
DeclaratorAST::Node decl;
1299
NameAST::Node declId;
1302
while( parsePtrOperator(ptrOp) ){
1303
ast->addPtrOp( ptrOp );
1306
if( lex->lookAhead(0) == '(' ){
1309
if( !parseAbstractDeclarator(decl) ){
1312
ast->setSubDeclarator( decl );
1314
if( lex->lookAhead(0) != ')'){
1322
while( lex->lookAhead(0) == '[' ){
1323
int startArray = lex->index();
1326
skipCommaExpression( expr );
1328
ADVANCE( ']', "]" );
1329
AST::Node array = CreateNode<AST>();
1330
UPDATE_POS( array, startArray, lex->index() );
1331
ast->addArrayDimension( array );
1334
bool skipParen = false;
1335
if( lex->lookAhead(0) == Token_identifier && lex->lookAhead(1) == '(' && lex->lookAhead(2) == '(' ){
1341
int index = lex->index();
1342
if( lex->lookAhead(0) == '(' ){
1345
ParameterDeclarationClauseAST::Node params;
1346
if( !parseParameterDeclarationClause(params) ){
1347
lex->setIndex( index );
1350
ast->setParameterDeclarationClause( params );
1352
if( lex->lookAhead(0) != ')' ){
1353
lex->setIndex( index );
1358
int startConstant = lex->index();
1359
if( lex->lookAhead(0) == Token_const ){
1361
AST::Node constant = CreateNode<AST>();
1362
UPDATE_POS( constant, startConstant, lex->index() );
1363
ast->setConstant( constant );
1366
GroupAST::Node except;
1367
if( parseExceptionSpecification(except) ){
1368
ast->setExceptionSpecification( except );
1373
if( lex->lookAhead(0) != ')' ){
1374
reportError( i18n("')' expected") );
1382
UPDATE_POS( ast, start, lex->index() );
1389
bool Parser::parseEnumSpecifier( TypeSpecifierAST::Node& node )
1391
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseEnumSpecifier()" << endl;
1393
int start = lex->index();
1395
if( lex->lookAhead(0) != Token_enum ){
1401
Comment c = comment();
1406
if( lex->lookAhead(0) != '{' ){
1407
lex->setIndex( start );
1412
EnumSpecifierAST::Node ast = CreateNode<EnumSpecifierAST>();
1413
ast->setName( name );
1415
ast->setComment( c );
1417
EnumeratorAST::Node enumerator;
1418
if( parseEnumerator(enumerator) ){
1419
ast->addEnumerator( enumerator );
1421
while( lex->lookAhead(0) == ',' ){
1424
if( !parseEnumerator(enumerator) ){
1425
//reportError( i18n("Enumerator expected") );
1429
ast->addEnumerator( enumerator );
1435
if( lex->lookAhead(0) != '}' )
1436
reportError( i18n("} missing") );
1441
UPDATE_POS( ast, start, lex->index() );
1447
bool Parser::parseTemplateParameterList( TemplateParameterListAST::Node& node )
1449
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTemplateParameterList()" << endl;
1451
int start = lex->index();
1453
TemplateParameterListAST::Node ast = CreateNode<TemplateParameterListAST>();
1455
TemplateParameterAST::Node param;
1456
if( !parseTemplateParameter(param) ){
1459
ast->addTemplateParameter( param );
1461
while( lex->lookAhead(0) == ',' ){
1464
if( !parseTemplateParameter(param) ){
1468
ast->addTemplateParameter( param );
1472
UPDATE_POS( ast, start, lex->index() );
1478
bool Parser::parseTemplateParameter( TemplateParameterAST::Node& node )
1480
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTemplateParameter()" << endl;
1482
int start = lex->index();
1483
TemplateParameterAST::Node ast = CreateNode<TemplateParameterAST>();
1485
TypeParameterAST::Node typeParameter;
1486
ParameterDeclarationAST::Node param;
1488
int tk = lex->lookAhead( 0 );
1490
if( (tk == Token_class || tk == Token_typename || tk == Token_template) && parseTypeParameter(typeParameter) ){
1491
ast->setTypeParameter( typeParameter );
1495
if( !parseParameterDeclaration(param) )
1497
ast->setTypeValueParameter( param );
1500
UPDATE_POS( ast, start, lex->index() );
1506
bool Parser::parseTypeParameter( TypeParameterAST::Node& node )
1508
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTypeParameter()" << endl;
1510
int start = lex->index();
1511
TypeParameterAST::Node ast = CreateNode<TypeParameterAST>();
1513
AST_FROM_TOKEN( kind, lex->index() );
1514
ast->setKind( kind );
1516
switch( lex->lookAhead(0) ){
1519
case Token_typename:
1521
nextToken(); // skip class
1523
// parse optional name
1525
if( parseName(name) ){
1526
ast->setName( name );
1527
if( lex->lookAhead(0) == '=' ){
1531
if( !parseTypeId(typeId) ){
1535
ast->setTypeId( typeId );
1541
case Token_template:
1543
nextToken(); // skip template
1544
ADVANCE( '<', '<' );
1546
TemplateParameterListAST::Node params;
1547
if( !parseTemplateParameterList(params) ){
1550
ast->setTemplateParameterList( params );
1552
ADVANCE( '>', ">" );
1554
if( lex->lookAhead(0) == Token_class )
1557
// parse optional name
1559
if( parseName(name) ){
1560
ast->setName( name );
1561
if( lex->lookAhead(0) == '=' ){
1565
if( !parseTypeId(typeId) ){
1569
ast->setTypeId( typeId );
1573
if( lex->lookAhead(0) == '=' ){
1576
NameAST::Node templ_name;
1577
parseName( templ_name );
1588
UPDATE_POS( ast, start, lex->index() );
1593
bool Parser::parseStorageClassSpecifier( GroupAST::Node& node )
1595
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseStorageClassSpecifier()" << endl;
1597
int start = lex->index();
1598
GroupAST::Node ast = CreateNode<GroupAST>();
1600
while( !lex->lookAhead(0).isNull() ){
1601
int tk = lex->lookAhead( 0 );
1602
if( tk == Token_friend || tk == Token_auto || tk == Token_register || tk == Token_static ||
1603
tk == Token_extern || tk == Token_mutable ){
1604
int startNode = lex->index();
1607
AST::Node n = CreateNode<AST>();
1608
UPDATE_POS( n, startNode, lex->index() );
1614
if( ast->nodeList().count() == 0 )
1617
UPDATE_POS( ast, start, lex->index() );
1622
bool Parser::parseFunctionSpecifier( GroupAST::Node& node )
1624
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseFunctionSpecifier()" << endl;
1626
int start = lex->index();
1627
GroupAST::Node ast = CreateNode<GroupAST>();
1629
while( !lex->lookAhead(0).isNull() ){
1630
int tk = lex->lookAhead( 0 );
1631
if( tk == Token_inline || tk == Token_virtual || tk == Token_explicit ){
1632
int startNode = lex->index();
1635
AST::Node n = CreateNode<AST>();
1636
UPDATE_POS( n, startNode, lex->index() );
1643
if( ast->nodeList().count() == 0 )
1646
UPDATE_POS( ast, start, lex->index() );
1651
bool Parser::parseTypeId( AST::Node& node )
1653
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTypeId()" << endl;
1655
/// @todo implement the AST for typeId
1656
int start = lex->index();
1657
AST::Node ast = CreateNode<AST>();
1659
TypeSpecifierAST::Node spec;
1660
if( !parseTypeSpecifier(spec) ){
1664
DeclaratorAST::Node decl;
1665
parseAbstractDeclarator( decl );
1667
UPDATE_POS( ast, start, lex->index() );
1673
bool Parser::parseInitDeclaratorList( InitDeclaratorListAST::Node& node )
1675
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseInitDeclaratorList()" << endl;
1677
int start = lex->index();
1679
InitDeclaratorListAST::Node ast = CreateNode<InitDeclaratorListAST>();
1680
InitDeclaratorAST::Node decl;
1682
if( !parseInitDeclarator(decl) ){
1685
ast->addInitDeclarator( decl );
1687
while( lex->lookAhead(0) == ',' ){
1690
if( !parseInitDeclarator(decl) ){
1694
ast->addInitDeclarator( decl );
1696
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseInitDeclaratorList() -- end" << endl;
1698
UPDATE_POS( ast, start, lex->index() );
1704
bool Parser::parseParameterDeclarationClause( ParameterDeclarationClauseAST::Node& node )
1706
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseParameterDeclarationClause()" << endl;
1708
int start = lex->index();
1710
ParameterDeclarationClauseAST::Node ast = CreateNode<ParameterDeclarationClauseAST>();
1712
ParameterDeclarationListAST::Node params;
1713
if( !parseParameterDeclarationList(params) ){
1715
if ( lex->lookAhead(0) == ')' )
1718
if( lex->lookAhead(0) == Token_ellipsis && lex->lookAhead(1) == ')' ){
1719
AST_FROM_TOKEN( ellipsis, lex->index() );
1720
ast->setEllipsis( ellipsis );
1727
if( lex->lookAhead(0) == Token_ellipsis ){
1728
AST_FROM_TOKEN( ellipsis, lex->index() );
1729
ast->setEllipsis( ellipsis );
1734
ast->setParameterDeclarationList( params );
1736
/// @todo add ellipsis
1737
UPDATE_POS( ast, start, lex->index() );
1744
void Parser::nextToken( bool skipComm ) {
1747
if( lex->lookAhead(0) == Token_comment ) {
1755
Comment Parser::comment() {
1756
return m_commentStore.latestComment();
1760
void Parser::preparseLineComments( int l ) {
1761
for( int a = 0; a < 40; a++ ) {
1762
if( lex->lookAhead(a).isNull() ) break;
1764
lex->lookAhead( a ).getStartPosition( &line, &col );
1767
} else if( line == l ) {
1768
if( lex->lookAhead( a ) == Token_comment ) {
1769
processComment( a );
1778
void Parser::processComment( int offset ) {
1780
lex->lookAhead( offset ).getStartPosition( &line, &col );
1781
m_commentStore.addComment( Comment( lex->lookAhead(offset).text(), line ) );
1784
template<class Type>
1785
void Parser::eventuallyTakeComment( int startLn, int endLn, Type& ast ) {
1786
if( comment().line() >= startLn && comment().line() <= endLn ) {
1789
ast->setComment( comment() );
1797
template<class Type>
1798
void Parser::eventuallyTakeComment( Type& ast ) {
1799
if( &(*ast) && comment() ) {
1800
ast->setComment( comment() );
1806
void Parser::clearComment( ) {
1808
m_commentStore.clear();
1812
int Parser::currentLine() {
1814
lex->lookAhead( 0 ).getStartPosition( &ln, &col );
1818
bool Parser::parseParameterDeclarationList( ParameterDeclarationListAST::Node& node )
1820
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseParameterDeclarationList()" << endl;
1822
int start = lex->index();
1824
ParameterDeclarationListAST::Node ast = CreateNode<ParameterDeclarationListAST>();
1826
ParameterDeclarationAST::Node param;
1827
if( !parseParameterDeclaration(param) ){
1828
lex->setIndex( start );
1831
ast->addParameter( param );
1833
while( lex->lookAhead(0) == ',' ){
1836
if( lex->lookAhead(0) == Token_ellipsis )
1839
if( !parseParameterDeclaration(param) ){
1840
lex->setIndex( start );
1843
ast->addParameter( param );
1846
UPDATE_POS( ast, start, lex->index() );
1852
bool Parser::parseParameterDeclaration( ParameterDeclarationAST::Node& node )
1854
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseParameterDeclaration()" << endl;
1856
int start = lex->index();
1859
TypeSpecifierAST::Node spec;
1860
if( !parseTypeSpecifier(spec) ){
1861
lex->setIndex( start );
1865
int index = lex->index();
1867
DeclaratorAST::Node decl;
1868
if( !parseDeclarator(decl) ){
1869
lex->setIndex( index );
1871
// try with abstract declarator
1872
if( !parseAbstractDeclarator(decl) )
1877
if( lex->lookAhead(0) == '=' ){
1879
if( !parseLogicalOrExpression(expr,true) ){
1880
//reportError( i18n("Expression expected") );
1884
ParameterDeclarationAST::Node ast = CreateNode<ParameterDeclarationAST>();
1885
ast->setTypeSpec( spec );
1886
ast->setDeclarator( decl );
1887
ast->setExpression( expr );
1889
UPDATE_POS( ast, start, lex->index() );
1896
bool Parser::parseClassSpecifier( TypeSpecifierAST::Node& node )
1898
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseClassSpecifier()" << endl;
1900
int start = lex->index();
1903
int classKeyStart = lex->index();
1905
int kind = lex->lookAhead( 0 );
1906
if( kind == Token_class || kind == Token_struct || kind == Token_union ){
1907
AST::Node asn = CreateNode<AST>();
1910
UPDATE_POS( classKey, classKeyStart, lex->index() );
1915
GroupAST::Node winDeclSpec;
1916
parseWinDeclSpec( winDeclSpec );
1918
while( lex->lookAhead(0) == Token_identifier && lex->lookAhead(1) == Token_identifier )
1924
BaseClauseAST::Node bases;
1925
if( lex->lookAhead(0) == ':' ){
1926
if( !parseBaseClause(bases) ){
1931
if( lex->lookAhead(0) != '{' ){
1932
lex->setIndex( start );
1936
ClassSpecifierAST::Node ast = CreateNode<ClassSpecifierAST>();
1938
eventuallyTakeComment( ast );
1940
ADVANCE( '{', '{' );
1943
ast->setWinDeclSpec( winDeclSpec );
1944
ast->setClassKey( classKey );
1945
ast->setName( name );
1946
ast->setBaseClause( bases );
1949
while( !lex->lookAhead(0).isNull() ){
1950
if( lex->lookAhead(0) == '}' )
1953
DeclarationAST::Node memSpec;
1954
int startDecl = lex->index();
1955
if( !parseMemberSpecification(memSpec) ){
1956
if( startDecl == lex->index() )
1957
nextToken(); // skip at least one token
1958
skipUntilDeclaration();
1960
ast->addDeclaration( memSpec );
1965
if( lex->lookAhead(0) != '}' ){
1966
reportError( i18n("} missing") );
1970
UPDATE_POS( ast, start, lex->index() );
1976
bool Parser::parseAccessSpecifier( AST::Node& node )
1978
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseAccessSpecifier()" << endl;
1980
int start = lex->index();
1982
switch( lex->lookAhead(0) ){
1984
case Token_protected:
1985
case Token_private: {
1986
AST::Node asn = CreateNode<AST>();
1989
UPDATE_POS( node, start, lex->index() );
1997
bool Parser::parseMemberSpecification( DeclarationAST::Node& node )
1999
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseMemberSpecification()" << endl;
2001
int start = lex->index();
2005
if( lex->lookAhead(0) == ';' ){
2008
} else if( lex->lookAhead(0) == Token_Q_OBJECT || lex->lookAhead(0) == Token_K_DCOP ){
2011
} else if( lex->lookAhead(0) == Token_signals || lex->lookAhead(0) == Token_k_dcop || lex->lookAhead(0) == Token_k_dcop_signals ){
2012
AccessDeclarationAST::Node ast = CreateNode<AccessDeclarationAST>();
2014
AST::Node n = CreateNode<AST>();
2015
UPDATE_POS( n, start, lex->index() );
2016
ast->addAccess( n );
2017
ADVANCE( ':', ":" );
2018
UPDATE_POS( ast, start, lex->index() );
2021
} else if( parseTypedef(node) ){
2023
} else if( parseUsing(node) ){
2025
} else if( parseTemplateDeclaration(node) ){
2027
} else if( parseAccessSpecifier(access) ){
2028
AccessDeclarationAST::Node ast = CreateNode<AccessDeclarationAST>();
2029
ast->addAccess( access );
2031
int startSlot = lex->index();
2032
if( lex->lookAhead(0) == Token_slots ){
2034
AST::Node sl = CreateNode<AST>();
2035
UPDATE_POS( sl, startSlot, lex->index() );
2036
ast->addAccess( sl );
2038
ADVANCE( ':', ":" );
2039
UPDATE_POS( ast, start, lex->index() );
2044
lex->setIndex( start );
2046
GroupAST::Node storageSpec;
2047
parseStorageClassSpecifier( storageSpec );
2050
parseCvQualify( cv );
2052
TypeSpecifierAST::Node spec;
2053
if( parseEnumSpecifier(spec) || parseClassSpecifier(spec) ){
2054
spec->setCvQualify( cv );
2057
parseCvQualify( cv2 );
2058
spec->setCv2Qualify( cv2 );
2060
InitDeclaratorListAST::Node declarators;
2061
parseInitDeclaratorList( declarators );
2062
ADVANCE( ';', ";" );
2064
SimpleDeclarationAST::Node ast = CreateNode<SimpleDeclarationAST>();
2065
ast->setTypeSpec( spec );
2066
ast->setInitDeclaratorList( declarators );
2067
UPDATE_POS( ast, start, lex->index() );
2073
lex->setIndex( start );
2074
return parseDeclarationInternal( node );
2077
bool Parser::parseCtorInitializer( AST::Node& /*node*/ )
2079
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseCtorInitializer()" << endl;
2081
if( lex->lookAhead(0) != ':' ){
2087
if( !parseMemInitializerList(inits) ){
2088
reportError( i18n("Member initializers expected") );
2094
bool Parser::parseElaboratedTypeSpecifier( TypeSpecifierAST::Node& node )
2096
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseElaboratedTypeSpecifier()" << endl;
2098
int start = lex->index();
2100
int tk = lex->lookAhead( 0 );
2101
if( tk == Token_class ||
2102
tk == Token_struct ||
2103
tk == Token_union ||
2105
tk == Token_typename )
2107
AST::Node kind = CreateNode<AST>();
2109
UPDATE_POS( kind, start, lex->index() );
2113
if( parseName(name) ){
2114
ElaboratedTypeSpecifierAST::Node ast = CreateNode<ElaboratedTypeSpecifierAST>();
2115
ast->setKind( kind );
2116
ast->setName( name );
2117
UPDATE_POS( ast, start, lex->index() );
2124
lex->setIndex( start );
2128
bool Parser::parseDeclaratorId( NameAST::Node& node )
2130
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeclaratorId()" << endl;
2131
return parseName( node );
2134
bool Parser::parseExceptionSpecification( GroupAST::Node& node )
2136
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseExceptionSpecification()" << endl;
2138
if( lex->lookAhead(0) != Token_throw ){
2143
ADVANCE( '(', "(" );
2144
if( lex->lookAhead(0) == Token_ellipsis ){
2145
// extension found in MSVC++ 7.x headers
2146
int start = lex->index();
2147
GroupAST::Node ast = CreateNode<GroupAST>();
2148
AST_FROM_TOKEN( ellipsis, lex->index() );
2149
ast->addNode( ellipsis );
2151
UPDATE_POS( ast, start, lex->index() );
2153
} else if( lex->lookAhead(0) == ')' ) {
2154
node = CreateNode<GroupAST>();
2156
parseTypeIdList( node );
2158
ADVANCE( ')', ")" );
2163
bool Parser::parseEnumerator( EnumeratorAST::Node& node )
2165
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseEnumerator()" << endl;
2167
int start = lex->index();
2169
if( lex->lookAhead(0) != Token_identifier ){
2176
EnumeratorAST::Node ena = CreateNode<EnumeratorAST>();
2179
AST::Node id = CreateNode<AST>();
2180
UPDATE_POS( id, start, lex->index() );
2182
int line = currentLine();
2184
if( lex->lookAhead(0) == '=' ){
2188
line = currentLine();
2189
if( !parseConstantExpression(expr) ){
2190
reportError( i18n("Constant expression expected") );
2192
node->setExpr( expr );
2195
UPDATE_POS( node, start, lex->index() );
2197
preparseLineComments( line );
2199
node->setComment( m_commentStore.getCommentInRange( line ) );
2204
bool Parser::parseInitDeclarator( InitDeclaratorAST::Node& node )
2206
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseInitDeclarator()" << endl;
2208
int start = lex->index();
2210
DeclaratorAST::Node decl;
2212
if( !parseDeclarator(decl) ){
2216
parseInitializer( init );
2218
InitDeclaratorAST::Node ast = CreateNode<InitDeclaratorAST>();
2219
ast->setDeclarator( decl );
2220
ast->setInitializer( init );
2221
UPDATE_POS( ast, start, lex->index() );
2229
bool Parser::parseBaseClause( BaseClauseAST::Node& node )
2231
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseBaseClause()" << endl;
2233
int start = lex->index();
2234
if( lex->lookAhead(0) != ':' ){
2239
BaseClauseAST::Node bca = CreateNode<BaseClauseAST>();
2241
BaseSpecifierAST::Node baseSpec;
2242
if( parseBaseSpecifier(baseSpec) ){
2243
bca->addBaseSpecifier( baseSpec );
2245
while( lex->lookAhead(0) == ',' ){
2248
if( !parseBaseSpecifier(baseSpec) ){
2249
reportError( i18n("Base class specifier expected") );
2252
bca->addBaseSpecifier( baseSpec );
2257
UPDATE_POS( bca, start, lex->index() );
2263
bool Parser::parseInitializer( AST::Node& node )
2265
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseInitializer()" << endl;
2267
if( lex->lookAhead(0) == '=' ){
2271
if( !parseInitializerClause(node) ){
2272
reportError( i18n("Initializer clause expected") );
2275
} else if( lex->lookAhead(0) == '(' ){
2278
skipCommaExpression( expr );
2280
ADVANCE( ')', ")" );
2286
bool Parser::parseMemInitializerList( AST::Node& /*node*/ )
2288
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseMemInitializerList()" << endl;
2291
if( !parseMemInitializer(init) ){
2295
while( lex->lookAhead(0) == ',' ){
2298
if( parseMemInitializer(init) ){
2307
bool Parser::parseMemInitializer( AST::Node& /*node*/ )
2309
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseMemInitializer()" << endl;
2311
NameAST::Node initId;
2312
if( !parseMemInitializerId(initId) ){
2313
reportError( i18n("Identifier expected") );
2316
ADVANCE( '(', '(' );
2318
skipCommaExpression( expr );
2319
ADVANCE( ')', ')' );
2324
bool Parser::parseTypeIdList( GroupAST::Node& node )
2326
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTypeIdList()" << endl;
2328
int start = lex->index();
2331
if( !parseTypeId(typeId) ){
2335
GroupAST::Node ast = CreateNode<GroupAST>();
2336
ast->addNode( typeId );
2338
while( lex->lookAhead(0) == ',' ){
2340
if( parseTypeId(typeId) ){
2341
ast->addNode( typeId );
2343
reportError( i18n("Type id expected") );
2348
UPDATE_POS( ast, start, lex->index() );
2353
bool Parser::parseBaseSpecifier( BaseSpecifierAST::Node& node )
2355
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseBaseSpecifier()" << endl;
2357
int start = lex->index();
2358
BaseSpecifierAST::Node ast = CreateNode<BaseSpecifierAST>();
2361
if( lex->lookAhead(0) == Token_virtual ){
2362
AST_FROM_TOKEN( virt, lex->index() );
2363
ast->setIsVirtual( virt );
2367
parseAccessSpecifier( access );
2369
parseAccessSpecifier( access );
2371
if( lex->lookAhead(0) == Token_virtual ){
2372
AST_FROM_TOKEN( virt, lex->index() );
2373
ast->setIsVirtual( virt );
2379
if( !parseName(name) ){
2380
reportError( i18n("Class name expected") );
2383
ast->setAccess( access );
2384
ast->setName( name );
2385
UPDATE_POS( ast, start, lex->index() );
2392
bool Parser::parseInitializerClause( AST::Node& node )
2394
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseInitializerClause()" << endl;
2396
if( lex->lookAhead(0) == '{' ){
2397
if( !skip('{','}') ){
2398
reportError( i18n("} missing") );
2404
if( !parseAssignmentExpression(node) ){
2405
//reportError( i18n("Expression expected") );
2412
bool Parser::parseMemInitializerId( NameAST::Node& node )
2414
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseMemInitializerId()" << endl;
2416
return parseName( node );
2419
bool Parser::parsePtrToMember( AST::Node& /*node*/ )
2421
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parsePtrToMember()" << endl;
2423
if( lex->lookAhead(0) == Token_scope ){
2427
while( lex->lookAhead(0) == Token_identifier ){
2430
if( lex->lookAhead(0) == Token_scope && lex->lookAhead(1) == '*' ){
2431
nextToken(); // skip ::
2432
nextToken(); // skip *
2441
bool Parser::parseUnqualifiedName( ClassOrNamespaceNameAST::Node& node )
2443
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseUnqualifiedName()" << endl;
2445
int start = lex->index();
2446
bool isDestructor = false;
2448
ClassOrNamespaceNameAST::Node ast = CreateNode<ClassOrNamespaceNameAST>();
2450
if( lex->lookAhead(0) == Token_identifier ){
2451
int startName = lex->index();
2452
AST::Node n = CreateNode<AST>();
2454
UPDATE_POS( n, startName, lex->index() );
2456
} else if( lex->lookAhead(0) == '~' && lex->lookAhead(1) == Token_identifier ){
2457
int startName = lex->index();
2458
AST::Node n = CreateNode<AST>();
2459
nextToken(); // skip ~
2460
nextToken(); // skip classname
2461
UPDATE_POS( n, startName, lex->index() );
2463
isDestructor = true;
2464
} else if( lex->lookAhead(0) == Token_operator ){
2466
if( !parseOperatorFunctionId(n) )
2473
if( !isDestructor ){
2475
int index = lex->index();
2477
if( lex->lookAhead(0) == '<' ){
2480
// optional template arguments
2481
TemplateArgumentListAST::Node args;
2482
parseTemplateArgumentList( args );
2484
if( lex->lookAhead(0) != '>' ){
2485
lex->setIndex( index );
2488
ast->setTemplateArgumentList( args );
2493
UPDATE_POS( ast, start, lex->index() );
2499
bool Parser::parseStringLiteral( AST::Node& /*node*/ )
2501
while( !lex->lookAhead(0).isNull() ) {
2502
if( lex->lookAhead(0) == Token_identifier &&
2503
lex->lookAhead(0).text() == "L" && lex->lookAhead(1) == Token_string_literal ) {
2507
} else if( lex->lookAhead(0) == Token_string_literal ) {
2515
bool Parser::skipExpressionStatement( StatementAST::Node& node )
2517
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::skipExpressionStatement()" << endl;
2519
int start = lex->index();
2522
skipCommaExpression( expr );
2524
ADVANCE( ';', ";" );
2526
ExpressionStatementAST::Node ast = CreateNode<ExpressionStatementAST>();
2527
ast->setExpression( expr );
2528
UPDATE_POS( ast, start, lex->index() );
2534
bool Parser::parseStatement( StatementAST::Node& node ) // thanks to fiore@8080.it ;)
2536
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseStatement()" << endl;
2537
switch( lex->lookAhead(0) ){
2540
return parseWhileStatement( node );
2543
return parseDoStatement( node );
2546
return parseForStatement( node );
2549
return parseForEachStatement( node );
2552
return parseIfStatement( node );
2555
return parseSwitchStatement( node );
2558
return parseTryBlockStatement( node );
2562
return parseLabeledStatement( node );
2565
case Token_continue:
2567
ADVANCE( ';', ";" );
2572
ADVANCE( Token_identifier, "identifier" );
2573
ADVANCE( ';', ";" );
2580
skipCommaExpression( expr );
2581
ADVANCE( ';', ";" );
2586
return parseCompoundStatement( node );
2588
case Token_identifier:
2589
if( parseLabeledStatement(node) )
2594
////kdDebug(9007)<< "------------> try with declaration statement" << endl;
2595
if ( parseDeclarationStatement(node) )
2598
return skipExpressionStatement( node );
2601
bool Parser::parseCondition( ConditionAST::Node& node )
2603
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseCondition()" << endl;
2605
int start = lex->index();
2607
ConditionAST::Node ast = CreateNode<ConditionAST>();
2609
TypeSpecifierAST::Node spec;
2610
if( parseTypeSpecifier(spec) ){
2611
DeclaratorAST::Node decl;
2612
if( parseDeclarator(decl) ) {
2613
if( lex->lookAhead(0) == '=' ) {
2617
if( skipExpression(expr) ){
2618
ast->setTypeSpec( spec );
2619
ast->setDeclarator( decl );
2620
ast->setExpression( expr );
2622
UPDATE_POS( ast, start, lex->index() );
2628
ast->setTypeSpec( spec );
2629
ast->setDeclarator( decl );
2631
UPDATE_POS( ast, start, lex->index() );
2639
lex->setIndex( start );
2642
if( !skipCommaExpression(expr) )
2645
ast->setExpression( expr );
2646
UPDATE_POS( ast, start, lex->index() );
2652
bool Parser::parseWhileStatement( StatementAST::Node& node )
2654
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseWhileStatement()" << endl;
2655
int start = lex->index();
2657
ADVANCE( Token_while, "while" );
2658
ADVANCE( '(' , "(" );
2660
ConditionAST::Node cond;
2661
if( !parseCondition(cond) ){
2662
reportError( i18n("condition expected") );
2665
ADVANCE( ')', ")" );
2667
StatementAST::Node body;
2668
if( !parseStatement(body) ){
2669
reportError( i18n("statement expected") );
2672
WhileStatementAST::Node ast = CreateNode<WhileStatementAST>();
2673
ast->setCondition( cond );
2674
ast->setStatement( body );
2675
UPDATE_POS( ast, start, lex->index() );
2681
bool Parser::parseDoStatement( StatementAST::Node& node )
2683
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDoStatement()" << endl;
2684
int start = lex->index();
2686
ADVANCE( Token_do, "do" );
2688
StatementAST::Node body;
2689
if( !parseStatement(body) ){
2690
reportError( i18n("statement expected") );
2694
ADVANCE_NR( Token_while, "while" );
2695
ADVANCE_NR( '(' , "(" );
2698
if( !skipCommaExpression(expr) ){
2699
reportError( i18n("expression expected") );
2703
ADVANCE_NR( ')', ")" );
2704
ADVANCE_NR( ';', ";" );
2706
DoStatementAST::Node ast = CreateNode<DoStatementAST>();
2707
ast->setStatement( body );
2708
//ast->setCondition( condition );
2709
UPDATE_POS( ast, start, lex->index() );
2715
bool Parser::parseForStatement( StatementAST::Node& node )
2717
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseForStatement()" << endl;
2718
int start = lex->index();
2720
ADVANCE( Token_for, "for" );
2721
ADVANCE( '(', "(" );
2723
StatementAST::Node init;
2724
if( !parseForInitStatement(init) ){
2725
reportError( i18n("for initialization expected") );
2729
ConditionAST::Node cond;
2730
parseCondition( cond );
2731
ADVANCE( ';', ";" );
2734
skipCommaExpression( expr );
2735
ADVANCE( ')', ")" );
2737
StatementAST::Node body;
2738
parseStatement(body);
2740
ForStatementAST::Node ast = CreateNode<ForStatementAST>();
2741
ast->setInitStatement( init );
2742
ast->setCondition( cond );
2743
// ast->setExpression( expression );
2744
ast->setStatement( body );
2745
UPDATE_POS( ast, start, lex->index() );
2752
///@todo add the right parsing for the foreach statement
2753
bool Parser::parseForEachStatement( StatementAST::Node& node )
2755
int start = lex->index();
2757
ADVANCE( Token_foreach, "foreach" );
2758
ADVANCE( '(', "(" );
2761
// replace with the right parsing
2762
skipCommaExpression( expr );
2763
ADVANCE( ')', ")" );
2765
StatementAST::Node body;
2766
parseStatement(body);
2768
ForEachStatementAST::Node ast = CreateNode<ForEachStatementAST>();
2769
// add here the parser results
2770
ast->setStatement( body );
2771
UPDATE_POS( ast, start, lex->index() );
2777
bool Parser::parseForInitStatement( StatementAST::Node& node )
2779
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseForInitStatement()" << endl;
2781
if ( parseDeclarationStatement(node) )
2784
return skipExpressionStatement( node );
2787
bool Parser::parseCompoundStatement( StatementAST::Node& node )
2789
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseCompoundStatement()" << endl;
2790
int start = lex->index();
2792
if( lex->lookAhead(0) != '{' ){
2797
StatementListAST::Node ast = CreateNode<StatementListAST>();
2799
while( !lex->lookAhead(0).isNull() ){
2800
if( lex->lookAhead(0) == '}' )
2803
StatementAST::Node stmt;
2804
int startStmt = lex->index();
2805
if( !parseStatement(stmt) ){
2806
if( startStmt == lex->index() )
2808
skipUntilStatement();
2810
ast->addStatement( stmt );
2816
if( lex->lookAhead(0) != '}' ){
2817
reportError( i18n("} expected") );
2822
UPDATE_POS( ast, start, lex->index() );
2828
bool Parser::parseIfStatement( StatementAST::Node& node )
2830
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseIfStatement()" << endl;
2832
int start = lex->index();
2834
ADVANCE( Token_if, "if" );
2836
ADVANCE( '(' , "(" );
2838
IfStatementAST::Node ast = CreateNode<IfStatementAST>();
2840
ConditionAST::Node cond;
2841
if( !parseCondition(cond) ){
2842
reportError( i18n("condition expected") );
2845
ADVANCE( ')', ")" );
2847
StatementAST::Node stmt;
2848
if( !parseStatement(stmt) ){
2849
reportError( i18n("statement expected") );
2852
ast->setCondition( cond );
2853
ast->setStatement( stmt );
2855
if( lex->lookAhead(0) == Token_else ){
2857
StatementAST::Node elseStmt;
2858
if( !parseStatement(elseStmt) ) {
2859
reportError( i18n("statement expected") );
2861
ast->setElseStatement( elseStmt );
2864
UPDATE_POS( ast, start, lex->index() );
2870
bool Parser::parseSwitchStatement( StatementAST::Node& node )
2872
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseSwitchStatement()" << endl;
2873
int start = lex->index();
2874
ADVANCE( Token_switch, "switch" );
2876
ADVANCE( '(' , "(" );
2878
ConditionAST::Node cond;
2879
if( !parseCondition(cond) ){
2880
reportError( i18n("condition expected") );
2883
ADVANCE( ')', ")" );
2885
StatementAST::Node stmt;
2886
if( !parseCompoundStatement(stmt) ){
2891
SwitchStatementAST::Node ast = CreateNode<SwitchStatementAST>();
2892
ast->setCondition( cond );
2893
ast->setStatement( stmt );
2894
UPDATE_POS( ast, start, lex->index() );
2900
bool Parser::parseLabeledStatement( StatementAST::Node& node )
2902
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseLabeledStatement()" << endl;
2903
switch( lex->lookAhead(0) ){
2904
case Token_identifier:
2906
if( lex->lookAhead(1) == ':' ){
2910
StatementAST::Node stmt;
2911
if( parseStatement(stmt) ){
2922
if( !parseConstantExpression(expr) ){
2923
reportError( i18n("expression expected") );
2924
} else if( lex->lookAhead(0) == Token_ellipsis ){
2928
if( !parseConstantExpression(expr2) ){
2929
reportError( i18n("expression expected") );
2932
ADVANCE( ':', ":" );
2934
StatementAST::Node stmt;
2935
if( parseStatement(stmt) ){
2947
bool Parser::parseBlockDeclaration( DeclarationAST::Node& node )
2949
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseBlockDeclaration()" << endl;
2950
switch( lex->lookAhead(0) ) {
2952
return parseTypedef( node );
2954
return parseUsing( node );
2956
return parseAsmDefinition( node );
2957
case Token_namespace:
2958
return parseNamespaceAliasDefinition( node );
2961
int start = lex->index();
2963
GroupAST::Node storageSpec;
2964
parseStorageClassSpecifier( storageSpec );
2967
parseCvQualify( cv );
2969
TypeSpecifierAST::Node spec;
2970
if ( !parseTypeSpecifierOrClassSpec(spec) ) { // replace with simpleTypeSpecifier?!?!
2971
lex->setIndex( start );
2974
spec->setCvQualify( cv );
2977
parseCvQualify( cv2 );
2978
spec->setCv2Qualify( cv2 );
2980
InitDeclaratorListAST::Node declarators;
2981
parseInitDeclaratorList( declarators );
2983
if( lex->lookAhead(0) != ';' ){
2984
lex->setIndex( start );
2989
SimpleDeclarationAST::Node ast = CreateNode<SimpleDeclarationAST>();
2990
ast->setTypeSpec( spec );
2991
ast->setInitDeclaratorList( declarators );
2992
UPDATE_POS( ast, start, lex->index() );
2998
bool Parser::parseNamespaceAliasDefinition( DeclarationAST::Node& /*node*/ )
3000
if ( lex->lookAhead(0) != Token_namespace ) {
3005
ADVANCE( Token_identifier, "identifier" );
3006
ADVANCE( '=', "=" );
3009
if( !parseName(name) ){
3010
reportError( i18n("Namespace name expected") );
3013
ADVANCE( ';', ";" );
3019
bool Parser::parseDeclarationStatement( StatementAST::Node& node )
3021
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeclarationStatement()" << endl;
3023
int start = lex->index();
3025
DeclarationAST::Node decl;
3026
if ( !parseBlockDeclaration(decl) ){
3030
DeclarationStatementAST::Node ast = CreateNode<DeclarationStatementAST>();
3031
ast->setDeclaration( decl );
3032
UPDATE_POS( ast, start, lex->index() );
3035
////kdDebug(9007)<< "---------------------> found a block declaration" << endl;
3039
bool Parser::parseDeclarationInternal( DeclarationAST::Node& node )
3041
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeclarationInternal()" << endl;
3043
int start = lex->index();
3045
// that is for the case '__declspec(dllexport) int ...' or
3046
// '__declspec(dllexport) inline int ...', etc.
3047
GroupAST::Node winDeclSpec;
3048
parseWinDeclSpec( winDeclSpec );
3050
GroupAST::Node funSpec;
3051
bool hasFunSpec = parseFunctionSpecifier( funSpec );
3053
GroupAST::Node storageSpec;
3054
bool hasStorageSpec = parseStorageClassSpecifier( storageSpec );
3056
if( hasStorageSpec && !hasFunSpec )
3057
hasFunSpec = parseFunctionSpecifier( funSpec );
3059
// that is for the case 'friend __declspec(dllexport) ....'
3060
GroupAST::Node winDeclSpec2;
3061
parseWinDeclSpec( winDeclSpec2 );
3064
parseCvQualify( cv );
3066
int index = lex->index();
3068
if( parseName(name) && lex->lookAhead(0) == '(' ){
3069
// no type specifier, maybe a constructor or a cast operator??
3071
lex->setIndex( index );
3073
InitDeclaratorAST::Node declarator;
3074
if( parseInitDeclarator(declarator) ){
3075
int endSignature = lex->index();
3077
switch( lex->lookAhead(0) ){
3082
InitDeclaratorListAST::Node declarators = CreateNode<InitDeclaratorListAST>();
3084
// update declarators position
3085
int startLine, startColumn, endLine, endColumn;
3086
if( declarator.get() ){
3087
declarator->getStartPosition( &startLine, &startColumn );
3088
declarator->getEndPosition( &endLine, &endColumn );
3089
declarators->setStartPosition( startLine, startColumn );
3090
declarators->setEndPosition( endLine, endColumn );
3092
declarators->addInitDeclarator( declarator );
3094
SimpleDeclarationAST::Node ast = CreateNode<SimpleDeclarationAST>();
3095
ast->setInitDeclaratorList( declarators );
3096
ast->setText( toString(start, endSignature) );
3098
UPDATE_POS( node, start, lex->index() );
3107
StatementListAST::Node funBody;
3108
if( parseCtorInitializer(ctorInit) && parseFunctionBody(funBody) ){
3109
FunctionDefinitionAST::Node ast = CreateNode<FunctionDefinitionAST>();
3110
ast->setStorageSpecifier( storageSpec );
3111
ast->setFunctionSpecifier( funSpec );
3112
ast->setInitDeclarator( declarator );
3113
ast->setFunctionBody( funBody );
3114
ast->setText( toString(start, endSignature) );
3116
UPDATE_POS( node, start, lex->index() );
3124
StatementListAST::Node funBody;
3125
if( parseFunctionBody(funBody) ){
3126
FunctionDefinitionAST::Node ast = CreateNode<FunctionDefinitionAST>();
3127
ast->setStorageSpecifier( storageSpec );
3128
ast->setFunctionSpecifier( funSpec );
3129
ast->setInitDeclarator( declarator );
3130
ast->setText( toString(start, endSignature) );
3131
ast->setFunctionBody( funBody );
3133
UPDATE_POS( node, start, lex->index() );
3141
// ops!! it seems a declarator
3153
lex->setIndex( index );
3155
if( lex->lookAhead(0) == Token_const && lex->lookAhead(1) == Token_identifier && lex->lookAhead(2) == '=' ){
3156
// constant definition
3158
InitDeclaratorListAST::Node declarators;
3159
if( parseInitDeclaratorList(declarators) ){
3160
ADVANCE( ';', ";" );
3161
DeclarationAST::Node ast = CreateNode<DeclarationAST>();
3163
UPDATE_POS( node, start, lex->index() );
3170
Comment mcomment = comment();
3173
TypeSpecifierAST::Node spec;
3174
if( parseTypeSpecifier(spec) ){
3176
parseFunctionSpecifier( funSpec ); // e.g. "void inline"
3177
spec->setCvQualify( cv );
3179
InitDeclaratorListAST::Node declarators;
3181
InitDeclaratorAST::Node decl;
3182
int startDeclarator = lex->index();
3183
bool maybeFunctionDefinition = false;
3185
if( lex->lookAhead(0) != ';' ){
3186
if( parseInitDeclarator(decl) && lex->lookAhead(0) == '{' ){
3187
// function definition
3188
maybeFunctionDefinition = true;
3190
lex->setIndex( startDeclarator );
3191
if( !parseInitDeclaratorList(declarators) ){
3198
int endSignature = lex->index();
3199
switch( lex->lookAhead(0) ){
3203
SimpleDeclarationAST::Node ast = CreateNode<SimpleDeclarationAST>();
3205
ast->setComment( mcomment );
3207
decl->getEndPosition( &line, &col );
3209
preparseLineComments( line );
3210
Comment c = m_commentStore.getCommentInRange( line );
3212
ast->addComment( c );
3216
ast->setStorageSpecifier( storageSpec );
3217
ast->setFunctionSpecifier( funSpec );
3218
ast->setText( toString(start, endSignature) );
3219
ast->setTypeSpec( spec );
3220
ast->setWinDeclSpec( winDeclSpec );
3221
ast->setInitDeclaratorList( declarators );
3224
UPDATE_POS( node, start, lex->index() );
3230
if( !maybeFunctionDefinition ){
3234
StatementListAST::Node funBody;
3235
if ( parseFunctionBody(funBody) ) {
3236
FunctionDefinitionAST::Node ast = CreateNode<FunctionDefinitionAST>();
3238
ast->setComment( mcomment );
3240
ast->setWinDeclSpec( winDeclSpec );
3241
ast->setStorageSpecifier( storageSpec );
3242
ast->setFunctionSpecifier( funSpec );
3243
ast->setText( toString(start, endSignature) );
3244
ast->setTypeSpec( spec );
3245
ast->setFunctionBody( funBody );
3246
ast->setInitDeclarator( decl );
3248
UPDATE_POS( node, start, lex->index() );
3261
bool Parser::parseFunctionBody( StatementListAST::Node& node )
3263
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseFunctionBody()" << endl;
3265
int start = lex->index();
3266
if( lex->lookAhead(0) != '{' ){
3271
StatementListAST::Node ast = CreateNode<StatementListAST>();
3273
while( !lex->lookAhead(0).isNull() ){
3274
if( lex->lookAhead(0) == '}' )
3277
StatementAST::Node stmt;
3278
int startStmt = lex->index();
3279
if( !parseStatement(stmt) ){
3280
if( startStmt == lex->index() )
3282
skipUntilStatement();
3284
ast->addStatement( stmt );
3289
if( lex->lookAhead(0) != '}' ){
3290
reportError( i18n("} expected") );
3294
UPDATE_POS( ast, start, lex->index() );
3300
QString Parser::toString( int start, int end, const QString& sep ) const
3304
for( int i=start; i<end; ++i ){
3305
const Token& t = lex->tokenAt(i);
3306
if( t != Token_comment )
3310
return l.join( sep ).stripWhiteSpace();
3313
bool Parser::parseTypeSpecifierOrClassSpec( TypeSpecifierAST::Node& node )
3315
if( parseClassSpecifier(node) )
3317
else if( parseEnumSpecifier(node) )
3319
else if( parseTypeSpecifier(node) )
3325
bool Parser::parseTryBlockStatement( StatementAST::Node& node )
3327
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseTryBlockStatement()" << endl;
3329
int start = lex->index();
3330
if( lex->lookAhead(0) != Token_try ){
3335
StatementAST::Node stmt;
3336
if( !parseCompoundStatement(stmt) ){
3340
if( lex->lookAhead(0) != Token_catch ){
3341
reportError( i18n("catch expected") );
3344
CatchStatementListAST::Node list = CreateNode<CatchStatementListAST>();
3346
while( lex->lookAhead(0) == Token_catch ){
3349
ADVANCE( '(', "(" );
3350
ConditionAST::Node cond;
3351
if( !parseCondition(cond) ){
3352
reportError( i18n("condition expected") );
3355
ADVANCE( ')', ")" );
3357
StatementAST::Node body;
3358
if( !parseCompoundStatement(body) ){
3362
CatchStatementAST::Node cstmt = CreateNode<CatchStatementAST>();
3363
cstmt->setCondition( cond );
3364
cstmt->setStatement( body );
3367
cond->getStartPosition( &l, &c );
3368
else if( body.get() )
3369
body->getStartPosition( &l, &c );
3371
cstmt->setStartPosition( l, c );
3373
body->getEndPosition( &l, &c );
3375
cstmt->setEndPosition( l, c );
3376
list->addStatement( cstmt );
3379
TryBlockStatementAST::Node ast = CreateNode<TryBlockStatementAST>();
3380
ast->setStatement( stmt );
3381
ast->setCatchStatementList( list );
3382
UPDATE_POS( ast, start, lex->index() );
3388
bool Parser::parsePrimaryExpression( AST::Node& /*node*/ )
3390
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parsePrimarExpression()" << endl;
3393
switch( lex->lookAhead(0) ){
3394
case Token_string_literal:
3397
parseStringLiteral( lit );
3401
case Token_number_literal:
3402
case Token_char_literal:
3412
case Token_dynamic_cast:
3413
case Token_static_cast:
3414
case Token_reinterpret_cast:
3415
case Token_const_cast:
3421
parseTypeId( typeId );
3426
parseCommaExpression( expr );
3436
parseCommaExpression( expr );
3444
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "token = " << lex->lookAhead(0).text() << endl;
3446
if( !parseExpression(expr) ){
3455
int start = lex->index();
3456
TypeSpecifierAST::Node typeSpec;
3457
if( parseSimpleTypeSpecifier(typeSpec) && lex->lookAhead(0) == '(' ){
3460
parseCommaExpression( expr );
3465
lex->setIndex( start );
3467
if( parseName(name) )
3475
bool Parser::parsePostfixExpression( AST::Node& /*node*/ )
3477
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parsePostfixExpression()" << endl;
3480
if( !parsePrimaryExpression(expr) )
3484
switch(lex->lookAhead(0))
3490
parseCommaExpression( e );
3499
parseCommaExpression( funArgs );
3513
if( lex->lookAhead(0) == Token_template )
3517
if( !parseName(name) ){
3523
case Token_typename:
3528
if( !parseName(name) ){
3534
parseCommaExpression(expr);
3549
bool Parser::parseUnaryExpression( AST::Node& node )
3551
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseUnaryExpression()" << endl;
3553
switch( lex->lookAhead(0) ){
3565
return parseCastExpression( expr );
3571
int index = lex->index();
3572
if( lex->lookAhead(0) == '(' ){
3575
if( parseTypeId(typeId) && lex->lookAhead(0) == ')' ){
3579
lex->setIndex( index );
3582
return parseUnaryExpression( expr );
3586
return parseNewExpression( node );
3589
return parseDeleteExpression( node );
3592
return parsePostfixExpression( node );
3595
bool Parser::parseNewExpression( AST::Node& /*node*/ )
3597
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseNewExpression()" << endl;
3598
if( lex->lookAhead(0) == Token_scope && lex->lookAhead(1) == Token_new )
3601
CHECK( Token_new, "new");
3603
if( lex->lookAhead(0) == '(' ){
3606
parseCommaExpression( expr );
3610
if( lex->lookAhead(0) == '(' ){
3613
parseTypeId( typeId );
3617
parseNewTypeId( typeId );
3621
parseNewInitializer( init );
3625
bool Parser::parseNewTypeId( AST::Node& /*node*/ )
3627
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseNewTypeId()" << endl;
3628
TypeSpecifierAST::Node typeSpec;
3629
if( parseTypeSpecifier(typeSpec) ){
3630
AST::Node declarator;
3631
parseNewDeclarator( declarator );
3638
bool Parser::parseNewDeclarator( AST::Node& /*node*/ )
3640
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseNewDeclarator()" << endl;
3642
if( parsePtrOperator(ptrOp) ){
3643
AST::Node declarator;
3644
parseNewDeclarator( declarator );
3648
if( lex->lookAhead(0) == '[' ){
3649
while( lex->lookAhead(0) == '[' ){
3652
parseExpression( expr );
3653
ADVANCE( ']', "]" );
3661
bool Parser::parseNewInitializer( AST::Node& /*node*/ )
3663
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseNewInitializer()" << endl;
3664
if( lex->lookAhead(0) != '(' )
3669
parseCommaExpression( expr );
3675
bool Parser::parseDeleteExpression( AST::Node& /*node*/ )
3677
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseDeleteExpression()" << endl;
3678
if( lex->lookAhead(0) == Token_scope && lex->lookAhead(1) == Token_delete )
3681
CHECK( Token_delete, "delete" );
3683
if( lex->lookAhead(0) == '[' ){
3689
return parseCastExpression( expr );
3692
bool Parser::parseCastExpression( AST::Node& /*node*/ )
3694
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseCastExpression()" << endl;
3696
int index = lex->index();
3698
if( lex->lookAhead(0) == '(' ){
3701
if ( parseTypeId(typeId) ) {
3702
if ( lex->lookAhead(0) == ')' ) {
3705
if( parseCastExpression(expr) )
3711
lex->setIndex( index );
3714
return parseUnaryExpression( expr );
3717
bool Parser::parsePmExpression( AST::Node& /*node*/ )
3719
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser:parsePmExpression()" << endl;
3721
if( !parseCastExpression(expr) )
3724
while( lex->lookAhead(0) == Token_ptrmem ){
3727
if( !parseCastExpression(expr) )
3734
bool Parser::parseMultiplicativeExpression( AST::Node& /*node*/ )
3736
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseMultiplicativeExpression()" << endl;
3738
if( !parsePmExpression(expr) )
3741
while( lex->lookAhead(0) == '*' || lex->lookAhead(0) == '/' || lex->lookAhead(0) == '%' ){
3744
if( !parsePmExpression(expr) )
3752
bool Parser::parseAdditiveExpression( AST::Node& /*node*/ )
3754
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseAdditiveExpression()" << endl;
3756
if( !parseMultiplicativeExpression(expr) )
3759
while( lex->lookAhead(0) == '+' || lex->lookAhead(0) == '-' ){
3762
if( !parseMultiplicativeExpression(expr) )
3769
bool Parser::parseShiftExpression( AST::Node& /*node*/ )
3771
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseShiftExpression()" << endl;
3773
if( !parseAdditiveExpression(expr) )
3776
while( lex->lookAhead(0) == Token_shift ){
3779
if( !parseAdditiveExpression(expr) )
3786
bool Parser::parseRelationalExpression( AST::Node& /*node*/, bool templArgs )
3788
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseRelationalExpression()" << endl;
3790
if( !parseShiftExpression(expr) )
3793
while( lex->lookAhead(0) == '<' || (lex->lookAhead(0) == '>' && !templArgs) ||
3794
lex->lookAhead(0) == Token_leq || lex->lookAhead(0) == Token_geq ){
3797
if( !parseShiftExpression(expr) )
3804
bool Parser::parseEqualityExpression( AST::Node& /*node*/, bool templArgs )
3806
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseEqualityExpression()" << endl;
3808
if( !parseRelationalExpression(expr, templArgs) )
3811
while( lex->lookAhead(0) == Token_eq || lex->lookAhead(0) == Token_not_eq ){
3814
if( !parseRelationalExpression(expr, templArgs) )
3821
bool Parser::parseAndExpression( AST::Node& /*node*/, bool templArgs )
3823
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseAndExpression()" << endl;
3825
if( !parseEqualityExpression(expr, templArgs) )
3828
while( lex->lookAhead(0) == '&' ){
3831
if( !parseEqualityExpression(expr, templArgs) )
3838
bool Parser::parseExclusiveOrExpression( AST::Node& /*node*/, bool templArgs )
3840
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseExclusiveOrExpression()" << endl;
3842
if( !parseAndExpression(expr, templArgs) )
3845
while( lex->lookAhead(0) == '^' ){
3848
if( !parseAndExpression(expr, templArgs) )
3855
bool Parser::parseInclusiveOrExpression( AST::Node& /*node*/, bool templArgs )
3857
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseInclusiveOrExpression()" << endl;
3859
if( !parseExclusiveOrExpression(expr, templArgs) )
3862
while( lex->lookAhead(0) == '|' ){
3865
if( !parseExclusiveOrExpression(expr, templArgs) )
3872
bool Parser::parseLogicalAndExpression( AST::Node& /*node*/, bool templArgs )
3874
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseLogicalAndExpression()" << endl;
3877
if( !parseInclusiveOrExpression(expr, templArgs) )
3880
while( lex->lookAhead(0) == Token_and ){
3883
if( !parseInclusiveOrExpression(expr, templArgs) )
3890
bool Parser::parseLogicalOrExpression( AST::Node& node, bool templArgs )
3892
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseLogicalOrExpression()" << endl;
3894
int start = lex->index();
3897
if( !parseLogicalAndExpression(expr, templArgs) )
3900
while( lex->lookAhead(0) == Token_or ){
3903
if( !parseLogicalAndExpression(expr, templArgs) )
3907
AST::Node ast = CreateNode<AST>();
3908
UPDATE_POS( ast, start, lex->index() );
3913
bool Parser::parseConditionalExpression( AST::Node& /*node*/ )
3915
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseConditionalExpression()" << endl;
3917
if( !parseLogicalOrExpression(expr) )
3920
if( lex->lookAhead(0) == '?' ){
3923
if( !parseExpression(expr) )
3928
if( !parseAssignmentExpression(expr) )
3935
bool Parser::parseAssignmentExpression( AST::Node& node )
3937
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseAssignmentExpression()" << endl;
3938
int start = lex->index();
3940
if( lex->lookAhead(0) == Token_throw && !parseThrowExpression(expr) )
3942
else if( !parseConditionalExpression(expr) )
3945
while( lex->lookAhead(0) == Token_assign || lex->lookAhead(0) == '=' ){
3948
if( !parseConditionalExpression(expr) )
3952
AST::Node ast = CreateNode<AST>();
3953
UPDATE_POS( ast, start, lex->index() );
3958
bool Parser::parseConstantExpression( AST::Node& node )
3960
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseConstantExpression()" << endl;
3961
int start = lex->index();
3962
if( parseConditionalExpression(node) ){
3963
AST::Node ast = CreateNode<AST>();
3964
UPDATE_POS( ast, start, lex->index() );
3971
bool Parser::parseExpression( AST::Node& node )
3973
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseExpression()" << endl;
3975
int start = lex->index();
3977
if( !parseCommaExpression(node) )
3980
AST::Node ast = CreateNode<AST>();
3981
UPDATE_POS( ast, start, lex->index() );
3986
bool Parser::parseCommaExpression( AST::Node& node )
3988
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseCommaExpression()" << endl;
3989
int start = lex->index();
3992
if( !parseAssignmentExpression(expr) )
3995
while( lex->lookAhead(0) == ',' ){
3998
if( !parseAssignmentExpression(expr) )
4002
AST::Node ast = CreateNode<AST>();
4003
UPDATE_POS( ast, start, lex->index() );
4008
bool Parser::parseThrowExpression( AST::Node& /*node*/ )
4010
////kdDebug(9007)<< "--- tok = " << lex->lookAhead(0).text() << " -- " << "Parser::parseThrowExpression()" << endl;
4011
if( lex->lookAhead(0) != Token_throw )
4014
CHECK( Token_throw, "throw" );
4016
if( !parseAssignmentExpression(expr) )
4022
bool Parser::parseIvarDeclList( AST::Node & node )
4028
bool Parser::parseIvarDecls( AST::Node & node )
4034
bool Parser::parseIvarDecl( AST::Node & node )
4040
bool Parser::parseIvars( AST::Node & node )
4046
bool Parser::parseIvarDeclarator( AST::Node & node )
4052
bool Parser::parseMethodDecl( AST::Node & node )
4058
bool Parser::parseUnarySelector( AST::Node & node )
4064
bool Parser::parseKeywordSelector( AST::Node & node )
4070
bool Parser::parseSelector( AST::Node & node )
4076
bool Parser::parseKeywordDecl( AST::Node & node )
4082
bool Parser::parseReceiver( AST::Node & node )
4088
bool Parser::parseObjcMessageExpr( AST::Node & node )
4094
bool Parser::parseMessageArgs( AST::Node & node )
4100
bool Parser::parseKeywordExpr( AST::Node & node )
4106
bool Parser::parseKeywordArgList( AST::Node & node )
4112
bool Parser::parseKeywordArg( AST::Node & node )
4118
bool Parser::parseReservedWord( AST::Node & node )
4124
bool Parser::parseMyParms( AST::Node & node )
4130
bool Parser::parseMyParm( AST::Node & node )
4136
bool Parser::parseOptParmList( AST::Node & node )
4142
bool Parser::parseObjcSelectorExpr( AST::Node & node )
4148
bool Parser::parseSelectorArg( AST::Node & node )
4154
bool Parser::parseKeywordNameList( AST::Node & node )
4160
bool Parser::parseKeywordName( AST::Node & node )
4166
bool Parser::parseObjcEncodeExpr( AST::Node & node )
4172
bool Parser::parseObjcString( AST::Node & node )
4178
bool Parser::parseProtocolRefs( AST::Node & node )
4184
bool Parser::parseIdentifierList( GroupAST::Node & node )
4186
int start = lex->index();
4188
if( lex->lookAhead(0) != Token_identifier )
4191
GroupAST::Node ast = CreateNode<GroupAST>();
4193
AST_FROM_TOKEN( tk, lex->index() );
4197
while( lex->lookAhead(0) == ',' ){
4199
if( lex->lookAhead(0) == Token_identifier ){
4200
AST_FROM_TOKEN( tk, lex->index() );
4204
ADVANCE( Token_identifier, "identifier" );
4208
UPDATE_POS( node, start, lex->index() );
4212
bool Parser::parseIdentifierColon( AST::Node & node )
4216
if( lex->lookAhead(0) == Token_identifier && lex->lookAhead(1) == ':' ){
4220
} // ### else if PTYPENAME -> return true ;
4225
bool Parser::parseObjcProtocolExpr( AST::Node & node )
4231
bool Parser::parseObjcOpenBracketExpr( AST::Node & node )
4237
bool Parser::parseObjcCloseBracket( AST::Node & node )
4243
bool Parser::parseObjcDef( DeclarationAST::Node & node )
4249
bool Parser::parseObjcClassDef( DeclarationAST::Node & node )
4255
bool Parser::parseObjcClassDecl( DeclarationAST::Node & node )
4259
ADVANCE( OBJC_CLASS, "@class" );
4261
GroupAST::Node idList;
4262
if ( !parseIdentifierList( idList ) )
4265
ADVANCE( ';', ";" );
4270
bool Parser::parseObjcProtocolDecl( DeclarationAST::Node & node )
4274
ADVANCE( OBJC_PROTOCOL, "@protocol" );
4276
GroupAST::Node idList;
4277
if ( !parseIdentifierList( idList ) )
4280
ADVANCE( ';', ";" );
4285
bool Parser::parseObjcAliasDecl( DeclarationAST::Node & node )
4289
ADVANCE( OBJC_ALIAS, "@alias" );
4291
GroupAST::Node idList;
4292
if ( !parseIdentifierList( idList ) )
4295
ADVANCE( ';', ";" );
4300
bool Parser::parseObjcProtocolDef( DeclarationAST::Node & node )
4306
bool Parser::parseObjcMethodDef( DeclarationAST::Node & node )
4312
bool Parser::parseWinDeclSpec( GroupAST::Node & node )
4314
if( lex->lookAhead(0) == Token_identifier && lex->lookAhead(0).text() == "__declspec" && lex->lookAhead(1) == '(' && lex->lookAhead(2) != ')'){
4315
int start = lex->index();
4317
nextToken(); // skip '('
4319
if ( !parseIdentifierList( node ) )
4322
ADVANCE( ')', ")" );
4324
UPDATE_POS( node, start, lex->index() );