001 /* 002 * Copyright 2010-2013 JetBrains s.r.o. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017 package org.jetbrains.jet.lang.parsing; 018 019 import com.intellij.lang.PsiBuilder; 020 import com.intellij.psi.tree.IElementType; 021 import com.intellij.psi.tree.TokenSet; 022 import org.jetbrains.annotations.Nullable; 023 import org.jetbrains.jet.JetNodeType; 024 import org.jetbrains.jet.lexer.JetKeywordToken; 025 026 import java.util.HashMap; 027 import java.util.Map; 028 029 import static org.jetbrains.jet.JetNodeTypes.*; 030 import static org.jetbrains.jet.lexer.JetTokens.*; 031 032 public class JetParsing extends AbstractJetParsing { 033 // TODO: token sets to constants, including derived methods 034 public static final Map<String, IElementType> MODIFIER_KEYWORD_MAP = new HashMap<String, IElementType>(); 035 static { 036 for (IElementType softKeyword : MODIFIER_KEYWORDS.getTypes()) { 037 MODIFIER_KEYWORD_MAP.put(((JetKeywordToken) softKeyword).getValue(), softKeyword); 038 } 039 } 040 041 private static final TokenSet TOPLEVEL_OBJECT_FIRST = TokenSet.create(TYPE_KEYWORD, TRAIT_KEYWORD, CLASS_KEYWORD, 042 FUN_KEYWORD, VAL_KEYWORD, PACKAGE_KEYWORD); 043 private static final TokenSet ENUM_MEMBER_FIRST = TokenSet.create(TYPE_KEYWORD, TRAIT_KEYWORD, CLASS_KEYWORD, 044 FUN_KEYWORD, VAL_KEYWORD, IDENTIFIER); 045 046 private static final TokenSet CLASS_NAME_RECOVERY_SET = TokenSet.orSet(TokenSet.create(LT, LPAR, COLON, LBRACE), TOPLEVEL_OBJECT_FIRST); 047 private static final TokenSet TYPE_PARAMETER_GT_RECOVERY_SET = TokenSet.create(WHERE_KEYWORD, LPAR, COLON, LBRACE, GT); 048 private static final TokenSet PARAMETER_NAME_RECOVERY_SET = TokenSet.create(COLON, EQ, COMMA, RPAR); 049 private static final TokenSet PACKAGE_NAME_RECOVERY_SET = TokenSet.create(DOT, EOL_OR_SEMICOLON); 050 private static final TokenSet IMPORT_RECOVERY_SET = TokenSet.create(AS_KEYWORD, DOT, EOL_OR_SEMICOLON); 051 /*package*/ static final TokenSet TYPE_REF_FIRST = TokenSet.create(LBRACKET, IDENTIFIER, FUN_KEYWORD, LPAR, CAPITALIZED_THIS_KEYWORD, HASH); 052 private static final TokenSet RECEIVER_TYPE_TERMINATORS = TokenSet.create(DOT, SAFE_ACCESS); 053 private static final TokenSet VALUE_PARAMETER_FIRST = TokenSet.orSet(TokenSet.create(IDENTIFIER, LBRACKET), MODIFIER_KEYWORDS); 054 055 static JetParsing createForTopLevel(SemanticWhitespaceAwarePsiBuilder builder) { 056 JetParsing jetParsing = new JetParsing(builder); 057 jetParsing.myExpressionParsing = new JetExpressionParsing(builder, jetParsing); 058 return jetParsing; 059 } 060 061 private static JetParsing createForByClause(SemanticWhitespaceAwarePsiBuilder builder) { 062 final SemanticWhitespaceAwarePsiBuilderForByClause builderForByClause = new SemanticWhitespaceAwarePsiBuilderForByClause(builder); 063 JetParsing jetParsing = new JetParsing(builderForByClause); 064 jetParsing.myExpressionParsing = new JetExpressionParsing(builderForByClause, jetParsing) { 065 @Override 066 protected boolean parseCallWithClosure() { 067 if (builderForByClause.getStackSize() > 0) { 068 return super.parseCallWithClosure(); 069 } 070 return false; 071 } 072 073 @Override 074 protected JetParsing create(SemanticWhitespaceAwarePsiBuilder builder) { 075 return createForByClause(builder); 076 } 077 }; 078 return jetParsing; 079 } 080 081 private JetExpressionParsing myExpressionParsing; 082 083 private JetParsing(SemanticWhitespaceAwarePsiBuilder builder) { 084 super(builder); 085 } 086 087 /* 088 * [start] jetlFile 089 * : preamble toplevelObject* [eof] 090 * ; 091 */ 092 void parseFile() { 093 PsiBuilder.Marker fileMarker = mark(); 094 095 parsePreamble(true); 096 097 while (!eof()) { 098 parseTopLevelObject(); 099 } 100 101 fileMarker.done(JET_FILE); 102 } 103 104 void parseTypeCodeFragment() { 105 PsiBuilder.Marker marker = mark(); 106 parseTypeRef(); 107 108 while (!eof()) { 109 error("unexpected symbol"); 110 advance(); 111 } 112 113 marker.done(TYPE_CODE_FRAGMENT); 114 } 115 116 void parseExpressionCodeFragment() { 117 PsiBuilder.Marker marker = mark(); 118 myExpressionParsing.parseExpression(); 119 120 while (!eof()) { 121 error("unexpected symbol"); 122 advance(); 123 } 124 125 marker.done(EXPRESSION_CODE_FRAGMENT); 126 } 127 128 void parseScript() { 129 PsiBuilder.Marker fileMarker = mark(); 130 131 parsePreamble(false); 132 133 PsiBuilder.Marker scriptMarker = mark(); 134 parseImportDirectives(); 135 136 PsiBuilder.Marker blockMarker = mark(); 137 138 myExpressionParsing.parseStatements(); 139 140 blockMarker.done(BLOCK); 141 scriptMarker.done(SCRIPT); 142 fileMarker.done(JET_FILE); 143 } 144 145 /* 146 *preamble 147 * : packageDirective? import* 148 * ; 149 */ 150 private void parsePreamble(boolean imports) { 151 /* 152 * packageDirective 153 * : modifiers "package" SimpleName{"."} SEMI? 154 * ; 155 */ 156 PsiBuilder.Marker packageDirective = mark(); 157 PsiBuilder.Marker firstEntry = mark(); 158 parseModifierList(MODIFIER_LIST, true); 159 160 if (at(PACKAGE_KEYWORD)) { 161 advance(); // PACKAGE_KEYWORD 162 163 164 parsePackageName(); 165 166 if (at(LBRACE)) { 167 // Because it's blocked package and it will be parsed as one of top level objects 168 firstEntry.rollbackTo(); 169 packageDirective.done(PACKAGE_DIRECTIVE); 170 return; 171 } 172 173 firstEntry.drop(); 174 175 consumeIf(SEMICOLON); 176 } 177 else { 178 firstEntry.rollbackTo(); 179 } 180 packageDirective.done(PACKAGE_DIRECTIVE); 181 182 if(imports) 183 parseImportDirectives(); 184 } 185 186 /* SimpleName{"."} */ 187 private void parsePackageName() { 188 PsiBuilder.Marker qualifiedExpression = mark(); 189 boolean simpleName = true; 190 while (true) { 191 if (myBuilder.newlineBeforeCurrentToken()) { 192 errorWithRecovery("Package name must be a '.'-separated identifier list placed on a single line", PACKAGE_NAME_RECOVERY_SET); 193 break; 194 } 195 196 PsiBuilder.Marker nsName = mark(); 197 if (expect(IDENTIFIER, "Package name must be a '.'-separated identifier list", PACKAGE_NAME_RECOVERY_SET)) { 198 nsName.done(REFERENCE_EXPRESSION); 199 } 200 else { 201 nsName.drop(); 202 } 203 204 if (!simpleName) { 205 PsiBuilder.Marker precedingMarker = qualifiedExpression.precede(); 206 qualifiedExpression.done(DOT_QUALIFIED_EXPRESSION); 207 qualifiedExpression = precedingMarker; 208 } 209 210 if (at(DOT)) { 211 simpleName = false; 212 advance(); // DOT 213 } 214 else { 215 break; 216 } 217 } 218 qualifiedExpression.drop(); 219 } 220 221 /* 222 * import 223 * : "import" SimpleName{"."} ("." "*" | "as" SimpleName)? SEMI? 224 * ; 225 */ 226 private void parseImportDirective() { 227 assert _at(IMPORT_KEYWORD); 228 PsiBuilder.Marker importDirective = mark(); 229 advance(); // IMPORT_KEYWORD 230 231 if (closeImportWithErrorIfNewline(importDirective, "Expecting qualified name")) { 232 return; 233 } 234 235 PsiBuilder.Marker qualifiedName = mark(); 236 237 PsiBuilder.Marker reference = mark(); 238 expect(IDENTIFIER, "Expecting qualified name"); 239 reference.done(REFERENCE_EXPRESSION); 240 241 while (at(DOT) && lookahead(1) != MUL) { 242 advance(); // DOT 243 244 if (closeImportWithErrorIfNewline(importDirective, "Import must be placed on a single line")) { 245 qualifiedName.drop(); 246 return; 247 } 248 249 reference = mark(); 250 if (expect(IDENTIFIER, "Qualified name must be a '.'-separated identifier list", IMPORT_RECOVERY_SET)) { 251 reference.done(REFERENCE_EXPRESSION); 252 } 253 else { 254 reference.drop(); 255 } 256 257 PsiBuilder.Marker precede = qualifiedName.precede(); 258 qualifiedName.done(DOT_QUALIFIED_EXPRESSION); 259 qualifiedName = precede; 260 } 261 qualifiedName.drop(); 262 263 if (at(DOT)) { 264 advance(); // DOT 265 assert _at(MUL); 266 advance(); // MUL 267 if (at(AS_KEYWORD)) { 268 PsiBuilder.Marker as = mark(); 269 advance(); // AS_KEYWORD 270 if (closeImportWithErrorIfNewline(importDirective, "Expecting identifier")) { 271 as.drop(); 272 return; 273 } 274 consumeIf(IDENTIFIER); 275 as.error("Cannot rename all imported items to one identifier"); 276 } 277 } 278 if (at(AS_KEYWORD)) { 279 advance(); // AS_KEYWORD 280 if (closeImportWithErrorIfNewline(importDirective, "Expecting identifier")) { 281 return; 282 } 283 expect(IDENTIFIER, "Expecting identifier", TokenSet.create(SEMICOLON)); 284 } 285 consumeIf(SEMICOLON); 286 importDirective.done(IMPORT_DIRECTIVE); 287 } 288 289 private boolean closeImportWithErrorIfNewline(PsiBuilder.Marker importDirective, String errorMessage) { 290 if (myBuilder.newlineBeforeCurrentToken()) { 291 error(errorMessage); 292 importDirective.done(IMPORT_DIRECTIVE); 293 return true; 294 } 295 return false; 296 } 297 298 private void parseImportDirectives() { 299 if (at(IMPORT_KEYWORD)) { 300 PsiBuilder.Marker importList = mark(); 301 while (at(IMPORT_KEYWORD)) { 302 parseImportDirective(); 303 } 304 importList.done(IMPORT_LIST); 305 } 306 } 307 308 /* 309 * toplevelObject 310 * : package 311 * : class 312 * : extension 313 * : function 314 * : property 315 * : typedef 316 * : object 317 * ; 318 */ 319 private void parseTopLevelObject() { 320 PsiBuilder.Marker decl = mark(); 321 322 TokenDetector detector = new TokenDetector(ENUM_KEYWORD); 323 parseModifierList(MODIFIER_LIST, detector, true); 324 325 IElementType keywordToken = tt(); 326 IElementType declType = null; 327 // if (keywordToken == PACKAGE_KEYWORD) { 328 // declType = parsePackageBlock(); 329 // } 330 // else 331 if (keywordToken == CLASS_KEYWORD || keywordToken == TRAIT_KEYWORD) { 332 declType = parseClass(detector.isDetected()); 333 } 334 else if (keywordToken == FUN_KEYWORD) { 335 declType = parseFunction(); 336 } 337 else if (keywordToken == VAL_KEYWORD || keywordToken == VAR_KEYWORD) { 338 declType = parseProperty(); 339 } 340 else if (keywordToken == TYPE_KEYWORD) { 341 declType = parseTypeDef(); 342 } 343 else if (keywordToken == OBJECT_KEYWORD) { 344 parseObject(true, true); 345 declType = OBJECT_DECLARATION; 346 } 347 348 if (declType == null) { 349 errorAndAdvance("Expecting package directive or top level declaration"); 350 decl.drop(); 351 } 352 else { 353 decl.done(declType); 354 } 355 } 356 357 /* 358 * (modifier | attribute)* 359 */ 360 boolean parseModifierList(JetNodeType nodeType, boolean allowShortAnnotations) { 361 return parseModifierList(nodeType, null, allowShortAnnotations); 362 } 363 364 /** 365 * (modifier | attribute)* 366 * 367 * Feeds modifiers (not attributes) into the passed consumer, if it is not null 368 */ 369 boolean parseModifierList(JetNodeType nodeType, @Nullable Consumer<IElementType> tokenConsumer, boolean allowShortAnnotations) { 370 PsiBuilder.Marker list = mark(); 371 boolean empty = true; 372 while (!eof()) { 373 if (atSet(MODIFIER_KEYWORDS)) { 374 if (tokenConsumer != null) tokenConsumer.consume(tt()); 375 advance(); // MODIFIER 376 } 377 else if (at(LBRACKET) || (allowShortAnnotations && at(IDENTIFIER))) { 378 parseAnnotation(allowShortAnnotations); 379 } 380 else { 381 break; 382 } 383 empty = false; 384 } 385 if (empty) { 386 list.drop(); 387 } 388 else { 389 list.done(nodeType); 390 } 391 return !empty; 392 } 393 394 /* 395 * annotations 396 * : annotation* 397 * ; 398 */ 399 void parseAnnotations(boolean allowShortAnnotations) { 400 while (true) { 401 if (!(parseAnnotation(allowShortAnnotations))) break; 402 } 403 } 404 405 /* 406 * annotation 407 * : "[" annotationEntry+ "]" 408 * : annotationEntry 409 * ; 410 */ 411 private boolean parseAnnotation(boolean allowShortAnnotations) { 412 if (at(LBRACKET)) { 413 PsiBuilder.Marker annotation = mark(); 414 415 myBuilder.disableNewlines(); 416 advance(); // LBRACKET 417 418 if (!at(IDENTIFIER)) { 419 error("Expecting a list of attributes"); 420 } 421 else { 422 parseAnnotationEntry(); 423 while (at(COMMA)) { 424 errorAndAdvance("No commas needed to separate attributes"); 425 } 426 427 while (at(IDENTIFIER)) { 428 parseAnnotationEntry(); 429 while (at(COMMA)) { 430 errorAndAdvance("No commas needed to separate attributes"); 431 } 432 } 433 } 434 435 expect(RBRACKET, "Expecting ']' to close an attribute annotation"); 436 myBuilder.restoreNewlinesState(); 437 438 annotation.done(ANNOTATION); 439 return true; 440 } 441 else if (allowShortAnnotations && at(IDENTIFIER)) { 442 parseAnnotationEntry(); 443 return true; 444 } 445 return false; 446 } 447 448 /* 449 * annotationEntry 450 * : SimpleName{"."} typeArguments? valueArguments? 451 * ; 452 */ 453 private void parseAnnotationEntry() { 454 assert _at(IDENTIFIER); 455 456 PsiBuilder.Marker attribute = mark(); 457 458 PsiBuilder.Marker reference = mark(); 459 PsiBuilder.Marker typeReference = mark(); 460 parseUserType(); 461 typeReference.done(TYPE_REFERENCE); 462 reference.done(CONSTRUCTOR_CALLEE); 463 464 parseTypeArgumentList(); 465 466 if (at(LPAR)) { 467 myExpressionParsing.parseValueArgumentList(); 468 } 469 attribute.done(ANNOTATION_ENTRY); 470 } 471 472 /* 473 * class 474 * : modifiers ("class" | "trait") SimpleName 475 * typeParameters? 476 * modifiers ("(" primaryConstructorParameter{","} ")")? 477 * (":" attributes delegationSpecifier{","})? 478 * typeConstraints 479 * (classBody? | enumClassBody) 480 * ; 481 */ 482 IElementType parseClass(boolean enumClass) { 483 assert _atSet(CLASS_KEYWORD, TRAIT_KEYWORD); 484 advance(); // CLASS_KEYWORD or TRAIT_KEYWORD 485 486 expect(IDENTIFIER, "Class name expected", CLASS_NAME_RECOVERY_SET); 487 boolean typeParametersDeclared = parseTypeParameterList(TYPE_PARAMETER_GT_RECOVERY_SET); 488 489 PsiBuilder.Marker beforeConstructorModifiers = mark(); 490 boolean hasConstructorModifiers = parseModifierList(PRIMARY_CONSTRUCTOR_MODIFIER_LIST, false); 491 492 // Some modifiers found, but no parentheses following: class has already ended, and we are looking at something else 493 if (hasConstructorModifiers && !atSet(LPAR, LBRACE, COLON) ) { 494 beforeConstructorModifiers.rollbackTo(); 495 return CLASS; 496 } 497 498 // We are still inside a class declaration 499 beforeConstructorModifiers.drop(); 500 501 if (at(LPAR)) { 502 parseValueParameterList(false, TokenSet.create(COLON, LBRACE)); 503 } 504 else if (hasConstructorModifiers) { 505 // A comprehensive error message for cases like: 506 // class A private : Foo 507 // or 508 // class A private { 509 error("Expecting primary constructor parameter list"); 510 } 511 512 if (at(COLON)) { 513 advance(); // COLON 514 parseDelegationSpecifierList(); 515 } 516 517 parseTypeConstraintsGuarded(typeParametersDeclared); 518 519 if (at(LBRACE)) { 520 if (enumClass) { 521 parseEnumClassBody(); 522 } 523 else { 524 parseClassBody(); 525 } 526 } 527 528 return CLASS; 529 } 530 531 /* 532 * enumClassBody 533 * : "{" enumEntry* "}" 534 * ; 535 */ 536 private void parseEnumClassBody() { 537 if (!at(LBRACE)) return; 538 539 PsiBuilder.Marker classBody = mark(); 540 541 myBuilder.enableNewlines(); 542 advance(); // LBRACE 543 544 while (!eof() && !at(RBRACE)) { 545 PsiBuilder.Marker entryOrMember = mark(); 546 547 TokenSet constructorNameFollow = TokenSet.create(SEMICOLON, COLON, LPAR, LT, LBRACE); 548 int lastId = findLastBefore(ENUM_MEMBER_FIRST, constructorNameFollow, false); 549 TokenDetector enumDetector = new TokenDetector(ENUM_KEYWORD); 550 createTruncatedBuilder(lastId).parseModifierList(MODIFIER_LIST, enumDetector, false); 551 552 IElementType type; 553 if (at(IDENTIFIER)) { 554 parseEnumEntry(); 555 type = ENUM_ENTRY; 556 } 557 else { 558 type = parseMemberDeclarationRest(enumDetector.isDetected()); 559 } 560 561 if (type == null) { 562 errorAndAdvance("Expecting an enum entry or member declaration"); 563 entryOrMember.drop(); 564 } 565 else { 566 entryOrMember.done(type); 567 } 568 } 569 570 expect(RBRACE, "Expecting '}' to close enum class body"); 571 myBuilder.restoreNewlinesState(); 572 573 classBody.done(CLASS_BODY); 574 } 575 576 /* 577 * enumEntry 578 * : modifiers SimpleName (":" initializer{","})? classBody? 579 * ; 580 */ 581 private void parseEnumEntry() { 582 assert _at(IDENTIFIER); 583 584 PsiBuilder.Marker nameAsDeclaration = mark(); 585 advance(); // IDENTIFIER 586 nameAsDeclaration.done(OBJECT_DECLARATION_NAME); 587 588 if (at(COLON)) { 589 advance(); // COLON 590 591 parseInitializerList(); 592 } 593 594 if (at(LBRACE)) { 595 parseClassBody(); 596 } 597 598 consumeIf(SEMICOLON); 599 } 600 601 /* 602 * classBody 603 * : ("{" memberDeclaration "}")? 604 * ; 605 */ 606 /*package*/ void parseClassBody() { 607 PsiBuilder.Marker body = mark(); 608 609 myBuilder.enableNewlines(); 610 expect(LBRACE, "Expecting a class body", TokenSet.create(LBRACE)); 611 612 while (!eof()) { 613 if (at(RBRACE)) { 614 break; 615 } 616 parseMemberDeclaration(); 617 } 618 expect(RBRACE, "Missing '}"); 619 myBuilder.restoreNewlinesState(); 620 621 body.done(CLASS_BODY); 622 } 623 624 /* 625 * memberDeclaration 626 * : modifiers memberDeclaration' 627 * ; 628 * 629 * memberDeclaration' 630 * : classObject 631 * : constructor 632 * : function 633 * : property 634 * : class 635 * : extension 636 * : typedef 637 * : anonymousInitializer 638 * : object 639 * ; 640 */ 641 private void parseMemberDeclaration() { 642 PsiBuilder.Marker decl = mark(); 643 644 TokenDetector enumDetector = new TokenDetector(ENUM_KEYWORD); 645 parseModifierList(MODIFIER_LIST, enumDetector, true); 646 647 IElementType declType = parseMemberDeclarationRest(enumDetector.isDetected()); 648 649 if (declType == null) { 650 errorWithRecovery("Expecting member declaration", TokenSet.create(RBRACE)); 651 decl.drop(); 652 } 653 else { 654 decl.done(declType); 655 } 656 } 657 658 private IElementType parseMemberDeclarationRest(boolean isEnum) { 659 IElementType keywordToken = tt(); 660 IElementType declType = null; 661 if (keywordToken == CLASS_KEYWORD) { 662 if (lookahead(1) == OBJECT_KEYWORD) { 663 declType = parseClassObject(); 664 } 665 else { 666 declType = parseClass(isEnum); 667 } 668 } 669 else if (keywordToken == TRAIT_KEYWORD) { 670 declType = parseClass(isEnum); 671 } 672 else if (keywordToken == FUN_KEYWORD) { 673 declType = parseFunction(); 674 } 675 else if (keywordToken == VAL_KEYWORD || keywordToken == VAR_KEYWORD) { 676 declType = parseProperty(); 677 } 678 else if (keywordToken == TYPE_KEYWORD) { 679 declType = parseTypeDef(); 680 } 681 else if (keywordToken == OBJECT_KEYWORD) { 682 parseObject(true, true); 683 declType = OBJECT_DECLARATION; 684 } 685 else if (keywordToken == LBRACE) { 686 parseBlock(); 687 declType = ANONYMOUS_INITIALIZER; 688 } 689 return declType; 690 } 691 692 /* 693 * object 694 * : "object" SimpleName? ":" delegationSpecifier{","}? classBody? 695 * ; 696 */ 697 void parseObject(boolean named, boolean optionalBody) { 698 assert _at(OBJECT_KEYWORD); 699 700 advance(); // OBJECT_KEYWORD 701 702 if (named) { 703 PsiBuilder.Marker propertyDeclaration = mark(); 704 expect(IDENTIFIER, "Expecting object name", TokenSet.create(LBRACE)); 705 propertyDeclaration.done(OBJECT_DECLARATION_NAME); 706 } 707 else { 708 if (at(IDENTIFIER)) { 709 error("An object expression cannot bind a name"); 710 } 711 } 712 713 if (optionalBody) { 714 if (at(COLON)) { 715 advance(); // COLON 716 parseDelegationSpecifierList(); 717 } 718 if (at(LBRACE)) { 719 parseClassBody(); 720 } 721 } 722 else { 723 if (at(LBRACE)) { 724 parseClassBody(); 725 } 726 else { 727 expect(COLON, "Expecting ':'", TokenSet.create(IDENTIFIER, PACKAGE_KEYWORD)); 728 parseDelegationSpecifierList(); 729 parseClassBody(); 730 } 731 } 732 } 733 734 /* 735 * initializer{","} 736 */ 737 private void parseInitializerList() { 738 PsiBuilder.Marker list = mark(); 739 while (true) { 740 if (at(COMMA)) errorAndAdvance("Expecting a this or super constructor call"); 741 parseInitializer(); 742 if (!at(COMMA)) break; 743 advance(); // COMMA 744 } 745 list.done(INITIALIZER_LIST); 746 } 747 748 /* 749 * initializer 750 * : attributes "this" valueArguments 751 * : attributes constructorInvocation // type parameters may (must?) be omitted 752 * ; 753 */ 754 private void parseInitializer() { 755 PsiBuilder.Marker initializer = mark(); 756 parseAnnotations(false); 757 758 IElementType type; 759 if (at(THIS_KEYWORD)) { 760 PsiBuilder.Marker mark = mark(); 761 advance(); // THIS_KEYWORD 762 mark.done(THIS_CONSTRUCTOR_REFERENCE); 763 type = THIS_CALL; 764 } 765 else if (atSet(TYPE_REF_FIRST)) { 766 PsiBuilder.Marker reference = mark(); 767 parseTypeRef(); 768 reference.done(CONSTRUCTOR_CALLEE); 769 type = DELEGATOR_SUPER_CALL; 770 } 771 else { 772 errorWithRecovery("Expecting constructor call (this(...)) or supertype initializer", TokenSet.create(LBRACE, COMMA)); 773 initializer.drop(); 774 return; 775 } 776 myExpressionParsing.parseValueArgumentList(); 777 778 initializer.done(type); 779 } 780 781 /* 782 * classObject 783 * : modifiers "class" object 784 * ; 785 */ 786 private JetNodeType parseClassObject() { 787 assert _at(CLASS_KEYWORD) && lookahead(1) == OBJECT_KEYWORD; 788 789 advance(); // CLASS_KEYWORD 790 791 PsiBuilder.Marker objectDeclaration = mark(); 792 parseObject(false, true); 793 objectDeclaration.done(OBJECT_DECLARATION); 794 795 return CLASS_OBJECT; 796 } 797 798 /* 799 * typedef 800 * : modifiers "type" SimpleName (typeParameters typeConstraints)? "=" type 801 * ; 802 */ 803 JetNodeType parseTypeDef() { 804 assert _at(TYPE_KEYWORD); 805 806 advance(); // TYPE_KEYWORD 807 808 expect(IDENTIFIER, "Type name expected", TokenSet.orSet(TokenSet.create(LT, EQ, SEMICOLON), TOPLEVEL_OBJECT_FIRST)); 809 810 if (parseTypeParameterList(TYPE_PARAMETER_GT_RECOVERY_SET)) { 811 parseTypeConstraints(); 812 } 813 814 expect(EQ, "Expecting '='", TokenSet.orSet(TOPLEVEL_OBJECT_FIRST, TokenSet.create(SEMICOLON))); 815 816 parseTypeRef(); 817 818 consumeIf(SEMICOLON); 819 820 return TYPEDEF; 821 } 822 823 /* 824 * variableDeclarationEntry 825 * : SimpleName (":" type)? 826 * ; 827 * 828 * property 829 * : modifiers ("val" | "var") 830 * typeParameters? (type "." | annotations)? 831 * ("(" variableDeclarationEntry{","} ")" | variableDeclarationEntry) 832 * typeConstraints 833 * ("by" | "=" expression SEMI?)? 834 * (getter? setter? | setter? getter?) SEMI? 835 * ; 836 */ 837 private IElementType parseProperty() { 838 return parseProperty(false); 839 } 840 841 public IElementType parseProperty(boolean local) { 842 if (at(VAL_KEYWORD) || at(VAR_KEYWORD)) { 843 advance(); // VAL_KEYWORD or VAR_KEYWORD 844 } 845 else { 846 errorAndAdvance("Expecting 'val' or 'var'"); 847 } 848 849 boolean typeParametersDeclared = at(LT) && parseTypeParameterList(TokenSet.create(IDENTIFIER, EQ, COLON, SEMICOLON)); 850 851 TokenSet propertyNameFollow = TokenSet.create(COLON, EQ, LBRACE, RBRACE, SEMICOLON, VAL_KEYWORD, VAR_KEYWORD, FUN_KEYWORD, CLASS_KEYWORD); 852 853 myBuilder.disableJoiningComplexTokens(); 854 855 // TODO: extract constant 856 int lastDot = matchTokenStreamPredicate(new LastBefore( 857 new AtSet(DOT, SAFE_ACCESS), 858 new AbstractTokenStreamPredicate() { 859 @Override 860 public boolean matching(boolean topLevel) { 861 if (topLevel && (at(EQ) || at(COLON))) return true; 862 if (topLevel && at(IDENTIFIER)) { 863 IElementType lookahead = lookahead(1); 864 return lookahead != LT && lookahead != DOT && lookahead != SAFE_ACCESS && lookahead != QUEST; 865 } 866 return false; 867 } 868 })); 869 870 PsiBuilder.Marker receiver = mark(); 871 parseReceiverType("property", propertyNameFollow, lastDot); 872 873 boolean multiDeclaration = at(LPAR); 874 boolean receiverTypeDeclared = lastDot != -1; 875 876 errorIf(receiver, multiDeclaration && receiverTypeDeclared, "Receiver type is not allowed on a multi-declaration"); 877 878 if (multiDeclaration) { 879 PsiBuilder.Marker multiDecl = mark(); 880 parseMultiDeclarationName(propertyNameFollow); 881 errorIf(multiDecl, !local, "Multi-declarations are only allowed for local variables/values"); 882 } 883 else { 884 parseFunctionOrPropertyName(receiverTypeDeclared, "property", propertyNameFollow); 885 } 886 887 myBuilder.restoreJoiningComplexTokensState(); 888 889 if (at(COLON)) { 890 PsiBuilder.Marker type = mark(); 891 advance(); // COLON 892 parseTypeRef(); 893 errorIf(type, multiDeclaration, "Type annotations are not allowed on multi-declarations"); 894 } 895 896 parseTypeConstraintsGuarded(typeParametersDeclared); 897 898 if (local) { 899 if (at(BY_KEYWORD)) { 900 parsePropertyDelegate(); 901 } 902 else if (at(EQ)) { 903 advance(); // EQ 904 myExpressionParsing.parseExpression(); 905 // "val a = 1; b" must not be an infix call of b on "val ...;" 906 } 907 } 908 else { 909 if (at(BY_KEYWORD)) { 910 parsePropertyDelegate(); 911 consumeIf(SEMICOLON); 912 } 913 else if (at(EQ)) { 914 advance(); // EQ 915 myExpressionParsing.parseExpression(); 916 consumeIf(SEMICOLON); 917 } 918 919 if (parsePropertyGetterOrSetter()) { 920 parsePropertyGetterOrSetter(); 921 } 922 if (!atSet(EOL_OR_SEMICOLON, RBRACE)) { 923 if (getLastToken() != SEMICOLON) { 924 errorUntil("Property getter or setter expected", TokenSet.create(EOL_OR_SEMICOLON)); 925 } 926 } 927 else { 928 consumeIf(SEMICOLON); 929 } 930 } 931 932 return multiDeclaration ? MULTI_VARIABLE_DECLARATION : PROPERTY; 933 } 934 935 /* 936 * propertyDelegate 937 * : "by" expression 938 * ; 939 */ 940 private void parsePropertyDelegate() { 941 assert _at(BY_KEYWORD); 942 PsiBuilder.Marker delegate = mark(); 943 advance(); // BY_KEYWORD 944 myExpressionParsing.parseExpression(); 945 delegate.done(PROPERTY_DELEGATE); 946 } 947 948 /* 949 * (SimpleName (":" type)){","} 950 */ 951 public void parseMultiDeclarationName(TokenSet follow) { 952 // Parsing multi-name, e.g. 953 // val (a, b) = foo() 954 myBuilder.disableNewlines(); 955 advance(); // LPAR 956 957 TokenSet recoverySet = TokenSet.orSet(PARAMETER_NAME_RECOVERY_SET, follow); 958 if (!atSet(follow)) { 959 while (true) { 960 if (at(COMMA)) { 961 errorAndAdvance("Expecting a name"); 962 } 963 else if (at(RPAR)) { 964 error("Expecting a name"); 965 break; 966 } 967 PsiBuilder.Marker property = mark(); 968 expect(IDENTIFIER, "Expecting a name", recoverySet); 969 970 if (at(COLON)) { 971 advance(); // COLON 972 parseTypeRef(follow); 973 } 974 property.done(MULTI_VARIABLE_DECLARATION_ENTRY); 975 976 if (!at(COMMA)) break; 977 advance(); // COMMA 978 } 979 } 980 981 expect(RPAR, "Expecting ')'", follow); 982 myBuilder.restoreNewlinesState(); 983 } 984 985 /* 986 * getterOrSetter 987 * : modifiers ("get" | "set") 988 * : 989 * ( "get" "(" ")" 990 * | 991 * "set" "(" modifiers parameter ")" 992 * ) functionBody 993 * ; 994 */ 995 private boolean parsePropertyGetterOrSetter() { 996 PsiBuilder.Marker getterOrSetter = mark(); 997 998 parseModifierList(MODIFIER_LIST, false); 999 1000 if (!at(GET_KEYWORD) && !at(SET_KEYWORD)) { 1001 getterOrSetter.rollbackTo(); 1002 return false; 1003 } 1004 1005 boolean setter = at(SET_KEYWORD); 1006 advance(); // GET_KEYWORD or SET_KEYWORD 1007 1008 if (!at(LPAR)) { 1009 // Account for Jet-114 (val a : int get {...}) 1010 TokenSet ACCESSOR_FIRST_OR_PROPERTY_END = TokenSet.orSet(MODIFIER_KEYWORDS, TokenSet.create(LBRACKET, GET_KEYWORD, SET_KEYWORD, EOL_OR_SEMICOLON, RBRACE)); 1011 if (!atSet(ACCESSOR_FIRST_OR_PROPERTY_END)) { 1012 errorUntil("Accessor body expected", TokenSet.orSet(ACCESSOR_FIRST_OR_PROPERTY_END, TokenSet.create(LBRACE, LPAR, EQ))); 1013 } 1014 else { 1015 getterOrSetter.done(PROPERTY_ACCESSOR); 1016 return true; 1017 } 1018 } 1019 1020 myBuilder.disableNewlines(); 1021 expect(LPAR, "Expecting '('", TokenSet.create(RPAR, IDENTIFIER, COLON, LBRACE, EQ)); 1022 if (setter) { 1023 PsiBuilder.Marker parameterList = mark(); 1024 PsiBuilder.Marker setterParameter = mark(); 1025 parseModifierListWithShortAnnotations(MODIFIER_LIST, TokenSet.create(IDENTIFIER), TokenSet.create(RPAR, COMMA, COLON)); 1026 expect(IDENTIFIER, "Expecting parameter name", TokenSet.create(RPAR, COLON, LBRACE, EQ)); 1027 1028 if (at(COLON)) { 1029 advance(); // COLON 1030 parseTypeRef(); 1031 } 1032 setterParameter.done(VALUE_PARAMETER); 1033 parameterList.done(VALUE_PARAMETER_LIST); 1034 } 1035 if (!at(RPAR)) errorUntil("Expecting ')'", TokenSet.create(RPAR, COLON, LBRACE, EQ, EOL_OR_SEMICOLON)); 1036 expect(RPAR, "Expecting ')'", TokenSet.create(RPAR, COLON, LBRACE, EQ)); 1037 myBuilder.restoreNewlinesState(); 1038 1039 if (at(COLON)) { 1040 advance(); 1041 1042 parseTypeRef(); 1043 } 1044 1045 parseFunctionBody(); 1046 1047 getterOrSetter.done(PROPERTY_ACCESSOR); 1048 1049 return true; 1050 } 1051 1052 /* 1053 * function 1054 * : modifiers "fun" typeParameters? 1055 * (type "." | attributes)? 1056 * SimpleName 1057 * typeParameters? functionParameters (":" type)? 1058 * typeConstraints 1059 * functionBody? 1060 * ; 1061 */ 1062 IElementType parseFunction() { 1063 assert _at(FUN_KEYWORD); 1064 1065 advance(); // FUN_KEYWORD 1066 1067 // Recovery for the case of class A { fun| } 1068 if (at(RBRACE)) { 1069 error("Function body expected"); 1070 return FUN; 1071 } 1072 1073 boolean typeParameterListOccurred = false; 1074 if (at(LT)) { 1075 parseTypeParameterList(TokenSet.create(LBRACKET, LBRACE, LPAR)); 1076 typeParameterListOccurred = true; 1077 } 1078 1079 myBuilder.disableJoiningComplexTokens(); 1080 int lastDot = findLastBefore(RECEIVER_TYPE_TERMINATORS, TokenSet.create(LPAR), true); 1081 1082 TokenSet functionNameFollow = TokenSet.create(LT, LPAR, COLON, EQ); 1083 parseReceiverType("function", functionNameFollow, lastDot); 1084 1085 parseFunctionOrPropertyName(lastDot != -1, "function", functionNameFollow); 1086 1087 myBuilder.restoreJoiningComplexTokensState(); 1088 1089 TokenSet valueParametersFollow = TokenSet.create(COLON, EQ, LBRACE, SEMICOLON, RPAR); 1090 1091 if (at(LT)) { 1092 PsiBuilder.Marker error = mark(); 1093 parseTypeParameterList(TokenSet.orSet(TokenSet.create(LPAR), valueParametersFollow)); 1094 errorIf(error, typeParameterListOccurred, "Only one type parameter list is allowed for a function"); 1095 typeParameterListOccurred = true; 1096 } 1097 1098 if (at(LPAR)) { 1099 parseValueParameterList(false, valueParametersFollow); 1100 } 1101 else { 1102 error("Expecting '('"); 1103 } 1104 1105 if (at(COLON)) { 1106 advance(); // COLON 1107 1108 parseTypeRef(); 1109 } 1110 1111 parseTypeConstraintsGuarded(typeParameterListOccurred); 1112 1113 if (at(SEMICOLON)) { 1114 advance(); // SEMICOLON 1115 } 1116 else if (at(EQ) || at(LBRACE)) { 1117 parseFunctionBody(); 1118 } 1119 1120 return FUN; 1121 } 1122 1123 /* 1124 * (type "." | attributes)? 1125 */ 1126 private void parseReceiverType(String title, TokenSet nameFollow, int lastDot) { 1127 if (lastDot == -1) { // There's no explicit receiver type specified 1128 parseAnnotations(false); 1129 } 1130 else { 1131 createTruncatedBuilder(lastDot).parseTypeRef(); 1132 1133 if (atSet(RECEIVER_TYPE_TERMINATORS)) { 1134 advance(); // expectation 1135 } 1136 else { 1137 errorWithRecovery("Expecting '.' before a " + title + " name", nameFollow); 1138 } 1139 } 1140 } 1141 1142 /* 1143 * IDENTIFIER 1144 */ 1145 private void parseFunctionOrPropertyName(boolean receiverFound, String title, TokenSet nameFollow) { 1146 if (!receiverFound) { 1147 expect(IDENTIFIER, "Expecting " + title + " name or receiver type", nameFollow); 1148 } 1149 else { 1150 expect(IDENTIFIER, "Expecting " + title + " name", nameFollow); 1151 } 1152 } 1153 1154 /* 1155 * functionBody 1156 * : block 1157 * : "=" element 1158 * ; 1159 */ 1160 private void parseFunctionBody() { 1161 if (at(LBRACE)) { 1162 parseBlock(); 1163 } 1164 else if (at(EQ)) { 1165 advance(); // EQ 1166 myExpressionParsing.parseExpression(); 1167 consumeIf(SEMICOLON); 1168 } 1169 else { 1170 errorAndAdvance("Expecting function body"); 1171 } 1172 } 1173 1174 /* 1175 * block 1176 * : "{" (expressions)* "}" 1177 * ; 1178 */ 1179 void parseBlock() { 1180 PsiBuilder.Marker block = mark(); 1181 1182 myBuilder.enableNewlines(); 1183 expect(LBRACE, "Expecting '{' to open a block"); 1184 1185 myExpressionParsing.parseStatements(); 1186 1187 expect(RBRACE, "Expecting '}"); 1188 myBuilder.restoreNewlinesState(); 1189 1190 block.done(BLOCK); 1191 } 1192 1193 /* 1194 * delegationSpecifier{","} 1195 */ 1196 /*package*/ void parseDelegationSpecifierList() { 1197 PsiBuilder.Marker list = mark(); 1198 1199 while (true) { 1200 if (at(COMMA)) { 1201 errorAndAdvance("Expecting a delegation specifier"); 1202 continue; 1203 } 1204 parseDelegationSpecifier(); 1205 if (!at(COMMA)) break; 1206 advance(); // COMMA 1207 } 1208 1209 list.done(DELEGATION_SPECIFIER_LIST); 1210 } 1211 1212 /* 1213 * attributes delegationSpecifier 1214 * 1215 * delegationSpecifier 1216 * : constructorInvocation // type and constructor arguments 1217 * : userType 1218 * : explicitDelegation 1219 * ; 1220 * 1221 * explicitDelegation 1222 * : userType "by" element 1223 * ; 1224 */ 1225 private void parseDelegationSpecifier() { 1226 PsiBuilder.Marker delegator = mark(); 1227 parseAnnotations(false); 1228 1229 PsiBuilder.Marker reference = mark(); 1230 parseTypeRef(); 1231 1232 if (at(BY_KEYWORD)) { 1233 reference.drop(); 1234 advance(); // BY_KEYWORD 1235 createForByClause(myBuilder).myExpressionParsing.parseExpression(); 1236 delegator.done(DELEGATOR_BY); 1237 } 1238 else if (at(LPAR)) { 1239 reference.done(CONSTRUCTOR_CALLEE); 1240 myExpressionParsing.parseValueArgumentList(); 1241 delegator.done(DELEGATOR_SUPER_CALL); 1242 } 1243 else { 1244 reference.drop(); 1245 delegator.done(DELEGATOR_SUPER_CLASS); 1246 } 1247 } 1248 1249 /* 1250 * typeParameters 1251 * : ("<" typeParameter{","} ">" 1252 * ; 1253 */ 1254 private boolean parseTypeParameterList(TokenSet recoverySet) { 1255 boolean result = false; 1256 if (at(LT)) { 1257 PsiBuilder.Marker list = mark(); 1258 1259 myBuilder.disableNewlines(); 1260 advance(); // LT 1261 1262 while (true) { 1263 if (at(COMMA)) errorAndAdvance("Expecting type parameter declaration"); 1264 parseTypeParameter(); 1265 1266 if (!at(COMMA)) break; 1267 advance(); // COMMA 1268 } 1269 1270 expect(GT, "Missing '>'", recoverySet); 1271 myBuilder.restoreNewlinesState(); 1272 result = true; 1273 1274 list.done(TYPE_PARAMETER_LIST); 1275 } 1276 return result; 1277 } 1278 1279 /* 1280 * typeConstraints 1281 * : ("where" typeConstraint{","})? 1282 * ; 1283 */ 1284 private void parseTypeConstraintsGuarded(boolean typeParameterListOccurred) { 1285 PsiBuilder.Marker error = mark(); 1286 boolean constraints = parseTypeConstraints(); 1287 errorIf(error, constraints && !typeParameterListOccurred, "Type constraints are not allowed when no type parameters declared"); 1288 } 1289 1290 private boolean parseTypeConstraints() { 1291 if (at(WHERE_KEYWORD)) { 1292 parseTypeConstraintList(); 1293 return true; 1294 } 1295 return false; 1296 } 1297 1298 /* 1299 * typeConstraint{","} 1300 */ 1301 private void parseTypeConstraintList() { 1302 assert _at(WHERE_KEYWORD); 1303 1304 advance(); // WHERE_KEYWORD 1305 1306 PsiBuilder.Marker list = mark(); 1307 1308 while (true) { 1309 if (at(COMMA)) errorAndAdvance("Type constraint expected"); 1310 parseTypeConstraint(); 1311 if (!at(COMMA)) break; 1312 advance(); // COMMA 1313 } 1314 1315 list.done(TYPE_CONSTRAINT_LIST); 1316 } 1317 1318 /* 1319 * typeConstraint 1320 * : attributes SimpleName ":" type 1321 * : attributes "class" "object" SimpleName ":" type 1322 * ; 1323 */ 1324 private void parseTypeConstraint() { 1325 PsiBuilder.Marker constraint = mark(); 1326 1327 parseAnnotations(false); 1328 1329 if (at(CLASS_KEYWORD)) { 1330 advance(); // CLASS_KEYWORD 1331 1332 expect(OBJECT_KEYWORD, "Expecting 'object'", TYPE_REF_FIRST); 1333 1334 } 1335 1336 PsiBuilder.Marker reference = mark(); 1337 if (expect(IDENTIFIER, "Expecting type parameter name", TokenSet.orSet(TokenSet.create(COLON, COMMA), TYPE_REF_FIRST))) { 1338 reference.done(REFERENCE_EXPRESSION); 1339 } 1340 else { 1341 reference.drop(); 1342 } 1343 1344 expect(COLON, "Expecting ':' before the upper bound", TYPE_REF_FIRST); 1345 1346 parseTypeRef(); 1347 1348 constraint.done(TYPE_CONSTRAINT); 1349 } 1350 1351 /* 1352 * typeParameter 1353 * : modifiers SimpleName (":" userType)? 1354 * ; 1355 */ 1356 private void parseTypeParameter() { 1357 if (atSet(TYPE_PARAMETER_GT_RECOVERY_SET)) { 1358 error("Type parameter declaration expected"); 1359 return; 1360 } 1361 1362 PsiBuilder.Marker mark = mark(); 1363 1364 parseModifierListWithShortAnnotations(MODIFIER_LIST, TokenSet.create(IDENTIFIER), TokenSet.create(COMMA, GT, COLON)); 1365 1366 expect(IDENTIFIER, "Type parameter name expected", TokenSet.EMPTY); 1367 1368 if (at(COLON)) { 1369 advance(); // COLON 1370 parseTypeRef(); 1371 } 1372 1373 mark.done(TYPE_PARAMETER); 1374 1375 } 1376 1377 /* 1378 * type 1379 * : attributes typeDescriptor 1380 * 1381 * typeDescriptor 1382 * : selfType 1383 * : functionType 1384 * : userType 1385 * : tupleType 1386 * : nullableType 1387 * ; 1388 * 1389 * nullableType 1390 * : typeDescriptor "?" 1391 */ 1392 void parseTypeRef() { 1393 parseTypeRef(TokenSet.EMPTY); 1394 } 1395 1396 void parseTypeRef(TokenSet extraRecoverySet) { 1397 PsiBuilder.Marker typeRefMarker = parseTypeRefContents(extraRecoverySet); 1398 typeRefMarker.done(TYPE_REFERENCE); 1399 } 1400 1401 // The extraRecoverySet is needed for the foo(bar<x, 1, y>(z)) case, to tell whether we should stop 1402 // on expression-indicating symbols or not 1403 private PsiBuilder.Marker parseTypeRefContents(TokenSet extraRecoverySet) { 1404 // Disabling token merge is required for cases like 1405 // Int?.(Foo) -> Bar 1406 // we don't support this case now 1407 // myBuilder.disableJoiningComplexTokens(); 1408 PsiBuilder.Marker typeRefMarker = mark(); 1409 parseAnnotations(false); 1410 1411 if (at(IDENTIFIER) || at(PACKAGE_KEYWORD)) { 1412 parseUserType(); 1413 } 1414 else if (at(HASH)) { 1415 parseTupleType(); 1416 } 1417 else if (at(LPAR)) { 1418 PsiBuilder.Marker functionOrParenthesizedType = mark(); 1419 1420 // This may be a function parameter list or just a prenthesized type 1421 advance(); // LPAR 1422 parseTypeRefContents(TokenSet.EMPTY).drop(); // parenthesized types, no reference element around it is needed 1423 1424 if (at(RPAR)) { 1425 advance(); // RPAR 1426 if (at(ARROW)) { 1427 // It's a function type with one parameter specified 1428 // (A) -> B 1429 functionOrParenthesizedType.rollbackTo(); 1430 parseFunctionType(); 1431 } 1432 else { 1433 // It's a parenthesized type 1434 // (A) 1435 functionOrParenthesizedType.drop(); 1436 } 1437 } 1438 else { 1439 // This must be a function type 1440 // (A, B) -> C 1441 // or 1442 // (a : A) -> C 1443 functionOrParenthesizedType.rollbackTo(); 1444 parseFunctionType(); 1445 } 1446 1447 } 1448 else if (at(CAPITALIZED_THIS_KEYWORD)) { 1449 parseSelfType(); 1450 } 1451 else { 1452 errorWithRecovery("Type expected", 1453 TokenSet.orSet(TOPLEVEL_OBJECT_FIRST, 1454 TokenSet.create(EQ, COMMA, GT, RBRACKET, DOT, RPAR, RBRACE, LBRACE, SEMICOLON), extraRecoverySet)); 1455 } 1456 1457 while (at(QUEST)) { 1458 PsiBuilder.Marker precede = typeRefMarker.precede(); 1459 1460 advance(); // QUEST 1461 typeRefMarker.done(NULLABLE_TYPE); 1462 1463 typeRefMarker = precede; 1464 } 1465 1466 if (at(DOT)) { 1467 // This is a receiver for a function type 1468 // A.(B) -> C 1469 // ^ 1470 1471 PsiBuilder.Marker functionType = typeRefMarker.precede(); 1472 PsiBuilder.Marker receiverType = typeRefMarker.precede(); 1473 typeRefMarker.done(TYPE_REFERENCE); 1474 receiverType.done(FUNCTION_TYPE_RECEIVER); 1475 1476 advance(); // DOT 1477 1478 if (at(LPAR)) { 1479 parseFunctionTypeContents().drop(); 1480 } 1481 else { 1482 error("Expecting function type"); 1483 } 1484 typeRefMarker = functionType.precede(); 1485 1486 functionType.done(FUNCTION_TYPE); 1487 } 1488 // myBuilder.restoreJoiningComplexTokensState(); 1489 return typeRefMarker; 1490 } 1491 1492 /* 1493 * userType 1494 * : ("package" ".")? simpleUserType{"."} 1495 * ; 1496 */ 1497 void parseUserType() { 1498 PsiBuilder.Marker userType = mark(); 1499 1500 if (at(PACKAGE_KEYWORD)) { 1501 advance(); // PACKAGE_KEYWORD 1502 expect(DOT, "Expecting '.'", TokenSet.create(IDENTIFIER)); 1503 } 1504 1505 PsiBuilder.Marker reference = mark(); 1506 while (true) { 1507 if (expect(IDENTIFIER, "Expecting type name", TokenSet.orSet(JetExpressionParsing.EXPRESSION_FIRST, JetExpressionParsing.EXPRESSION_FOLLOW))) { 1508 reference.done(REFERENCE_EXPRESSION); 1509 } 1510 else { 1511 reference.drop(); 1512 break; 1513 } 1514 1515 parseTypeArgumentList(); 1516 if (!at(DOT)) { 1517 break; 1518 } 1519 if (lookahead(1) == LPAR) { 1520 // This may be a receiver for a function type 1521 // Int.(Int) -> Int 1522 break; 1523 } 1524 1525 PsiBuilder.Marker precede = userType.precede(); 1526 userType.done(USER_TYPE); 1527 userType = precede; 1528 1529 advance(); // DOT 1530 reference = mark(); 1531 } 1532 1533 userType.done(USER_TYPE); 1534 } 1535 1536 /* 1537 * selfType 1538 * : "This" 1539 * ; 1540 */ 1541 private void parseSelfType() { 1542 assert _at(CAPITALIZED_THIS_KEYWORD); 1543 1544 PsiBuilder.Marker type = mark(); 1545 advance(); // CAPITALIZED_THIS_KEYWORD 1546 type.done(SELF_TYPE); 1547 } 1548 1549 /* 1550 * (optionalProjection type){","} 1551 */ 1552 private PsiBuilder.Marker parseTypeArgumentList() { 1553 if (!at(LT)) return null; 1554 1555 PsiBuilder.Marker list = mark(); 1556 1557 tryParseTypeArgumentList(TokenSet.EMPTY); 1558 1559 list.done(TYPE_ARGUMENT_LIST); 1560 return list; 1561 } 1562 1563 boolean tryParseTypeArgumentList(TokenSet extraRecoverySet) { 1564 myBuilder.disableNewlines(); 1565 advance(); // LT 1566 1567 while (true) { 1568 PsiBuilder.Marker projection = mark(); 1569 1570 // TokenSet lookFor = TokenSet.create(IDENTIFIER); 1571 // TokenSet stopAt = TokenSet.create(COMMA, COLON, GT); 1572 // parseModifierListWithShortAnnotations(MODIFIER_LIST, lookFor, stopAt); 1573 // Currently we do not allow annotations 1574 parseModifierList(MODIFIER_LIST, false); 1575 1576 if (at(MUL)) { 1577 advance(); // MUL 1578 } 1579 else { 1580 parseTypeRef(extraRecoverySet); 1581 } 1582 projection.done(TYPE_PROJECTION); 1583 if (!at(COMMA)) break; 1584 advance(); // COMMA 1585 } 1586 1587 boolean atGT = at(GT); 1588 if (!atGT) { 1589 error("Expecting a '>'"); 1590 } 1591 else { 1592 advance(); // GT 1593 } 1594 myBuilder.restoreNewlinesState(); 1595 return atGT; 1596 } 1597 1598 private void parseModifierListWithShortAnnotations(JetNodeType modifierList, TokenSet lookFor, TokenSet stopAt) { 1599 int lastId = findLastBefore(lookFor, stopAt, false); 1600 createTruncatedBuilder(lastId).parseModifierList(modifierList, true); 1601 } 1602 1603 /* 1604 * tupleType 1605 * : "#" "(" type{","}? ")" 1606 * : "#" "(" parameter{","} ")" // tuple with named entries, the names do not affect assignment compatibility 1607 * ; 1608 */ 1609 @Deprecated // Tuples are dropped, but parsing is left to minimize surprising. This code should be removed some time (in Kotlin 1.0?) 1610 private void parseTupleType() { 1611 assert _at(HASH); 1612 1613 PsiBuilder.Marker tuple = mark(); 1614 1615 myBuilder.disableNewlines(); 1616 advance(); // HASH 1617 consumeIf(LPAR); 1618 1619 if (!at(RPAR)) { 1620 while (true) { 1621 if (at(COLON)) { 1622 errorAndAdvance("Expecting a name for tuple entry"); 1623 } 1624 1625 if (at(IDENTIFIER) && lookahead(1) == COLON) { 1626 advance(); // IDENTIFIER 1627 advance(); // COLON 1628 parseTypeRef(); 1629 } 1630 else if (TYPE_REF_FIRST.contains(tt())) { 1631 parseTypeRef(); 1632 } 1633 else { 1634 error("Type expected"); 1635 break; 1636 } 1637 if (!at(COMMA)) break; 1638 advance(); // COMMA 1639 } 1640 } 1641 1642 consumeIf(RPAR); 1643 myBuilder.restoreNewlinesState(); 1644 1645 tuple.error("Tuples are not supported. Use data classes instead."); 1646 } 1647 1648 /* 1649 * functionType 1650 * : "(" (parameter | modifiers type){","}? ")" "->" type? 1651 * ; 1652 */ 1653 private void parseFunctionType() { 1654 parseFunctionTypeContents().done(FUNCTION_TYPE); 1655 } 1656 1657 private PsiBuilder.Marker parseFunctionTypeContents() { 1658 assert _at(LPAR) : tt(); 1659 PsiBuilder.Marker functionType = mark(); 1660 1661 // advance(); // LPAR 1662 // 1663 // int lastLPar = findLastBefore(TokenSet.create(LPAR), TokenSet.create(COLON), false); 1664 // if (lastLPar >= 0 && lastLPar > myBuilder.getCurrentOffset()) { 1665 // TODO : -1 is a hack? 1666 // createTruncatedBuilder(lastLPar - 1).parseTypeRef(); 1667 // advance(); // DOT 1668 // } 1669 1670 parseValueParameterList(true, TokenSet.EMPTY); 1671 1672 // if (at(COLON)) { 1673 // advance(); // COLON // expect(COLON, "Expecting ':' followed by a return type", TYPE_REF_FIRST); 1674 1675 expect(ARROW, "Expecting '->' to specify return type of a function type", TYPE_REF_FIRST); 1676 parseTypeRef(); 1677 // } 1678 1679 return functionType;//.done(FUNCTION_TYPE); 1680 } 1681 1682 /* 1683 * functionParameters 1684 * : "(" functionParameter{","}? ")" // default values 1685 * ; 1686 * 1687 * functionParameter 1688 * : modifiers functionParameterRest 1689 * ; 1690 * 1691 * functionParameterRest 1692 * : parameter ("=" element)? 1693 * ; 1694 */ 1695 void parseValueParameterList(boolean isFunctionTypeContents, TokenSet recoverySet) { 1696 assert _at(LPAR); 1697 PsiBuilder.Marker parameters = mark(); 1698 1699 myBuilder.disableNewlines(); 1700 advance(); // LPAR 1701 1702 if (!at(RPAR) && !atSet(recoverySet)) { 1703 while (true) { 1704 if (at(COMMA)) { 1705 errorAndAdvance("Expecting a parameter declaration"); 1706 } 1707 else if (at(RPAR)) { 1708 error("Expecting a parameter declaration"); 1709 break; 1710 } 1711 if (isFunctionTypeContents) { 1712 if (!tryParseValueParameter()) { 1713 PsiBuilder.Marker valueParameter = mark(); 1714 parseModifierList(MODIFIER_LIST, false); // lazy, out, ref 1715 parseTypeRef(); 1716 valueParameter.done(VALUE_PARAMETER); 1717 } 1718 } 1719 else { 1720 parseValueParameter(); 1721 } 1722 if (at(COMMA)) { 1723 advance(); // COMMA 1724 } 1725 else { 1726 if (!at(RPAR)) error("Expecting comma or ')'"); 1727 if (!atSet(VALUE_PARAMETER_FIRST)) break; 1728 } 1729 } 1730 } 1731 1732 expect(RPAR, "Expecting ')'", recoverySet); 1733 myBuilder.restoreNewlinesState(); 1734 1735 parameters.done(VALUE_PARAMETER_LIST); 1736 } 1737 1738 /* 1739 * functionParameter 1740 * : modifiers ("val" | "var")? parameter ("=" element)? 1741 * ; 1742 */ 1743 private boolean tryParseValueParameter() { 1744 return parseValueParameter(true); 1745 } 1746 1747 public void parseValueParameter() { 1748 parseValueParameter(false); 1749 } 1750 1751 private boolean parseValueParameter(boolean rollbackOnFailure) { 1752 PsiBuilder.Marker parameter = mark(); 1753 1754 parseModifierListWithShortAnnotations(MODIFIER_LIST, TokenSet.create(IDENTIFIER), TokenSet.create(COMMA, RPAR, COLON)); 1755 1756 if (at(VAR_KEYWORD) || at(VAL_KEYWORD)) { 1757 advance(); // VAR_KEYWORD | VAL_KEYWORD 1758 } 1759 1760 if (!parseFunctionParameterRest() && rollbackOnFailure) { 1761 parameter.rollbackTo(); 1762 return false; 1763 } 1764 1765 parameter.done(VALUE_PARAMETER); 1766 return true; 1767 } 1768 1769 /* 1770 * functionParameterRest 1771 * : parameter ("=" element)? 1772 * ; 1773 */ 1774 private boolean parseFunctionParameterRest() { 1775 boolean noErrors = true; 1776 1777 // Recovery for the case 'fun foo(Array<String>) {}' 1778 if (at(IDENTIFIER) && lookahead(1) == LT) { 1779 error("Parameter name expected"); 1780 parseTypeRef(); 1781 noErrors = false; 1782 } 1783 else { 1784 expect(IDENTIFIER, "Parameter name expected", PARAMETER_NAME_RECOVERY_SET); 1785 1786 if (at(COLON)) { 1787 advance(); // COLON 1788 parseTypeRef(); 1789 } 1790 else { 1791 errorWithRecovery("Parameters must have type annotation", PARAMETER_NAME_RECOVERY_SET); 1792 noErrors = false; 1793 } 1794 } 1795 1796 if (at(EQ)) { 1797 advance(); // EQ 1798 myExpressionParsing.parseExpression(); 1799 } 1800 1801 return noErrors; 1802 } 1803 1804 @Override 1805 protected JetParsing create(SemanticWhitespaceAwarePsiBuilder builder) { 1806 return createForTopLevel(builder); 1807 } 1808 1809 /*package*/ static class TokenDetector implements Consumer<IElementType> { 1810 1811 private boolean detected = false; 1812 private final TokenSet tokens; 1813 1814 public TokenDetector(JetKeywordToken token) { 1815 this.tokens = TokenSet.create(token); 1816 } 1817 1818 @Override 1819 public void consume(IElementType item) { 1820 if (tokens.contains(item)) { 1821 detected = true; 1822 } 1823 } 1824 1825 public boolean isDetected() { 1826 return detected; 1827 } 1828 } 1829 }