001 /*
002 * Copyright 2010-2015 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.kotlin.parsing;
018
019 import com.intellij.lang.PsiBuilder;
020 import com.intellij.openapi.diagnostic.Logger;
021 import com.intellij.psi.tree.IElementType;
022 import com.intellij.psi.tree.TokenSet;
023 import org.jetbrains.annotations.NotNull;
024 import org.jetbrains.annotations.Nullable;
025 import org.jetbrains.kotlin.JetNodeType;
026 import org.jetbrains.kotlin.lexer.JetKeywordToken;
027 import org.jetbrains.kotlin.lexer.JetTokens;
028
029 import java.util.HashMap;
030 import java.util.Map;
031
032 import static org.jetbrains.kotlin.JetNodeTypes.*;
033 import static org.jetbrains.kotlin.lexer.JetTokens.*;
034 import static org.jetbrains.kotlin.parsing.JetParsing.AnnotationParsingMode.*;
035 import static org.jetbrains.kotlin.parsing.JetParsing.DeclarationParsingMode.*;
036
037 public class JetParsing extends AbstractJetParsing {
038 private static final Logger LOG = Logger.getInstance(JetParsing.class);
039
040 // TODO: token sets to constants, including derived methods
041 public static final Map<String, IElementType> MODIFIER_KEYWORD_MAP = new HashMap<String, IElementType>();
042 static {
043 for (IElementType softKeyword : MODIFIER_KEYWORDS.getTypes()) {
044 MODIFIER_KEYWORD_MAP.put(((JetKeywordToken) softKeyword).getValue(), softKeyword);
045 }
046 }
047
048 private static final TokenSet TOP_LEVEL_DECLARATION_FIRST = TokenSet.create(
049 TYPE_ALIAS_KEYWORD, TRAIT_KEYWORD, INTERFACE_KEYWORD, CLASS_KEYWORD, OBJECT_KEYWORD,
050 FUN_KEYWORD, VAL_KEYWORD, PACKAGE_KEYWORD);
051 private static final TokenSet DECLARATION_FIRST = TokenSet.orSet(TOP_LEVEL_DECLARATION_FIRST,
052 TokenSet.create(INIT_KEYWORD, GET_KEYWORD, SET_KEYWORD, CONSTRUCTOR_KEYWORD));
053
054 private static final TokenSet CLASS_NAME_RECOVERY_SET = TokenSet.orSet(TokenSet.create(LT, LPAR, COLON, LBRACE),
055 TOP_LEVEL_DECLARATION_FIRST);
056 private static final TokenSet TYPE_PARAMETER_GT_RECOVERY_SET = TokenSet.create(WHERE_KEYWORD, LPAR, COLON, LBRACE, GT);
057 private static final TokenSet PARAMETER_NAME_RECOVERY_SET = TokenSet.create(COLON, EQ, COMMA, RPAR);
058 private static final TokenSet PACKAGE_NAME_RECOVERY_SET = TokenSet.create(DOT, EOL_OR_SEMICOLON);
059 private static final TokenSet IMPORT_RECOVERY_SET = TokenSet.create(AS_KEYWORD, DOT, EOL_OR_SEMICOLON);
060 /*package*/ static final TokenSet TYPE_REF_FIRST = TokenSet.create(LBRACKET, IDENTIFIER, LPAR, CAPITALIZED_THIS_KEYWORD, HASH, DYNAMIC_KEYWORD);
061 private static final TokenSet RECEIVER_TYPE_TERMINATORS = TokenSet.create(DOT, SAFE_ACCESS);
062 private static final TokenSet VALUE_PARAMETER_FIRST =
063 TokenSet.orSet(TokenSet.create(IDENTIFIER, LBRACKET, VAL_KEYWORD, VAR_KEYWORD), MODIFIER_KEYWORDS);
064 private static final TokenSet LAMBDA_VALUE_PARAMETER_FIRST =
065 TokenSet.orSet(TokenSet.create(IDENTIFIER, LBRACKET), MODIFIER_KEYWORDS);
066 private static final TokenSet SOFT_KEYWORDS_AT_MEMBER_START = TokenSet.create(CONSTRUCTOR_KEYWORD, INIT_KEYWORD);
067
068 static JetParsing createForTopLevel(SemanticWhitespaceAwarePsiBuilder builder) {
069 JetParsing jetParsing = new JetParsing(builder);
070 jetParsing.myExpressionParsing = new JetExpressionParsing(builder, jetParsing);
071 return jetParsing;
072 }
073
074 private static JetParsing createForByClause(SemanticWhitespaceAwarePsiBuilder builder) {
075 final SemanticWhitespaceAwarePsiBuilderForByClause builderForByClause = new SemanticWhitespaceAwarePsiBuilderForByClause(builder);
076 JetParsing jetParsing = new JetParsing(builderForByClause);
077 jetParsing.myExpressionParsing = new JetExpressionParsing(builderForByClause, jetParsing) {
078 @Override
079 protected boolean parseCallWithClosure() {
080 if (builderForByClause.getStackSize() > 0) {
081 return super.parseCallWithClosure();
082 }
083 return false;
084 }
085
086 @Override
087 protected JetParsing create(SemanticWhitespaceAwarePsiBuilder builder) {
088 return createForByClause(builder);
089 }
090 };
091 return jetParsing;
092 }
093
094 private JetExpressionParsing myExpressionParsing;
095
096 private JetParsing(SemanticWhitespaceAwarePsiBuilder builder) {
097 super(builder);
098 }
099
100 /*
101 * [start] jetlFile
102 * : preamble toplevelObject* [eof]
103 * ;
104 */
105 void parseFile() {
106 PsiBuilder.Marker fileMarker = mark();
107
108 parsePreamble();
109
110 while (!eof()) {
111 parseTopLevelDeclaration();
112 }
113
114 fileMarker.done(JET_FILE);
115 }
116
117 void parseTypeCodeFragment() {
118 PsiBuilder.Marker marker = mark();
119 parseTypeRef();
120
121 checkForUnexpectedSymbols();
122
123 marker.done(TYPE_CODE_FRAGMENT);
124 }
125
126 void parseExpressionCodeFragment() {
127 PsiBuilder.Marker marker = mark();
128 myExpressionParsing.parseExpression();
129
130 checkForUnexpectedSymbols();
131
132 marker.done(EXPRESSION_CODE_FRAGMENT);
133 }
134
135 void parseBlockCodeFragment() {
136 PsiBuilder.Marker marker = mark();
137 PsiBuilder.Marker blockMarker = mark();
138
139 if (at(PACKAGE_KEYWORD) || at(IMPORT_KEYWORD)) {
140 PsiBuilder.Marker err = mark();
141 parsePreamble();
142 err.error("Package directive and imports are forbidden in code fragments");
143 }
144
145 myExpressionParsing.parseStatements();
146
147 checkForUnexpectedSymbols();
148
149 blockMarker.done(BLOCK);
150 marker.done(BLOCK_CODE_FRAGMENT);
151 }
152
153 void parseScript() {
154 PsiBuilder.Marker fileMarker = mark();
155
156 parsePreamble();
157
158 PsiBuilder.Marker scriptMarker = mark();
159
160 PsiBuilder.Marker blockMarker = mark();
161
162 myExpressionParsing.parseStatements();
163
164 checkForUnexpectedSymbols();
165
166 blockMarker.done(BLOCK);
167 scriptMarker.done(SCRIPT);
168 fileMarker.done(JET_FILE);
169 }
170
171 private void checkForUnexpectedSymbols() {
172 while (!eof()) {
173 errorAndAdvance("unexpected symbol");
174 }
175 }
176
177 /*
178 *preamble
179 * : fileAnnotationList? packageDirective? import*
180 * ;
181 */
182 private void parsePreamble() {
183 PsiBuilder.Marker firstEntry = mark();
184
185 /*
186 * fileAnnotationList
187 * : fileAnnotations*
188 */
189 parseFileAnnotationList(FILE_ANNOTATIONS_BEFORE_PACKAGE);
190
191 /*
192 * packageDirective
193 * : modifiers "package" SimpleName{"."} SEMI?
194 * ;
195 */
196 PsiBuilder.Marker packageDirective = mark();
197 parseModifierList(ALLOW_UNESCAPED_REGULAR_ANNOTATIONS);
198
199 if (at(PACKAGE_KEYWORD)) {
200 advance(); // PACKAGE_KEYWORD
201
202 parsePackageName();
203
204 firstEntry.drop();
205
206 consumeIf(SEMICOLON);
207
208 packageDirective.done(PACKAGE_DIRECTIVE);
209 }
210 else {
211 // When package directive is omitted we should not report error on non-file annotations at the beginning of the file.
212 // So, we rollback the parsing position and reparse file annotation list without report error on non-file annotations.
213 firstEntry.rollbackTo();
214
215 parseFileAnnotationList(FILE_ANNOTATIONS_WHEN_PACKAGE_OMITTED);
216 packageDirective = mark();
217 packageDirective.done(PACKAGE_DIRECTIVE);
218 // this is necessary to allow comments at the start of the file to be bound to the first declaration
219 packageDirective.setCustomEdgeTokenBinders(DoNotBindAnything.INSTANCE$, null);
220 }
221
222 parseImportDirectives();
223 }
224
225 /* SimpleName{"."} */
226 private void parsePackageName() {
227 PsiBuilder.Marker qualifiedExpression = mark();
228 boolean simpleName = true;
229 while (true) {
230 if (myBuilder.newlineBeforeCurrentToken()) {
231 errorWithRecovery("Package name must be a '.'-separated identifier list placed on a single line", PACKAGE_NAME_RECOVERY_SET);
232 break;
233 }
234
235 if (at(DOT)) {
236 advance(); // DOT
237 qualifiedExpression.error("Package name must be a '.'-separated identifier list");
238 qualifiedExpression = mark();
239 continue;
240 }
241
242 PsiBuilder.Marker nsName = mark();
243 boolean simpleNameFound = expect(IDENTIFIER, "Package name must be a '.'-separated identifier list", PACKAGE_NAME_RECOVERY_SET);
244 if (simpleNameFound) {
245 nsName.done(REFERENCE_EXPRESSION);
246 }
247 else {
248 nsName.drop();
249 }
250
251 if (!simpleName) {
252 PsiBuilder.Marker precedingMarker = qualifiedExpression.precede();
253 qualifiedExpression.done(DOT_QUALIFIED_EXPRESSION);
254 qualifiedExpression = precedingMarker;
255 }
256
257 if (at(DOT)) {
258 advance(); // DOT
259
260 if (simpleName && !simpleNameFound) {
261 qualifiedExpression.drop();
262 qualifiedExpression = mark();
263 }
264 else {
265 simpleName = false;
266 }
267 }
268 else {
269 break;
270 }
271 }
272 qualifiedExpression.drop();
273 }
274
275 /*
276 * import
277 * : "import" SimpleName{"."} ("." "*" | "as" SimpleName)? SEMI?
278 * ;
279 */
280 private void parseImportDirective() {
281 assert _at(IMPORT_KEYWORD);
282 PsiBuilder.Marker importDirective = mark();
283 advance(); // IMPORT_KEYWORD
284
285 if (closeImportWithErrorIfNewline(importDirective, "Expecting qualified name")) {
286 return;
287 }
288
289 PsiBuilder.Marker qualifiedName = mark();
290
291 PsiBuilder.Marker reference = mark();
292 expect(IDENTIFIER, "Expecting qualified name");
293 reference.done(REFERENCE_EXPRESSION);
294
295 while (at(DOT) && lookahead(1) != MUL) {
296 advance(); // DOT
297
298 if (closeImportWithErrorIfNewline(importDirective, "Import must be placed on a single line")) {
299 qualifiedName.drop();
300 return;
301 }
302
303 reference = mark();
304 if (expect(IDENTIFIER, "Qualified name must be a '.'-separated identifier list", IMPORT_RECOVERY_SET)) {
305 reference.done(REFERENCE_EXPRESSION);
306 }
307 else {
308 reference.drop();
309 }
310
311 PsiBuilder.Marker precede = qualifiedName.precede();
312 qualifiedName.done(DOT_QUALIFIED_EXPRESSION);
313 qualifiedName = precede;
314 }
315 qualifiedName.drop();
316
317 if (at(DOT)) {
318 advance(); // DOT
319 assert _at(MUL);
320 advance(); // MUL
321 if (at(AS_KEYWORD)) {
322 PsiBuilder.Marker as = mark();
323 advance(); // AS_KEYWORD
324 if (closeImportWithErrorIfNewline(importDirective, "Expecting identifier")) {
325 as.drop();
326 return;
327 }
328 consumeIf(IDENTIFIER);
329 as.error("Cannot rename all imported items to one identifier");
330 }
331 }
332 if (at(AS_KEYWORD)) {
333 advance(); // AS_KEYWORD
334 if (closeImportWithErrorIfNewline(importDirective, "Expecting identifier")) {
335 return;
336 }
337 expect(IDENTIFIER, "Expecting identifier", TokenSet.create(SEMICOLON));
338 }
339 consumeIf(SEMICOLON);
340 importDirective.done(IMPORT_DIRECTIVE);
341 importDirective.setCustomEdgeTokenBinders(null, TrailingCommentsBinder.INSTANCE$);
342 }
343
344 private boolean closeImportWithErrorIfNewline(PsiBuilder.Marker importDirective, String errorMessage) {
345 if (myBuilder.newlineBeforeCurrentToken()) {
346 error(errorMessage);
347 importDirective.done(IMPORT_DIRECTIVE);
348 return true;
349 }
350 return false;
351 }
352
353 private void parseImportDirectives() {
354 PsiBuilder.Marker importList = mark();
355 if (!at(IMPORT_KEYWORD)) {
356 // this is necessary to allow comments at the start of the file to be bound to the first declaration
357 importList.setCustomEdgeTokenBinders(DoNotBindAnything.INSTANCE$, null);
358 }
359 while (at(IMPORT_KEYWORD)) {
360 parseImportDirective();
361 }
362 importList.done(IMPORT_LIST);
363 }
364
365 /*
366 * toplevelObject
367 * : package
368 * : class
369 * : extension
370 * : function
371 * : property
372 * : typeAlias
373 * : object
374 * ;
375 */
376 private void parseTopLevelDeclaration() {
377 if (at(SEMICOLON)) {
378 advance(); // SEMICOLON
379 return;
380 }
381 PsiBuilder.Marker decl = mark();
382
383 ModifierDetector detector = new ModifierDetector();
384 parseModifierList(detector, ALLOW_UNESCAPED_REGULAR_ANNOTATIONS);
385
386 IElementType keywordToken = tt();
387 IElementType declType = null;
388 // if (keywordToken == PACKAGE_KEYWORD) {
389 // declType = parsePackageBlock();
390 // }
391 // else
392 if (keywordToken == CLASS_KEYWORD || keywordToken == TRAIT_KEYWORD || keywordToken == INTERFACE_KEYWORD) {
393 declType = parseClass(detector.isEnumDetected(), TOP_LEVEL);
394 }
395 else if (keywordToken == FUN_KEYWORD) {
396 declType = parseFunction();
397 }
398 else if (keywordToken == VAL_KEYWORD || keywordToken == VAR_KEYWORD) {
399 declType = parseProperty();
400 }
401 else if (keywordToken == TYPE_ALIAS_KEYWORD) {
402 declType = parseTypeAlias();
403 }
404 else if (keywordToken == OBJECT_KEYWORD) {
405 parseObject(NameParsingMode.REQUIRED, true, TOP_LEVEL);
406 declType = OBJECT_DECLARATION;
407 }
408 else if (at(LBRACE)) {
409 error("Expecting a top level declaration");
410 parseBlock();
411 declType = FUN;
412 }
413
414 if (declType == null) {
415 errorAndAdvance("Expecting a top level declaration");
416 decl.drop();
417 }
418 else {
419 closeDeclarationWithCommentBinders(decl, declType, true);
420 }
421 }
422
423 /*
424 * (modifier | annotation)*
425 */
426 boolean parseModifierList(
427 @NotNull AnnotationParsingMode annotationParsingMode
428 ) {
429 return parseModifierList(null, annotationParsingMode);
430 }
431
432 /**
433 * (modifier | annotation)*
434 *
435 * Feeds modifiers (not annotations) into the passed consumer, if it is not null
436 */
437 boolean parseModifierList(
438 @Nullable Consumer<IElementType> tokenConsumer,
439 @NotNull AnnotationParsingMode annotationParsingMode
440 ) {
441 PsiBuilder.Marker list = mark();
442 boolean empty = true;
443 while (!eof()) {
444 if (annotationParsingMode.atMemberStart && atSet(SOFT_KEYWORDS_AT_MEMBER_START)) break;
445 if ((annotationParsingMode == PRIMARY_CONSTRUCTOR_MODIFIER_LIST || annotationParsingMode == PRIMARY_CONSTRUCTOR_MODIFIER_LIST_LOCAL) &&
446 atSet(CONSTRUCTOR_KEYWORD, WHERE_KEYWORD)) break;
447
448 if (at(AT)) {
449 if (!tryParseModifier(tokenConsumer)) {
450 parseAnnotation(annotationParsingMode);
451 }
452 }
453 else if (tryParseModifier(tokenConsumer)) {
454 // modifier advanced
455 }
456 else if (at(LBRACKET) || (annotationParsingMode.allowShortAnnotations && at(IDENTIFIER))) {
457 parseAnnotation(annotationParsingMode);
458 }
459 else {
460 break;
461 }
462 empty = false;
463 }
464 if (empty) {
465 list.drop();
466 }
467 else {
468 list.done(MODIFIER_LIST);
469 }
470 return !empty;
471 }
472
473 private boolean tryParseModifier(@Nullable Consumer<IElementType> tokenConsumer) {
474 PsiBuilder.Marker marker = mark();
475
476 if (at(AT) && !WHITE_SPACE_OR_COMMENT_BIT_SET.contains(myBuilder.rawLookup(1))) {
477 advance(); // AT
478 }
479
480 if (atSet(MODIFIER_KEYWORDS)) {
481 IElementType tt = tt();
482 if (tokenConsumer != null) {
483 tokenConsumer.consume(tt);
484 }
485 advance(); // MODIFIER
486 marker.collapse(tt);
487 return true;
488 }
489
490 marker.rollbackTo();
491 return false;
492 }
493
494 /*
495 * fileAnnotationList
496 * : ("[" "file:" annotationEntry+ "]")*
497 * ;
498 */
499 private void parseFileAnnotationList(AnnotationParsingMode mode) {
500 if (!mode.isFileAnnotationParsingMode) {
501 LOG.error("expected file annotation parsing mode, but:" + mode);
502 }
503
504 PsiBuilder.Marker fileAnnotationsList = mark();
505
506 if (parseAnnotations(mode)) {
507 fileAnnotationsList.done(FILE_ANNOTATION_LIST);
508 }
509 else {
510 fileAnnotationsList.drop();
511 }
512 }
513
514 /*
515 * annotations
516 * : annotation*
517 * ;
518 */
519 boolean parseAnnotations(AnnotationParsingMode mode) {
520 if (!parseAnnotation(mode)) return false;
521
522 while (parseAnnotation(mode)) {
523 // do nothing
524 }
525
526 return true;
527 }
528
529 /*
530 * annotation
531 * : "[" ("file" ":")? annotationEntry+ "]"
532 * : annotationEntry
533 * : "@" annotationEntry
534 * ;
535 */
536 private boolean parseAnnotation(AnnotationParsingMode mode) {
537 if (at(LBRACKET)) {
538 return parseAnnotationList(mode, false);
539 }
540 else if (mode.allowShortAnnotations && at(IDENTIFIER)) {
541 return parseAnnotationEntry(mode);
542 }
543 else if (at(AT)) {
544 IElementType nextRawToken = myBuilder.rawLookup(1);
545 IElementType tokenToMatch = nextRawToken;
546 boolean isTargetedAnnotation = false;
547
548 if ((nextRawToken == IDENTIFIER || nextRawToken == FILE_KEYWORD) && lookahead(2) == COLON) {
549 tokenToMatch = lookahead(3);
550 isTargetedAnnotation = true;
551 }
552 else if (lookahead(1) == COLON) {
553 // recovery for "@:ann"
554 isTargetedAnnotation = true;
555 tokenToMatch = lookahead(2);
556 }
557
558 if (tokenToMatch == IDENTIFIER) {
559 return parseAnnotationEntry(mode);
560 }
561 else if (tokenToMatch == LBRACKET) {
562 return parseAnnotationList(mode, true);
563 }
564 else {
565 if (isTargetedAnnotation) {
566 if (lookahead(1) == COLON) {
567 errorAndAdvance("Expected annotation identifier after ':'", 2); // AT, COLON
568 }
569 else {
570 errorAndAdvance("Expected annotation identifier after '@file:'", 3); // AT, FILE_KEYWORD, COLON
571 }
572 }
573 else {
574 errorAndAdvance("Expected annotation identifier after '@'", 1); // AT
575 }
576 }
577 return true;
578 }
579
580 return false;
581 }
582
583 private boolean parseAnnotationList(AnnotationParsingMode mode, boolean expectAtSymbol) {
584 assert !expectAtSymbol || _at(AT);
585 assert expectAtSymbol || _at(LBRACKET);
586 PsiBuilder.Marker annotation = mark();
587
588 myBuilder.disableNewlines();
589
590 advance(); // AT or LBRACKET
591
592 if (!parseAnnotationTargetIfNeeded(mode)) {
593 annotation.rollbackTo();
594 myBuilder.restoreNewlinesState();
595 return false;
596 }
597
598 if (expectAtSymbol) {
599 assert _at(LBRACKET);
600 advance(); // LBRACKET
601 }
602
603 if (!at(IDENTIFIER) && !at(AT)) {
604 error("Expecting a list of annotations");
605 }
606 else {
607 while (at(IDENTIFIER) || at(AT)) {
608 if (at(AT)) {
609 errorAndAdvance("No '@' needed in annotation list"); // AT
610 continue;
611 }
612
613 parseAnnotationEntry(ALLOW_UNESCAPED_REGULAR_ANNOTATIONS);
614 while (at(COMMA)) {
615 errorAndAdvance("No commas needed to separate annotations");
616 }
617 }
618 }
619
620 expect(RBRACKET, "Expecting ']' to close the annotation list");
621 myBuilder.restoreNewlinesState();
622
623 annotation.done(ANNOTATION);
624 return true;
625 }
626
627 // Returns true if we should continue parse annotation
628 private boolean parseAnnotationTargetIfNeeded(AnnotationParsingMode mode) {
629 if (mode.isFileAnnotationParsingMode) {
630 if (at(COLON)) {
631 // recovery for "@:ann"
632 errorAndAdvance("Expected 'file' keyword before ':'"); // COLON
633 return true;
634 }
635
636 if (lookahead(1) == COLON && !at(FILE_KEYWORD) && at(IDENTIFIER)) {
637 // recovery for "@fil:ann"
638 errorAndAdvance("Expected 'file' keyword as target"); // IDENTIFIER
639 advance(); // COLON
640 return true;
641 }
642
643 if (mode == FILE_ANNOTATIONS_WHEN_PACKAGE_OMITTED && !(at(FILE_KEYWORD) && lookahead(1) == COLON)) {
644 return false;
645 }
646
647 String message = "Expecting \"" + FILE_KEYWORD.getValue() + COLON.getValue() + "\" prefix for file annotations";
648 expect(FILE_KEYWORD, message);
649 expect(COLON, message, TokenSet.create(IDENTIFIER, RBRACKET, LBRACKET));
650 }
651 else if (at(FILE_KEYWORD) && lookahead(1) == COLON) {
652 errorAndAdvance("File annotations are only allowed before package declaration", 2);
653 }
654
655 return true;
656 }
657
658 /*
659 * annotationEntry
660 * : SimpleName{"."} typeArguments? valueArguments?
661 * ;
662 */
663 private boolean parseAnnotationEntry(AnnotationParsingMode mode) {
664 assert _at(IDENTIFIER) ||
665 (_at(AT) && !WHITE_SPACE_OR_COMMENT_BIT_SET.contains(myBuilder.rawLookup(1)));
666
667 PsiBuilder.Marker annotation = mark();
668
669 if (at(AT)) {
670 advance(); // AT
671 }
672
673 if (!parseAnnotationTargetIfNeeded(mode)) {
674 annotation.rollbackTo();
675 return false;
676 }
677
678 PsiBuilder.Marker reference = mark();
679 PsiBuilder.Marker typeReference = mark();
680 parseUserType();
681 typeReference.done(TYPE_REFERENCE);
682 reference.done(CONSTRUCTOR_CALLEE);
683
684 parseTypeArgumentList();
685
686 if (at(LPAR)) {
687 myExpressionParsing.parseValueArgumentList();
688 }
689 annotation.done(ANNOTATION_ENTRY);
690
691 return true;
692 }
693
694 public enum NameParsingMode {
695 REQUIRED,
696 ALLOWED,
697 PROHIBITED
698 }
699
700 public enum DeclarationParsingMode {
701 TOP_LEVEL,
702 CLASS_MEMBER,
703 LOCAL
704 }
705
706 /*
707 * class
708 * : modifiers ("class" | "interface") SimpleName
709 * typeParameters?
710 * primaryConstructor?
711 * (":" annotations delegationSpecifier{","})?
712 * typeConstraints
713 * (classBody? | enumClassBody)
714 * ;
715 *
716 * primaryConstructor
717 * : (modifiers "constructor")? ("(" functionParameter{","} ")")
718 * ;
719 *
720 * object
721 * : "object" SimpleName? primaryConstructor? ":" delegationSpecifier{","}? classBody?
722 * ;
723 */
724 IElementType parseClassOrObject(
725 boolean object,
726 NameParsingMode nameParsingMode,
727 boolean optionalBody,
728 boolean enumClass,
729 DeclarationParsingMode declarationParsingMode
730 ) {
731 if (object) {
732 assert _at(OBJECT_KEYWORD);
733 }
734 else {
735 assert _atSet(CLASS_KEYWORD, TRAIT_KEYWORD, INTERFACE_KEYWORD);
736 }
737 advance(); // CLASS_KEYWORD, TRAIT_KEYWORD or OBJECT_KEYWORD
738
739 if (nameParsingMode == NameParsingMode.REQUIRED) {
740 OptionalMarker marker = new OptionalMarker(object);
741 expect(IDENTIFIER, "Name expected", CLASS_NAME_RECOVERY_SET);
742 marker.done(OBJECT_DECLARATION_NAME);
743 }
744 else {
745 assert object : "Must be an object to be nameless";
746 if (at(IDENTIFIER)) {
747 if (nameParsingMode == NameParsingMode.PROHIBITED) {
748 errorAndAdvance("An object expression cannot bind a name");
749 }
750 else {
751 assert nameParsingMode == NameParsingMode.ALLOWED;
752 PsiBuilder.Marker marker = mark();
753 advance();
754 marker.done(OBJECT_DECLARATION_NAME);
755 }
756 }
757 }
758
759 OptionalMarker typeParamsMarker = new OptionalMarker(object);
760 boolean typeParametersDeclared = parseTypeParameterList(TYPE_PARAMETER_GT_RECOVERY_SET);
761 typeParamsMarker.error("Type parameters are not allowed for objects");
762
763 PsiBuilder.Marker beforeConstructorModifiers = mark();
764 PsiBuilder.Marker primaryConstructorMarker = mark();
765 boolean hasConstructorModifiers = parseModifierList(
766 declarationParsingMode != LOCAL ? PRIMARY_CONSTRUCTOR_MODIFIER_LIST : PRIMARY_CONSTRUCTOR_MODIFIER_LIST_LOCAL
767 );
768
769 // Some modifiers found, but no parentheses following: class has already ended, and we are looking at something else
770 if (hasConstructorModifiers && !atSet(LPAR, LBRACE, COLON, CONSTRUCTOR_KEYWORD)) {
771 beforeConstructorModifiers.rollbackTo();
772 return object ? OBJECT_DECLARATION : CLASS;
773 }
774
775 // We are still inside a class declaration
776 beforeConstructorModifiers.drop();
777
778 boolean hasConstructorKeyword = at(CONSTRUCTOR_KEYWORD);
779 if (hasConstructorKeyword) {
780 advance(); // CONSTRUCTOR_KEYWORD
781 }
782
783 if (at(LPAR)) {
784 parseValueParameterList(false, /* typeRequired = */ true, TokenSet.create(LBRACE, RBRACE));
785 primaryConstructorMarker.done(PRIMARY_CONSTRUCTOR);
786 }
787 else if (hasConstructorModifiers || hasConstructorKeyword) {
788 // A comprehensive error message for cases like:
789 // class A private : Foo
790 // or
791 // class A private {
792 primaryConstructorMarker.done(PRIMARY_CONSTRUCTOR);
793 if (hasConstructorKeyword) {
794 error("Expecting primary constructor parameter list");
795 }
796 else {
797 error("Expecting 'constructor' keyword");
798 }
799 }
800 else {
801 primaryConstructorMarker.drop();
802 }
803
804 if (at(COLON)) {
805 advance(); // COLON
806 parseDelegationSpecifierList();
807 }
808
809 OptionalMarker whereMarker = new OptionalMarker(object);
810 parseTypeConstraintsGuarded(typeParametersDeclared);
811 whereMarker.error("Where clause is not allowed for objects");
812
813 if (at(LBRACE)) {
814 if (enumClass) {
815 parseEnumClassBody();
816 }
817 else {
818 parseClassBody();
819 }
820 }
821 else if (!optionalBody) {
822 PsiBuilder.Marker fakeBody = mark();
823 error("Expecting a class body");
824 fakeBody.done(CLASS_BODY);
825 }
826
827 return object ? OBJECT_DECLARATION : CLASS;
828 }
829
830 IElementType parseClass(boolean enumClass, DeclarationParsingMode declarationParsingMode) {
831 return parseClassOrObject(false, NameParsingMode.REQUIRED, true, enumClass, declarationParsingMode);
832 }
833
834 void parseObject(NameParsingMode nameParsingMode, boolean optionalBody, DeclarationParsingMode declarationParsingMode) {
835 parseClassOrObject(true, nameParsingMode, optionalBody, false, declarationParsingMode);
836 }
837
838 /*
839 * enumClassBody
840 * : "{" enumEntries ";"? members "}"
841 * ;
842 */
843 private void parseEnumClassBody() {
844 if (!at(LBRACE)) return;
845
846 PsiBuilder.Marker body = mark();
847 myBuilder.enableNewlines();
848
849 advance(); // LBRACE
850
851 parseEnumEntries();
852 // TODO: syntax without SEMICOLON is deprecated, KT-7605
853 consumeIf(SEMICOLON);
854 parseMembers(true); // Members can include also entries, but it's deprecated syntax
855
856 expect(RBRACE, "Expecting '}' to close enum class body");
857 myBuilder.restoreNewlinesState();
858 body.done(CLASS_BODY);
859 }
860
861 /**
862 * enumEntries
863 * : (enumEntry ","? )?
864 * ;
865 */
866 private void parseEnumEntries() {
867 while (!eof() && !at(RBRACE)) {
868 if (!parseEnumEntry()) {
869 break;
870 }
871 parseEnumEntryDelimiter();
872 }
873 }
874
875 private void parseEnumEntryDelimiter() {
876 // TODO: syntax with SEMICOLON between enum entries is deprecated, KT-7605
877 if (at(SEMICOLON)) {
878 // Semicolon can be legally here only if member follows
879 PsiBuilder.Marker temp = mark();
880 advance(); // SEMICOLON
881 ModifierDetector detector = new ModifierDetector();
882 parseModifierList(detector, ONLY_ESCAPED_REGULAR_ANNOTATIONS);
883 if (!atSet(SOFT_KEYWORDS_AT_MEMBER_START) && at(IDENTIFIER)) {
884 // Otherwise it's old syntax that's not supported
885 temp.rollbackTo();
886 // Despite of the error, try to restore and parse next enum entry
887 temp = mark();
888 advance(); // SEMICOLON
889 temp.error("Expecting ','");
890 }
891 else {
892 temp.rollbackTo();
893 }
894 }
895 else {
896 // TODO: syntax without COMMA is deprecated (only last entry is an exception), KT-7605
897 consumeIf(COMMA);
898 }
899 }
900
901 /*
902 * enumEntry
903 * : modifiers SimpleName ((":" initializer) | ("(" arguments ")"))? classBody?
904 * ;
905 */
906 private boolean parseEnumEntry() {
907 PsiBuilder.Marker entry = mark();
908
909 ModifierDetector detector = new ModifierDetector();
910 parseModifierList(detector, ONLY_ESCAPED_REGULAR_ANNOTATIONS);
911
912 if (!atSet(SOFT_KEYWORDS_AT_MEMBER_START) && at(IDENTIFIER)) {
913 PsiBuilder.Marker nameAsDeclaration = mark();
914 advance(); // IDENTIFIER
915 nameAsDeclaration.done(OBJECT_DECLARATION_NAME);
916
917 if (at(LPAR)) {
918 // Arguments should be parsed here
919 // Also, "fake" constructor call tree is created,
920 // with empty type name inside
921 PsiBuilder.Marker initializerList = mark();
922 PsiBuilder.Marker delegatorSuperCall = mark();
923
924 PsiBuilder.Marker callee = mark();
925 PsiBuilder.Marker typeReference = mark();
926 PsiBuilder.Marker type = mark();
927 PsiBuilder.Marker referenceExpr = mark();
928 referenceExpr.done(ENUM_ENTRY_SUPERCLASS_REFERENCE_EXPRESSION);
929 type.done(USER_TYPE);
930 typeReference.done(TYPE_REFERENCE);
931 callee.done(CONSTRUCTOR_CALLEE);
932
933 myExpressionParsing.parseValueArgumentList();
934 delegatorSuperCall.done(DELEGATOR_SUPER_CALL);
935 initializerList.done(INITIALIZER_LIST);
936 }
937 // TODO: syntax with COLON is deprecated, should be changed to syntax with LPAR above, KT-7605
938 else if (at(COLON)) {
939 advance(); // COLON
940
941 parseInitializerList();
942 }
943 if (at(LBRACE)) {
944 parseClassBody();
945 }
946
947 // Probably some helper function
948 closeDeclarationWithCommentBinders(entry, ENUM_ENTRY, true);
949 return true;
950 }
951 else {
952 entry.rollbackTo();
953 return false;
954 }
955 }
956
957 /*
958 * classBody
959 * : ("{" members "}")?
960 * ;
961 */
962 private void parseClassBody() {
963 PsiBuilder.Marker body = mark();
964
965 myBuilder.enableNewlines();
966
967 if (expect(LBRACE, "Expecting a class body")) {
968 parseMembers();
969 expect(RBRACE, "Missing '}");
970 }
971
972 myBuilder.restoreNewlinesState();
973
974 body.done(CLASS_BODY);
975 }
976
977 /**
978 * members
979 * : memberDeclaration*
980 * ;
981 */
982 private void parseMembers() {
983 parseMembers(false);
984 }
985
986 private void parseMembers(boolean deprecatedEnumEntryPossible) {
987 while (!eof()) {
988 if (at(RBRACE)) {
989 break;
990 }
991 if (deprecatedEnumEntryPossible && parseEnumEntry()) {
992 // Enum entry is deprecated here
993 // Error is generated later in DeclarationsChecker
994 parseEnumEntryDelimiter();
995 consumeIf(SEMICOLON);
996 }
997 else {
998 parseMemberDeclaration();
999 }
1000 }
1001 }
1002
1003 /*
1004 * memberDeclaration
1005 * : modifiers memberDeclaration'
1006 * ;
1007 *
1008 * memberDeclaration'
1009 * : companionObject
1010 * : secondaryConstructor
1011 * : function
1012 * : property
1013 * : class
1014 * : extension
1015 * : typeAlias
1016 * : anonymousInitializer
1017 * : object
1018 * ;
1019 */
1020 private void parseMemberDeclaration() {
1021 if (at(SEMICOLON)) {
1022 advance(); // SEMICOLON
1023 return;
1024 }
1025 PsiBuilder.Marker decl = mark();
1026
1027 ModifierDetector detector = new ModifierDetector();
1028 parseModifierList(detector, ALLOW_UNESCAPED_REGULAR_ANNOTATIONS_AT_MEMBER_MODIFIER_LIST);
1029
1030 IElementType declType = parseMemberDeclarationRest(detector.isEnumDetected(), detector.isDefaultDetected());
1031
1032 if (declType == null) {
1033 errorWithRecovery("Expecting member declaration", TokenSet.EMPTY);
1034 decl.drop();
1035 }
1036 else {
1037 closeDeclarationWithCommentBinders(decl, declType, true);
1038 }
1039 }
1040
1041 private IElementType parseMemberDeclarationRest(boolean isEnum, boolean isDefault) {
1042 IElementType keywordToken = tt();
1043 IElementType declType = null;
1044 if (keywordToken == CLASS_KEYWORD || keywordToken == TRAIT_KEYWORD || keywordToken == INTERFACE_KEYWORD) {
1045 declType = parseClass(isEnum, CLASS_MEMBER);
1046 }
1047 else if (keywordToken == FUN_KEYWORD) {
1048 declType = parseFunction();
1049 }
1050 else if (keywordToken == VAL_KEYWORD || keywordToken == VAR_KEYWORD) {
1051 declType = parseProperty();
1052 }
1053 else if (keywordToken == TYPE_ALIAS_KEYWORD) {
1054 declType = parseTypeAlias();
1055 }
1056 else if (keywordToken == OBJECT_KEYWORD) {
1057 parseObject(isDefault ? NameParsingMode.ALLOWED : NameParsingMode.REQUIRED, true, CLASS_MEMBER);
1058 declType = OBJECT_DECLARATION;
1059 }
1060 else if (at(INIT_KEYWORD)) {
1061 advance(); // init
1062 if (at(LBRACE)) {
1063 parseBlock();
1064 }
1065 else {
1066 mark().error("Expecting '{' after 'init'");
1067 }
1068 declType = ANONYMOUS_INITIALIZER;
1069 }
1070 else if (at(CONSTRUCTOR_KEYWORD)) {
1071 parseSecondaryConstructor();
1072 declType = SECONDARY_CONSTRUCTOR;
1073 }
1074 else if (at(LBRACE)) {
1075 error("Expecting member declaration");
1076 parseBlock();
1077 declType = FUN;
1078 }
1079 return declType;
1080 }
1081
1082 /*
1083 * secondaryConstructor
1084 * : modifiers "constructor" valueParameters (":" constructorDelegationCall)? block
1085 * constructorDelegationCall
1086 * : "this" valueArguments
1087 * : "super" valueArguments
1088 */
1089 private void parseSecondaryConstructor() {
1090 assert _at(CONSTRUCTOR_KEYWORD);
1091
1092 advance(); // CONSTRUCTOR_KEYWORD
1093
1094 TokenSet valueArgsRecoverySet = TokenSet.create(LBRACE, SEMICOLON, RPAR, EOL_OR_SEMICOLON, RBRACE);
1095 if (at(LPAR)) {
1096 parseValueParameterList(false, /*typeRequired = */ true, valueArgsRecoverySet);
1097 }
1098 else {
1099 errorWithRecovery("Expecting '('", TokenSet.orSet(valueArgsRecoverySet, TokenSet.create(COLON)));
1100 }
1101
1102 if (at(COLON)) {
1103 advance(); // COLON
1104
1105 PsiBuilder.Marker delegationCall = mark();
1106
1107 if (at(THIS_KEYWORD) || at(SUPER_KEYWORD)) {
1108 parseThisOrSuper();
1109 myExpressionParsing.parseValueArgumentList();
1110 }
1111 else {
1112 error("Expecting a 'this' or 'super' constructor call");
1113 PsiBuilder.Marker beforeWrongDelegationCallee = null;
1114 if (!at(LPAR)) {
1115 beforeWrongDelegationCallee = mark();
1116 advance(); // wrong delegation callee
1117 }
1118 myExpressionParsing.parseValueArgumentList();
1119
1120 if (beforeWrongDelegationCallee != null) {
1121 if (at(LBRACE)) {
1122 beforeWrongDelegationCallee.drop();
1123 }
1124 else {
1125 beforeWrongDelegationCallee.rollbackTo();
1126 }
1127 }
1128 }
1129
1130 delegationCall.done(CONSTRUCTOR_DELEGATION_CALL);
1131 }
1132 else {
1133 // empty constructor delegation call
1134 PsiBuilder.Marker emptyDelegationCall = mark();
1135 mark().done(CONSTRUCTOR_DELEGATION_REFERENCE);
1136 emptyDelegationCall.done(CONSTRUCTOR_DELEGATION_CALL);
1137 }
1138
1139 if (at(LBRACE)) {
1140 parseBlock();
1141 }
1142 }
1143
1144 private void parseThisOrSuper() {
1145 assert _at(THIS_KEYWORD) || _at(SUPER_KEYWORD);
1146 PsiBuilder.Marker mark = mark();
1147
1148 advance(); // THIS_KEYWORD | SUPER_KEYWORD
1149
1150 mark.done(CONSTRUCTOR_DELEGATION_REFERENCE);
1151 }
1152
1153 /*
1154 * initializerList
1155 * : initializer
1156 *
1157 */
1158 private void parseInitializerList() {
1159 // In practice, only one initializer is always in use
1160 PsiBuilder.Marker list = mark();
1161 if (at(COMMA)) errorAndAdvance("Expecting a this or super constructor call");
1162 parseInitializer();
1163 list.done(INITIALIZER_LIST);
1164 }
1165
1166 /*
1167 * initializer
1168 * : annotations constructorInvocation // type parameters may (must?) be omitted
1169 * ;
1170 */
1171 private void parseInitializer() {
1172 PsiBuilder.Marker initializer = mark();
1173 parseAnnotations(ONLY_ESCAPED_REGULAR_ANNOTATIONS);
1174
1175 IElementType type;
1176 if (atSet(TYPE_REF_FIRST)) {
1177 PsiBuilder.Marker reference = mark();
1178 parseTypeRef();
1179 reference.done(CONSTRUCTOR_CALLEE);
1180 type = DELEGATOR_SUPER_CALL;
1181 }
1182 else {
1183 errorWithRecovery("Expecting constructor call (<class-name>(...))",
1184 TokenSet.orSet(TOP_LEVEL_DECLARATION_FIRST, TokenSet.create(RBRACE, LBRACE, COMMA, SEMICOLON)));
1185 initializer.drop();
1186 return;
1187 }
1188 myExpressionParsing.parseValueArgumentList();
1189
1190 initializer.done(type);
1191 }
1192
1193 /*
1194 * typeAlias
1195 * : modifiers "typealias" SimpleName (typeParameters typeConstraints)? "=" type
1196 * ;
1197 */
1198 JetNodeType parseTypeAlias() {
1199 assert _at(TYPE_ALIAS_KEYWORD);
1200
1201 advance(); // TYPE_ALIAS_KEYWORD
1202
1203 expect(IDENTIFIER, "Type name expected", TokenSet.orSet(TokenSet.create(LT, EQ, SEMICOLON), TOP_LEVEL_DECLARATION_FIRST));
1204
1205 if (parseTypeParameterList(TYPE_PARAMETER_GT_RECOVERY_SET)) {
1206 parseTypeConstraints();
1207 }
1208
1209 expect(EQ, "Expecting '='", TokenSet.orSet(TOP_LEVEL_DECLARATION_FIRST, TokenSet.create(SEMICOLON)));
1210
1211 parseTypeRef();
1212
1213 consumeIf(SEMICOLON);
1214
1215 return TYPEDEF;
1216 }
1217
1218 /*
1219 * variableDeclarationEntry
1220 * : SimpleName (":" type)?
1221 * ;
1222 *
1223 * property
1224 * : modifiers ("val" | "var")
1225 * typeParameters? (type "." | annotations)?
1226 * ("(" variableDeclarationEntry{","} ")" | variableDeclarationEntry)
1227 * typeConstraints
1228 * ("by" | "=" expression SEMI?)?
1229 * (getter? setter? | setter? getter?) SEMI?
1230 * ;
1231 */
1232 private IElementType parseProperty() {
1233 return parseProperty(false);
1234 }
1235
1236 public IElementType parseProperty(boolean local) {
1237 if (at(VAL_KEYWORD) || at(VAR_KEYWORD)) {
1238 advance(); // VAL_KEYWORD or VAR_KEYWORD
1239 }
1240 else {
1241 errorAndAdvance("Expecting 'val' or 'var'");
1242 }
1243
1244 boolean typeParametersDeclared = at(LT) && parseTypeParameterList(TokenSet.create(IDENTIFIER, EQ, COLON, SEMICOLON));
1245
1246 TokenSet propertyNameFollow = TokenSet.create(COLON, EQ, LBRACE, RBRACE, SEMICOLON, VAL_KEYWORD, VAR_KEYWORD, FUN_KEYWORD, CLASS_KEYWORD);
1247
1248 myBuilder.disableJoiningComplexTokens();
1249
1250 PsiBuilder.Marker receiver = mark();
1251 boolean receiverTypeDeclared = parseReceiverType("property", propertyNameFollow);
1252
1253 boolean multiDeclaration = at(LPAR);
1254
1255 errorIf(receiver, multiDeclaration && receiverTypeDeclared, "Receiver type is not allowed on a multi-declaration");
1256
1257 if (multiDeclaration) {
1258 PsiBuilder.Marker multiDecl = mark();
1259 parseMultiDeclarationName(propertyNameFollow);
1260 errorIf(multiDecl, !local, "Multi-declarations are only allowed for local variables/values");
1261 }
1262 else {
1263 parseFunctionOrPropertyName(receiverTypeDeclared, "property", propertyNameFollow, /*nameRequired = */ false);
1264 }
1265
1266 myBuilder.restoreJoiningComplexTokensState();
1267
1268 if (at(COLON)) {
1269 PsiBuilder.Marker type = mark();
1270 advance(); // COLON
1271 parseTypeRef();
1272 errorIf(type, multiDeclaration, "Type annotations are not allowed on multi-declarations");
1273 }
1274
1275 parseTypeConstraintsGuarded(typeParametersDeclared);
1276
1277 if (local) {
1278 if (at(BY_KEYWORD)) {
1279 parsePropertyDelegate();
1280 }
1281 else if (at(EQ)) {
1282 advance(); // EQ
1283 myExpressionParsing.parseExpression();
1284 // "val a = 1; b" must not be an infix call of b on "val ...;"
1285 }
1286 }
1287 else {
1288 if (at(BY_KEYWORD)) {
1289 parsePropertyDelegate();
1290 consumeIf(SEMICOLON);
1291 }
1292 else if (at(EQ)) {
1293 advance(); // EQ
1294 myExpressionParsing.parseExpression();
1295 consumeIf(SEMICOLON);
1296 }
1297
1298 if (parsePropertyGetterOrSetter()) {
1299 parsePropertyGetterOrSetter();
1300 }
1301 if (!atSet(EOL_OR_SEMICOLON, RBRACE)) {
1302 if (getLastToken() != SEMICOLON) {
1303 errorUntil("Property getter or setter expected", TokenSet.create(EOL_OR_SEMICOLON, LBRACE, RBRACE));
1304 }
1305 }
1306 else {
1307 consumeIf(SEMICOLON);
1308 }
1309 }
1310
1311 return multiDeclaration ? MULTI_VARIABLE_DECLARATION : PROPERTY;
1312 }
1313
1314 /*
1315 * propertyDelegate
1316 * : "by" expression
1317 * ;
1318 */
1319 private void parsePropertyDelegate() {
1320 assert _at(BY_KEYWORD);
1321 PsiBuilder.Marker delegate = mark();
1322 advance(); // BY_KEYWORD
1323 myExpressionParsing.parseExpression();
1324 delegate.done(PROPERTY_DELEGATE);
1325 }
1326
1327 /*
1328 * (SimpleName (":" type)){","}
1329 */
1330 public void parseMultiDeclarationName(TokenSet follow) {
1331 // Parsing multi-name, e.g.
1332 // val (a, b) = foo()
1333 myBuilder.disableNewlines();
1334 advance(); // LPAR
1335
1336 TokenSet recoverySet = TokenSet.orSet(PARAMETER_NAME_RECOVERY_SET, follow);
1337 if (!atSet(follow)) {
1338 while (true) {
1339 if (at(COMMA)) {
1340 errorAndAdvance("Expecting a name");
1341 }
1342 else if (at(RPAR)) {
1343 error("Expecting a name");
1344 break;
1345 }
1346 PsiBuilder.Marker property = mark();
1347
1348 parseModifierListWithUnescapedAnnotations(TokenSet.create(COMMA, RPAR, COLON, IN_KEYWORD, EQ));
1349
1350 expect(IDENTIFIER, "Expecting a name", recoverySet);
1351
1352 if (at(COLON)) {
1353 advance(); // COLON
1354 parseTypeRef(follow);
1355 }
1356 property.done(MULTI_VARIABLE_DECLARATION_ENTRY);
1357
1358 if (!at(COMMA)) break;
1359 advance(); // COMMA
1360 }
1361 }
1362
1363 expect(RPAR, "Expecting ')'", follow);
1364 myBuilder.restoreNewlinesState();
1365 }
1366
1367 /*
1368 * getterOrSetter
1369 * : modifiers ("get" | "set")
1370 * :
1371 * ( "get" "(" ")"
1372 * |
1373 * "set" "(" modifiers parameter ")"
1374 * ) functionBody
1375 * ;
1376 */
1377 private boolean parsePropertyGetterOrSetter() {
1378 PsiBuilder.Marker getterOrSetter = mark();
1379
1380 parseModifierList(ONLY_ESCAPED_REGULAR_ANNOTATIONS);
1381
1382 if (!at(GET_KEYWORD) && !at(SET_KEYWORD)) {
1383 getterOrSetter.rollbackTo();
1384 return false;
1385 }
1386
1387 boolean setter = at(SET_KEYWORD);
1388 advance(); // GET_KEYWORD or SET_KEYWORD
1389
1390 if (!at(LPAR)) {
1391 // Account for Jet-114 (val a : int get {...})
1392 TokenSet ACCESSOR_FIRST_OR_PROPERTY_END = TokenSet.orSet(MODIFIER_KEYWORDS, TokenSet.create(LBRACKET, GET_KEYWORD, SET_KEYWORD, EOL_OR_SEMICOLON, RBRACE));
1393 if (!atSet(ACCESSOR_FIRST_OR_PROPERTY_END)) {
1394 errorUntil("Accessor body expected", TokenSet.orSet(ACCESSOR_FIRST_OR_PROPERTY_END, TokenSet.create(LBRACE, LPAR, EQ)));
1395 }
1396 else {
1397 closeDeclarationWithCommentBinders(getterOrSetter, PROPERTY_ACCESSOR, false);
1398 return true;
1399 }
1400 }
1401
1402 myBuilder.disableNewlines();
1403 expect(LPAR, "Expecting '('", TokenSet.create(RPAR, IDENTIFIER, COLON, LBRACE, EQ));
1404 if (setter) {
1405 PsiBuilder.Marker parameterList = mark();
1406 PsiBuilder.Marker setterParameter = mark();
1407 parseModifierListWithUnescapedAnnotations(TokenSet.create(RPAR, COMMA, COLON));
1408 expect(IDENTIFIER, "Expecting parameter name", TokenSet.create(RPAR, COLON, LBRACE, EQ));
1409
1410 if (at(COLON)) {
1411 advance(); // COLON
1412 parseTypeRef();
1413 }
1414 setterParameter.done(VALUE_PARAMETER);
1415 parameterList.done(VALUE_PARAMETER_LIST);
1416 }
1417 if (!at(RPAR)) {
1418 errorUntil("Expecting ')'", TokenSet.create(RPAR, COLON, LBRACE, RBRACE, EQ, EOL_OR_SEMICOLON));
1419 }
1420 if (at(RPAR)) {
1421 advance();
1422 }
1423 myBuilder.restoreNewlinesState();
1424
1425 if (at(COLON)) {
1426 advance();
1427
1428 parseTypeRef();
1429 }
1430
1431 parseFunctionBody();
1432
1433 closeDeclarationWithCommentBinders(getterOrSetter, PROPERTY_ACCESSOR, false);
1434
1435 return true;
1436 }
1437
1438 /*
1439 * function
1440 * : modifiers "fun" typeParameters?
1441 * (type "." | annotations)?
1442 * SimpleName
1443 * typeParameters? functionParameters (":" type)?
1444 * typeConstraints
1445 * functionBody?
1446 * ;
1447 */
1448 IElementType parseFunction() {
1449 assert _at(FUN_KEYWORD);
1450
1451 advance(); // FUN_KEYWORD
1452
1453 // Recovery for the case of class A { fun| }
1454 if (at(RBRACE)) {
1455 error("Function body expected");
1456 return FUN;
1457 }
1458
1459 boolean typeParameterListOccurred = false;
1460 if (at(LT)) {
1461 parseTypeParameterList(TokenSet.create(LBRACKET, LBRACE, RBRACE, LPAR));
1462 typeParameterListOccurred = true;
1463 }
1464
1465 myBuilder.disableJoiningComplexTokens();
1466
1467 TokenSet functionNameFollow = TokenSet.create(LT, LPAR, RPAR, COLON, EQ);
1468 boolean receiverFound = parseReceiverType("function", functionNameFollow);
1469
1470 // function as expression has no name
1471 parseFunctionOrPropertyName(receiverFound, "function", functionNameFollow, /*nameRequired = */ true);
1472
1473 myBuilder.restoreJoiningComplexTokensState();
1474
1475 TokenSet valueParametersFollow = TokenSet.create(EQ, LBRACE, RBRACE, SEMICOLON, RPAR);
1476
1477 if (at(LT)) {
1478 PsiBuilder.Marker error = mark();
1479 parseTypeParameterList(TokenSet.orSet(TokenSet.create(LPAR), valueParametersFollow));
1480 errorIf(error, typeParameterListOccurred, "Only one type parameter list is allowed for a function");
1481 typeParameterListOccurred = true;
1482 }
1483
1484 if (at(LPAR)) {
1485 parseValueParameterList(false, /* typeRequired = */ false, valueParametersFollow);
1486 }
1487 else {
1488 error("Expecting '('");
1489 }
1490
1491 if (at(COLON)) {
1492 advance(); // COLON
1493
1494 parseTypeRef();
1495 }
1496
1497 parseTypeConstraintsGuarded(typeParameterListOccurred);
1498
1499 if (at(SEMICOLON)) {
1500 advance(); // SEMICOLON
1501 }
1502 else if (at(EQ) || at(LBRACE)) {
1503 parseFunctionBody();
1504 }
1505
1506 return FUN;
1507 }
1508
1509 /*
1510 * (type "." | annotations)?
1511 */
1512 private boolean parseReceiverType(String title, TokenSet nameFollow) {
1513 PsiBuilder.Marker annotations = mark();
1514 boolean annotationsPresent = parseAnnotations(ONLY_ESCAPED_REGULAR_ANNOTATIONS);
1515 int lastDot = lastDotAfterReceiver();
1516 boolean receiverPresent = lastDot != -1;
1517 if (annotationsPresent) {
1518 if (receiverPresent) {
1519 annotations.rollbackTo();
1520 }
1521 else {
1522 annotations.error("Annotations are not allowed in this position");
1523 }
1524 }
1525 else {
1526 annotations.drop();
1527 }
1528
1529 if (!receiverPresent) return false;
1530
1531 createTruncatedBuilder(lastDot).parseTypeRef();
1532
1533 if (atSet(RECEIVER_TYPE_TERMINATORS)) {
1534 advance(); // expectation
1535 }
1536 else {
1537 errorWithRecovery("Expecting '.' before a " + title + " name", nameFollow);
1538 }
1539 return true;
1540 }
1541
1542 private int lastDotAfterReceiver() {
1543 if (at(LPAR)) {
1544 return matchTokenStreamPredicate(
1545 new FirstBefore(
1546 new AtSet(RECEIVER_TYPE_TERMINATORS),
1547 new AbstractTokenStreamPredicate() {
1548 @Override
1549 public boolean matching(boolean topLevel) {
1550 if (topLevel && definitelyOutOfReceiver()) {
1551 return true;
1552 }
1553 return topLevel && !at(QUEST) && !at(LPAR) && !at(RPAR);
1554 }
1555 }
1556 ));
1557 }
1558 else {
1559 return matchTokenStreamPredicate(
1560 new LastBefore(
1561 new AtSet(RECEIVER_TYPE_TERMINATORS),
1562 new AbstractTokenStreamPredicate() {
1563 @Override
1564 public boolean matching(boolean topLevel) {
1565 if (topLevel && (definitelyOutOfReceiver() || at(LPAR))) return true;
1566 if (topLevel && at(IDENTIFIER)) {
1567 IElementType lookahead = lookahead(1);
1568 return lookahead != LT && lookahead != DOT && lookahead != SAFE_ACCESS && lookahead != QUEST;
1569 }
1570 return false;
1571 }
1572 }));
1573 }
1574 }
1575
1576 private boolean definitelyOutOfReceiver() {
1577 return atSet(EQ, COLON, LBRACE, RBRACE, BY_KEYWORD) || atSet(TOP_LEVEL_DECLARATION_FIRST);
1578 }
1579
1580 /*
1581 * IDENTIFIER
1582 */
1583 private void parseFunctionOrPropertyName(boolean receiverFound, String title, TokenSet nameFollow, boolean nameRequired) {
1584 if (nameRequired && atSet(nameFollow)) return; // no name
1585
1586 TokenSet recoverySet = TokenSet.orSet(nameFollow, TokenSet.create(LBRACE, RBRACE));
1587 if (!receiverFound) {
1588 expect(IDENTIFIER, "Expecting " + title + " name or receiver type", recoverySet);
1589 }
1590 else {
1591 expect(IDENTIFIER, "Expecting " + title + " name", recoverySet);
1592 }
1593 }
1594
1595 /*
1596 * functionBody
1597 * : block
1598 * : "=" element
1599 * ;
1600 */
1601 private void parseFunctionBody() {
1602 if (at(LBRACE)) {
1603 parseBlock();
1604 }
1605 else if (at(EQ)) {
1606 advance(); // EQ
1607 myExpressionParsing.parseExpression();
1608 consumeIf(SEMICOLON);
1609 }
1610 else {
1611 error("Expecting function body");
1612 }
1613 }
1614
1615 /*
1616 * block
1617 * : "{" (expressions)* "}"
1618 * ;
1619 */
1620 void parseBlock() {
1621 PsiBuilder.Marker block = mark();
1622
1623 myBuilder.enableNewlines();
1624 expect(LBRACE, "Expecting '{' to open a block");
1625
1626 myExpressionParsing.parseStatements();
1627
1628 expect(RBRACE, "Expecting '}'");
1629 myBuilder.restoreNewlinesState();
1630
1631 block.done(BLOCK);
1632 }
1633
1634 /*
1635 * delegationSpecifier{","}
1636 */
1637 /*package*/ void parseDelegationSpecifierList() {
1638 PsiBuilder.Marker list = mark();
1639
1640 while (true) {
1641 if (at(COMMA)) {
1642 errorAndAdvance("Expecting a delegation specifier");
1643 continue;
1644 }
1645 parseDelegationSpecifier();
1646 if (!at(COMMA)) break;
1647 advance(); // COMMA
1648 }
1649
1650 list.done(DELEGATION_SPECIFIER_LIST);
1651 }
1652
1653 /*
1654 * delegationSpecifier
1655 * : constructorInvocation // type and constructor arguments
1656 * : userType
1657 * : explicitDelegation
1658 * ;
1659 *
1660 * explicitDelegation
1661 * : userType "by" element
1662 * ;
1663 */
1664 private void parseDelegationSpecifier() {
1665 PsiBuilder.Marker delegator = mark();
1666 PsiBuilder.Marker reference = mark();
1667 parseTypeRef();
1668
1669 if (at(BY_KEYWORD)) {
1670 reference.drop();
1671 advance(); // BY_KEYWORD
1672 createForByClause(myBuilder).myExpressionParsing.parseExpression();
1673 delegator.done(DELEGATOR_BY);
1674 }
1675 else if (at(LPAR)) {
1676 reference.done(CONSTRUCTOR_CALLEE);
1677 myExpressionParsing.parseValueArgumentList();
1678 delegator.done(DELEGATOR_SUPER_CALL);
1679 }
1680 else {
1681 reference.drop();
1682 delegator.done(DELEGATOR_SUPER_CLASS);
1683 }
1684 }
1685
1686 /*
1687 * typeParameters
1688 * : ("<" typeParameter{","} ">"
1689 * ;
1690 */
1691 private boolean parseTypeParameterList(TokenSet recoverySet) {
1692 boolean result = false;
1693 if (at(LT)) {
1694 PsiBuilder.Marker list = mark();
1695
1696 myBuilder.disableNewlines();
1697 advance(); // LT
1698
1699 while (true) {
1700 if (at(COMMA)) errorAndAdvance("Expecting type parameter declaration");
1701 parseTypeParameter();
1702
1703 if (!at(COMMA)) break;
1704 advance(); // COMMA
1705 }
1706
1707 expect(GT, "Missing '>'", recoverySet);
1708 myBuilder.restoreNewlinesState();
1709 result = true;
1710
1711 list.done(TYPE_PARAMETER_LIST);
1712 }
1713 return result;
1714 }
1715
1716 /*
1717 * typeConstraints
1718 * : ("where" typeConstraint{","})?
1719 * ;
1720 */
1721 private void parseTypeConstraintsGuarded(boolean typeParameterListOccurred) {
1722 PsiBuilder.Marker error = mark();
1723 boolean constraints = parseTypeConstraints();
1724 errorIf(error, constraints && !typeParameterListOccurred, "Type constraints are not allowed when no type parameters declared");
1725 }
1726
1727 private boolean parseTypeConstraints() {
1728 if (at(WHERE_KEYWORD)) {
1729 parseTypeConstraintList();
1730 return true;
1731 }
1732 return false;
1733 }
1734
1735 /*
1736 * typeConstraint{","}
1737 */
1738 private void parseTypeConstraintList() {
1739 assert _at(WHERE_KEYWORD);
1740
1741 advance(); // WHERE_KEYWORD
1742
1743 PsiBuilder.Marker list = mark();
1744
1745 while (true) {
1746 if (at(COMMA)) errorAndAdvance("Type constraint expected");
1747 parseTypeConstraint();
1748 if (!at(COMMA)) break;
1749 advance(); // COMMA
1750 }
1751
1752 list.done(TYPE_CONSTRAINT_LIST);
1753 }
1754
1755 /*
1756 * typeConstraint
1757 * : annotations SimpleName ":" type
1758 * ;
1759 */
1760 private void parseTypeConstraint() {
1761 PsiBuilder.Marker constraint = mark();
1762
1763 parseAnnotations(ONLY_ESCAPED_REGULAR_ANNOTATIONS);
1764
1765 PsiBuilder.Marker reference = mark();
1766 if (expect(IDENTIFIER, "Expecting type parameter name", TokenSet.orSet(TokenSet.create(COLON, COMMA, LBRACE, RBRACE), TYPE_REF_FIRST))) {
1767 reference.done(REFERENCE_EXPRESSION);
1768 }
1769 else {
1770 reference.drop();
1771 }
1772
1773 expect(COLON, "Expecting ':' before the upper bound", TokenSet.orSet(TokenSet.create(LBRACE, RBRACE), TYPE_REF_FIRST));
1774
1775 parseTypeRef();
1776
1777 constraint.done(TYPE_CONSTRAINT);
1778 }
1779
1780 /*
1781 * typeParameter
1782 * : modifiers SimpleName (":" userType)?
1783 * ;
1784 */
1785 private void parseTypeParameter() {
1786 if (atSet(TYPE_PARAMETER_GT_RECOVERY_SET)) {
1787 error("Type parameter declaration expected");
1788 return;
1789 }
1790
1791 PsiBuilder.Marker mark = mark();
1792
1793 parseModifierListWithUnescapedAnnotations(TokenSet.create(COMMA, GT, COLON));
1794
1795 expect(IDENTIFIER, "Type parameter name expected", TokenSet.EMPTY);
1796
1797 if (at(COLON)) {
1798 advance(); // COLON
1799 parseTypeRef();
1800 }
1801
1802 mark.done(TYPE_PARAMETER);
1803
1804 }
1805
1806 /*
1807 * type
1808 * : annotations typeDescriptor
1809 *
1810 * typeDescriptor
1811 * : selfType
1812 * : functionType
1813 * : userType
1814 * : tupleType
1815 * : nullableType
1816 * : "dynamic"
1817 * ;
1818 *
1819 * nullableType
1820 * : typeDescriptor "?"
1821 */
1822 void parseTypeRef() {
1823 parseTypeRef(TokenSet.EMPTY);
1824 }
1825
1826 void parseTypeRef(TokenSet extraRecoverySet) {
1827 PsiBuilder.Marker typeRefMarker = parseTypeRefContents(extraRecoverySet);
1828 typeRefMarker.done(TYPE_REFERENCE);
1829 }
1830
1831 // The extraRecoverySet is needed for the foo(bar<x, 1, y>(z)) case, to tell whether we should stop
1832 // on expression-indicating symbols or not
1833 private PsiBuilder.Marker parseTypeRefContents(TokenSet extraRecoverySet) {
1834 // Disabling token merge is required for cases like
1835 // Int?.(Foo) -> Bar
1836 // we don't support this case now
1837 // myBuilder.disableJoiningComplexTokens();
1838 PsiBuilder.Marker typeRefMarker = mark();
1839 parseAnnotations(ONLY_ESCAPED_REGULAR_ANNOTATIONS);
1840
1841 IElementType lookahead = lookahead(1);
1842 IElementType lookahead2 = lookahead(2);
1843 if (at(IDENTIFIER) && !(lookahead == DOT && lookahead2 == IDENTIFIER) && lookahead != LT && at(DYNAMIC_KEYWORD)) {
1844 PsiBuilder.Marker dynamicType = mark();
1845 advance(); // DYNAMIC_KEYWORD
1846 dynamicType.done(DYNAMIC_TYPE);
1847 }
1848 else if (at(IDENTIFIER) || at(PACKAGE_KEYWORD) || atParenthesizedMutableForPlatformTypes(0)) {
1849 parseUserType();
1850 }
1851 else if (at(HASH)) {
1852 parseTupleType();
1853 }
1854 else if (at(LPAR)) {
1855 PsiBuilder.Marker functionOrParenthesizedType = mark();
1856
1857 // This may be a function parameter list or just a prenthesized type
1858 advance(); // LPAR
1859 parseTypeRefContents(TokenSet.EMPTY).drop(); // parenthesized types, no reference element around it is needed
1860
1861 if (at(RPAR)) {
1862 advance(); // RPAR
1863 if (at(ARROW)) {
1864 // It's a function type with one parameter specified
1865 // (A) -> B
1866 functionOrParenthesizedType.rollbackTo();
1867 parseFunctionType();
1868 }
1869 else {
1870 // It's a parenthesized type
1871 // (A)
1872 functionOrParenthesizedType.drop();
1873 }
1874 }
1875 else {
1876 // This must be a function type
1877 // (A, B) -> C
1878 // or
1879 // (a : A) -> C
1880 functionOrParenthesizedType.rollbackTo();
1881 parseFunctionType();
1882 }
1883
1884 }
1885 else if (at(CAPITALIZED_THIS_KEYWORD)) {
1886 parseSelfType();
1887 }
1888 else {
1889 errorWithRecovery("Type expected",
1890 TokenSet.orSet(TOP_LEVEL_DECLARATION_FIRST,
1891 TokenSet.create(EQ, COMMA, GT, RBRACKET, DOT, RPAR, RBRACE, LBRACE, SEMICOLON), extraRecoverySet));
1892 }
1893
1894 typeRefMarker = parseNullableTypeSuffix(typeRefMarker);
1895
1896 if (at(DOT)) {
1897 // This is a receiver for a function type
1898 // A.(B) -> C
1899 // ^
1900
1901 PsiBuilder.Marker functionType = typeRefMarker.precede();
1902 PsiBuilder.Marker receiverType = typeRefMarker.precede();
1903 typeRefMarker.done(TYPE_REFERENCE);
1904 receiverType.done(FUNCTION_TYPE_RECEIVER);
1905
1906 advance(); // DOT
1907
1908 if (at(LPAR)) {
1909 parseFunctionTypeContents().drop();
1910 }
1911 else {
1912 error("Expecting function type");
1913 }
1914 typeRefMarker = functionType.precede();
1915
1916 functionType.done(FUNCTION_TYPE);
1917 }
1918 // myBuilder.restoreJoiningComplexTokensState();
1919 return typeRefMarker;
1920 }
1921
1922 @NotNull
1923 PsiBuilder.Marker parseNullableTypeSuffix(@NotNull PsiBuilder.Marker typeRefMarker) {
1924 while (at(QUEST)) {
1925 PsiBuilder.Marker precede = typeRefMarker.precede();
1926 advance(); // QUEST
1927 typeRefMarker.done(NULLABLE_TYPE);
1928 typeRefMarker = precede;
1929 }
1930 return typeRefMarker;
1931 }
1932
1933 /*
1934 * userType
1935 * : ("package" ".")? simpleUserType{"."}
1936 * ;
1937 *
1938 * recovers on platform types:
1939 * - Foo!
1940 * - (Mutable)List<Foo>!
1941 * - Array<(out) Foo>!
1942 */
1943 void parseUserType() {
1944 PsiBuilder.Marker userType = mark();
1945
1946 if (at(PACKAGE_KEYWORD)) {
1947 advance(); // PACKAGE_KEYWORD
1948 expect(DOT, "Expecting '.'", TokenSet.create(IDENTIFIER, LBRACE, RBRACE));
1949 }
1950
1951 PsiBuilder.Marker reference = mark();
1952 while (true) {
1953 recoverOnParenthesizedWordForPlatformTypes(0, "Mutable", true);
1954
1955 if (expect(IDENTIFIER, "Expecting type name",
1956 TokenSet.orSet(JetExpressionParsing.EXPRESSION_FIRST, JetExpressionParsing.EXPRESSION_FOLLOW, DECLARATION_FIRST))) {
1957 reference.done(REFERENCE_EXPRESSION);
1958 }
1959 else {
1960 reference.drop();
1961 break;
1962 }
1963
1964 parseTypeArgumentList();
1965
1966 recoverOnPlatformTypeSuffix();
1967
1968 if (!at(DOT)) {
1969 break;
1970 }
1971 if (lookahead(1) == LPAR && !atParenthesizedMutableForPlatformTypes(1)) {
1972 // This may be a receiver for a function type
1973 // Int.(Int) -> Int
1974 break;
1975 }
1976
1977 PsiBuilder.Marker precede = userType.precede();
1978 userType.done(USER_TYPE);
1979 userType = precede;
1980
1981 advance(); // DOT
1982 reference = mark();
1983 }
1984
1985 userType.done(USER_TYPE);
1986 }
1987
1988 private boolean atParenthesizedMutableForPlatformTypes(int offset) {
1989 return recoverOnParenthesizedWordForPlatformTypes(offset, "Mutable", false);
1990 }
1991
1992 private boolean recoverOnParenthesizedWordForPlatformTypes(int offset, String word, boolean consume) {
1993 // Array<(out) Foo>! or (Mutable)List<Bar>!
1994 if (lookahead(offset) == LPAR && lookahead(offset + 1) == IDENTIFIER && lookahead(offset + 2) == RPAR && lookahead(offset + 3) == IDENTIFIER) {
1995 PsiBuilder.Marker error = mark();
1996
1997 advance(offset);
1998
1999 advance(); // LPAR
2000 if (!word.equals(myBuilder.getTokenText())) {
2001 // something other than "out" / "Mutable"
2002 error.rollbackTo();
2003 return false;
2004 }
2005 else {
2006 advance(); // IDENTIFIER('out')
2007 advance(); // RPAR
2008
2009 if (consume) {
2010 error.error("Unexpected tokens");
2011 }
2012 else {
2013 error.rollbackTo();
2014 }
2015
2016 return true;
2017 }
2018 }
2019 return false;
2020 }
2021
2022 private void recoverOnPlatformTypeSuffix() {
2023 // Recovery for platform types
2024 if (at(EXCL)) {
2025 PsiBuilder.Marker error = mark();
2026 advance(); // EXCL
2027 error.error("Unexpected token");
2028 }
2029 }
2030
2031 /*
2032 * selfType
2033 * : "This"
2034 * ;
2035 */
2036 private void parseSelfType() {
2037 assert _at(CAPITALIZED_THIS_KEYWORD);
2038
2039 PsiBuilder.Marker type = mark();
2040 advance(); // CAPITALIZED_THIS_KEYWORD
2041 type.done(SELF_TYPE);
2042 }
2043
2044 /*
2045 * (optionalProjection type){","}
2046 */
2047 private PsiBuilder.Marker parseTypeArgumentList() {
2048 if (!at(LT)) return null;
2049
2050 PsiBuilder.Marker list = mark();
2051
2052 tryParseTypeArgumentList(TokenSet.EMPTY);
2053
2054 list.done(TYPE_ARGUMENT_LIST);
2055 return list;
2056 }
2057
2058 boolean tryParseTypeArgumentList(TokenSet extraRecoverySet) {
2059 myBuilder.disableNewlines();
2060 advance(); // LT
2061
2062 while (true) {
2063 PsiBuilder.Marker projection = mark();
2064
2065 recoverOnParenthesizedWordForPlatformTypes(0, "out", true);
2066
2067 // TokenSet lookFor = TokenSet.create(IDENTIFIER);
2068 // TokenSet stopAt = TokenSet.create(COMMA, COLON, GT);
2069 // parseModifierListWithUnescapedAnnotations(MODIFIER_LIST, lookFor, stopAt);
2070 // Currently we do not allow annotations
2071 parseModifierList(ONLY_ESCAPED_REGULAR_ANNOTATIONS);
2072
2073 if (at(MUL)) {
2074 advance(); // MUL
2075 }
2076 else {
2077 parseTypeRef(extraRecoverySet);
2078 }
2079 projection.done(TYPE_PROJECTION);
2080 if (!at(COMMA)) break;
2081 advance(); // COMMA
2082 }
2083
2084 boolean atGT = at(GT);
2085 if (!atGT) {
2086 error("Expecting a '>'");
2087 }
2088 else {
2089 advance(); // GT
2090 }
2091 myBuilder.restoreNewlinesState();
2092 return atGT;
2093 }
2094
2095 public void parseModifierListWithUnescapedAnnotations(TokenSet stopAt) {
2096 parseModifierListWithUnescapedAnnotations(TokenSet.create(IDENTIFIER), stopAt);
2097 }
2098
2099 public void parseModifierListWithUnescapedAnnotations(TokenSet lookFor, TokenSet stopAt) {
2100 int lastId = findLastBefore(lookFor, stopAt, false);
2101 createTruncatedBuilder(lastId).parseModifierList(ALLOW_UNESCAPED_REGULAR_ANNOTATIONS);
2102 }
2103
2104 /*
2105 * tupleType
2106 * : "#" "(" type{","}? ")"
2107 * : "#" "(" parameter{","} ")" // tuple with named entries, the names do not affect assignment compatibility
2108 * ;
2109 */
2110 @Deprecated // Tuples are dropped, but parsing is left to minimize surprising. This code should be removed some time (in Kotlin 1.0?)
2111 private void parseTupleType() {
2112 assert _at(HASH);
2113
2114 PsiBuilder.Marker tuple = mark();
2115
2116 myBuilder.disableNewlines();
2117 advance(); // HASH
2118 consumeIf(LPAR);
2119
2120 if (!at(RPAR)) {
2121 while (true) {
2122 if (at(COLON)) {
2123 errorAndAdvance("Expecting a name for tuple entry");
2124 }
2125
2126 if (at(IDENTIFIER) && lookahead(1) == COLON) {
2127 advance(); // IDENTIFIER
2128 advance(); // COLON
2129 parseTypeRef();
2130 }
2131 else if (TYPE_REF_FIRST.contains(tt())) {
2132 parseTypeRef();
2133 }
2134 else {
2135 error("Type expected");
2136 break;
2137 }
2138 if (!at(COMMA)) break;
2139 advance(); // COMMA
2140 }
2141 }
2142
2143 consumeIf(RPAR);
2144 myBuilder.restoreNewlinesState();
2145
2146 tuple.error("Tuples are not supported. Use data classes instead.");
2147 }
2148
2149 /*
2150 * functionType
2151 * : "(" (parameter | modifiers type){","}? ")" "->" type?
2152 * ;
2153 */
2154 private void parseFunctionType() {
2155 parseFunctionTypeContents().done(FUNCTION_TYPE);
2156 }
2157
2158 private PsiBuilder.Marker parseFunctionTypeContents() {
2159 assert _at(LPAR) : tt();
2160 PsiBuilder.Marker functionType = mark();
2161
2162 parseValueParameterList(true, /* typeRequired = */ true, TokenSet.EMPTY);
2163
2164 expect(ARROW, "Expecting '->' to specify return type of a function type", TYPE_REF_FIRST);
2165 parseTypeRef();
2166
2167 return functionType;
2168 }
2169
2170 /*
2171 * functionParameters
2172 * : "(" functionParameter{","}? ")" // default values
2173 * ;
2174 *
2175 * functionParameter
2176 * : modifiers functionParameterRest
2177 * ;
2178 *
2179 * functionParameterRest
2180 * : parameter ("=" element)?
2181 * ;
2182 */
2183 void parseValueParameterList(boolean isFunctionTypeContents, boolean typeRequired, TokenSet recoverySet) {
2184 assert _at(LPAR);
2185 PsiBuilder.Marker parameters = mark();
2186
2187 myBuilder.disableNewlines();
2188 advance(); // LPAR
2189
2190 if (!at(RPAR) && !atSet(recoverySet)) {
2191 while (true) {
2192 if (at(COMMA)) {
2193 errorAndAdvance("Expecting a parameter declaration");
2194 }
2195 else if (at(RPAR)) {
2196 error("Expecting a parameter declaration");
2197 break;
2198 }
2199
2200 if (isFunctionTypeContents) {
2201 if (!tryParseValueParameter(typeRequired)) {
2202 PsiBuilder.Marker valueParameter = mark();
2203 parseModifierList(ONLY_ESCAPED_REGULAR_ANNOTATIONS); // lazy, out, ref
2204 parseTypeRef();
2205 closeDeclarationWithCommentBinders(valueParameter, VALUE_PARAMETER, false);
2206 }
2207 }
2208 else {
2209 parseValueParameter(typeRequired);
2210 }
2211
2212 if (at(COMMA)) {
2213 advance(); // COMMA
2214 }
2215 else {
2216 if (!at(RPAR)) error("Expecting comma or ')'");
2217 if (!atSet(isFunctionTypeContents ? LAMBDA_VALUE_PARAMETER_FIRST : VALUE_PARAMETER_FIRST)) break;
2218 }
2219 }
2220 }
2221
2222 expect(RPAR, "Expecting ')'", recoverySet);
2223 myBuilder.restoreNewlinesState();
2224
2225 parameters.done(VALUE_PARAMETER_LIST);
2226 }
2227
2228 /*
2229 * functionParameter
2230 * : modifiers ("val" | "var")? parameter ("=" element)?
2231 * ;
2232 */
2233 private boolean tryParseValueParameter(boolean typeRequired) {
2234 return parseValueParameter(true, typeRequired);
2235 }
2236
2237 public void parseValueParameter(boolean typeRequired) {
2238 parseValueParameter(false, typeRequired);
2239 }
2240
2241 private boolean parseValueParameter(boolean rollbackOnFailure, boolean typeRequired) {
2242 PsiBuilder.Marker parameter = mark();
2243
2244 parseModifierListWithUnescapedAnnotations(TokenSet.create(COMMA, RPAR, COLON));
2245
2246 if (at(VAR_KEYWORD) || at(VAL_KEYWORD)) {
2247 advance(); // VAR_KEYWORD | VAL_KEYWORD
2248 }
2249
2250 if (!parseFunctionParameterRest(typeRequired) && rollbackOnFailure) {
2251 parameter.rollbackTo();
2252 return false;
2253 }
2254
2255 closeDeclarationWithCommentBinders(parameter, VALUE_PARAMETER, false);
2256 return true;
2257 }
2258
2259 /*
2260 * functionParameterRest
2261 * : parameter ("=" element)?
2262 * ;
2263 */
2264 private boolean parseFunctionParameterRest(boolean typeRequired) {
2265 boolean noErrors = true;
2266
2267 // Recovery for the case 'fun foo(Array<String>) {}'
2268 // Recovery for the case 'fun foo(: Int) {}'
2269 if ((at(IDENTIFIER) && lookahead(1) == LT) || at(COLON)) {
2270 error("Parameter name expected");
2271 if (at(COLON)) {
2272 // We keep noErrors == true so that unnamed parameters starting with ":" are not rolled back during parsing of functional types
2273 advance(); // COLON
2274 }
2275 else {
2276 noErrors = false;
2277 }
2278 parseTypeRef();
2279 }
2280 else {
2281 expect(IDENTIFIER, "Parameter name expected", PARAMETER_NAME_RECOVERY_SET);
2282
2283 if (at(COLON)) {
2284 advance(); // COLON
2285 parseTypeRef();
2286 }
2287 else if (typeRequired) {
2288 errorWithRecovery("Parameters must have type annotation", PARAMETER_NAME_RECOVERY_SET);
2289 noErrors = false;
2290 }
2291 }
2292
2293 if (at(EQ)) {
2294 advance(); // EQ
2295 myExpressionParsing.parseExpression();
2296 }
2297
2298 return noErrors;
2299 }
2300
2301 @Override
2302 protected JetParsing create(SemanticWhitespaceAwarePsiBuilder builder) {
2303 return createForTopLevel(builder);
2304 }
2305
2306 /*package*/ static class ModifierDetector implements Consumer<IElementType> {
2307 private boolean enumDetected = false;
2308 private boolean defaultDetected = false;
2309
2310 @Override
2311 public void consume(IElementType item) {
2312 if (item == JetTokens.ENUM_KEYWORD) {
2313 enumDetected = true;
2314 }
2315 else if (item == JetTokens.COMPANION_KEYWORD) {
2316 defaultDetected = true;
2317 }
2318 }
2319
2320 public boolean isEnumDetected() {
2321 return enumDetected;
2322 }
2323
2324 public boolean isDefaultDetected() {
2325 return defaultDetected;
2326 }
2327 }
2328
2329 enum AnnotationParsingMode {
2330 FILE_ANNOTATIONS_BEFORE_PACKAGE(false, true, false),
2331 FILE_ANNOTATIONS_WHEN_PACKAGE_OMITTED(false, true, false),
2332 ONLY_ESCAPED_REGULAR_ANNOTATIONS(false, false, false),
2333 ALLOW_UNESCAPED_REGULAR_ANNOTATIONS(true, false, false),
2334 ALLOW_UNESCAPED_REGULAR_ANNOTATIONS_AT_MEMBER_MODIFIER_LIST(true, false, true),
2335 PRIMARY_CONSTRUCTOR_MODIFIER_LIST(true, false, false),
2336 PRIMARY_CONSTRUCTOR_MODIFIER_LIST_LOCAL(false, false, false);
2337
2338 boolean allowShortAnnotations;
2339 boolean isFileAnnotationParsingMode;
2340 boolean atMemberStart;
2341
2342 AnnotationParsingMode(
2343 boolean allowShortAnnotations,
2344 boolean isFileAnnotationParsingMode,
2345 boolean atMemberStart
2346 ) {
2347 this.allowShortAnnotations = allowShortAnnotations;
2348 this.isFileAnnotationParsingMode = isFileAnnotationParsingMode;
2349 this.atMemberStart = atMemberStart;
2350 }
2351 }
2352 }