Recovery fixed for properties and decomposers
This commit is contained in:
@@ -107,7 +107,8 @@ import static org.jetbrains.jet.lexer.JetTokens.*;
|
||||
}
|
||||
|
||||
protected void skipUntil(TokenSet tokenSet) {
|
||||
while (!eof() && !tokenSet.contains(tt())) {
|
||||
boolean stopAtEolOrSemi = tokenSet.contains(EOL_OR_SEMICOLON);
|
||||
while (!eof() && !tokenSet.contains(tt()) && !(stopAtEolOrSemi && at(EOL_OR_SEMICOLON))) {
|
||||
advance();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -484,18 +484,19 @@ public class JetParsing extends AbstractJetParsing {
|
||||
parseAttributeList();
|
||||
|
||||
TokenSet propertyNameFollow = TokenSet.create(COLON, EQ, LBRACE, EOL_OR_SEMICOLON);
|
||||
if (at(IDENTIFIER) && propertyNameFollow.contains(lookahead(1))) {
|
||||
if (at(IDENTIFIER) && propertyNameFollow.contains(lookahead(1))) { // There's no explicit receiver specified
|
||||
// val [a] name = foo
|
||||
receiverTypeAttributes.done(RECEIVER_TYPE_ATTRIBUTES);
|
||||
advance(); // IDENTIFIER
|
||||
}
|
||||
else {
|
||||
receiverTypeAttributes.rollbackTo();
|
||||
else { // There must be an explicit receiver
|
||||
receiverTypeAttributes.rollbackTo(); // Attributes are a part of the receiver type
|
||||
if (!TYPE_REF_FIRST.contains(tt())) {
|
||||
errorAndAdvance("Expecting receiver type or property name");
|
||||
errorUntil("Expecting receiver type or property name", propertyNameFollow);
|
||||
}
|
||||
else {
|
||||
// TODO: if this type is annotated with an attribute, and it is a single identifier, it is a error (fun [a] foo())
|
||||
// TODO: if this type is annotated with an attribute, and it is a single identifier,
|
||||
// TODO: it is NOT an error (fun [a] foo()) -- annotation on receiver
|
||||
parseTypeRef();
|
||||
// The property name may appear as the last section of the type
|
||||
if (at(DOT)) {
|
||||
@@ -520,7 +521,12 @@ public class JetParsing extends AbstractJetParsing {
|
||||
|
||||
// TODO: review
|
||||
// TODO: $field = foo or something like this
|
||||
parsePropertyGetterOrSetter();
|
||||
if (at(RBRACE)) {
|
||||
error("Expecting a getter and/or setter");
|
||||
}
|
||||
else {
|
||||
parsePropertyGetterOrSetter();
|
||||
}
|
||||
if (!at(RBRACE)) parsePropertyGetterOrSetter();
|
||||
|
||||
if (!at(RBRACE)) {
|
||||
@@ -591,7 +597,7 @@ public class JetParsing extends AbstractJetParsing {
|
||||
myExpressionParsing.parseExpression();
|
||||
}
|
||||
else {
|
||||
error("Expecting function body");
|
||||
errorAndAdvance("Expecting function body");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -812,6 +818,7 @@ public class JetParsing extends AbstractJetParsing {
|
||||
|
||||
parseAttributeList();
|
||||
|
||||
TokenSet simpleTypeFirst = TokenSet.create(IDENTIFIER, LBRACE, LPAR);
|
||||
while (true) {
|
||||
if (at(IDENTIFIER)) {
|
||||
parseSimpleUserType();
|
||||
@@ -826,7 +833,12 @@ public class JetParsing extends AbstractJetParsing {
|
||||
}
|
||||
|
||||
if (!at(DOT)) break;
|
||||
advance(); // DOT
|
||||
if (simpleTypeFirst.contains(lookahead(1))) {
|
||||
advance(); // DOT
|
||||
} else {
|
||||
break;
|
||||
// TODO: ERROR here?
|
||||
}
|
||||
}
|
||||
type.done(TYPE_REFERENCE);
|
||||
}
|
||||
|
||||
@@ -8,3 +8,6 @@ decomposer foobar([a])
|
||||
decomposer (a, a).
|
||||
decomposer ().
|
||||
decomposer foo<T>.{() : ()}.bar(a, a).
|
||||
|
||||
|
||||
decomposer foo.bar.-()
|
||||
@@ -174,4 +174,20 @@ JetFile: Decomposers_ERR.jet
|
||||
PsiElement(IDENTIFIER)('a')
|
||||
PsiElement(RPAR)(')')
|
||||
PsiErrorElement:Expecting namespace or top level declaration
|
||||
PsiElement(DOT)('.')
|
||||
PsiElement(DOT)('.')
|
||||
PsiWhiteSpace('\n\n\n')
|
||||
DECOMPOSER
|
||||
PsiElement(decomposer)('decomposer')
|
||||
PsiWhiteSpace(' ')
|
||||
TYPE_REFERENCE
|
||||
USER_TYPE
|
||||
PsiElement(IDENTIFIER)('foo')
|
||||
PsiElement(DOT)('.')
|
||||
USER_TYPE
|
||||
PsiElement(IDENTIFIER)('bar')
|
||||
PsiElement(DOT)('.')
|
||||
PsiErrorElement:Expecting decomposer name
|
||||
PsiElement(MINUS)('-')
|
||||
DECOMPOSER_PROPERTY_LIST
|
||||
PsiElement(LPAR)('(')
|
||||
PsiElement(RPAR)(')')
|
||||
@@ -1,3 +1,6 @@
|
||||
var - f = s
|
||||
var - f {}
|
||||
var - f :
|
||||
val foo :
|
||||
val [a foo = foo
|
||||
val foo.bar.
|
||||
@@ -15,3 +18,8 @@ val foo.bar.{() : ()}.foo = foo {
|
||||
set() {}
|
||||
set() {}
|
||||
}
|
||||
val f.d.- = f
|
||||
|
||||
val foo {
|
||||
get() -
|
||||
}
|
||||
@@ -1,5 +1,43 @@
|
||||
JetFile: Properties_ERR.jet
|
||||
NAMESPACE
|
||||
PROPERTY
|
||||
PsiElement(var)('var')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiErrorElement:Expecting receiver type or property name
|
||||
PsiElement(MINUS)('-')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(IDENTIFIER)('f')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(EQ)('=')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(IDENTIFIER)('s')
|
||||
PsiWhiteSpace('\n')
|
||||
PROPERTY
|
||||
PsiElement(var)('var')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiErrorElement:Expecting receiver type or property name
|
||||
PsiElement(MINUS)('-')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(IDENTIFIER)('f')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(LBRACE)('{')
|
||||
PsiErrorElement:Expecting a getter and/or setter
|
||||
<empty list>
|
||||
PsiElement(RBRACE)('}')
|
||||
PsiWhiteSpace('\n')
|
||||
PROPERTY
|
||||
PsiElement(var)('var')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiErrorElement:Expecting receiver type or property name
|
||||
PsiElement(MINUS)('-')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(IDENTIFIER)('f')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(COLON)(':')
|
||||
PsiWhiteSpace('\n')
|
||||
TYPE_REFERENCE
|
||||
PsiErrorElement:Type expected
|
||||
<empty list>
|
||||
PROPERTY
|
||||
PsiElement(val)('val')
|
||||
PsiWhiteSpace(' ')
|
||||
@@ -40,9 +78,9 @@ JetFile: Properties_ERR.jet
|
||||
PsiElement(DOT)('.')
|
||||
USER_TYPE
|
||||
PsiElement(IDENTIFIER)('bar')
|
||||
PsiElement(DOT)('.')
|
||||
PsiErrorElement:Type expected
|
||||
<empty list>
|
||||
PsiElement(DOT)('.')
|
||||
PsiErrorElement:Expecting property name
|
||||
<empty list>
|
||||
PsiWhiteSpace('\n')
|
||||
PROPERTY
|
||||
PsiElement(val)('val')
|
||||
@@ -222,4 +260,41 @@ JetFile: Properties_ERR.jet
|
||||
PsiElement(RBRACE)('}')
|
||||
PsiWhiteSpace('\n')
|
||||
PsiErrorElement:Expecting namespace or top level declaration
|
||||
PsiElement(RBRACE)('}')
|
||||
PsiWhiteSpace('\n')
|
||||
PROPERTY
|
||||
PsiElement(val)('val')
|
||||
PsiWhiteSpace(' ')
|
||||
TYPE_REFERENCE
|
||||
USER_TYPE
|
||||
PsiElement(IDENTIFIER)('f')
|
||||
PsiElement(DOT)('.')
|
||||
USER_TYPE
|
||||
PsiElement(IDENTIFIER)('d')
|
||||
PsiElement(DOT)('.')
|
||||
PsiErrorElement:Expecting property name
|
||||
PsiElement(MINUS)('-')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(EQ)('=')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(IDENTIFIER)('f')
|
||||
PsiWhiteSpace('\n\n')
|
||||
PROPERTY
|
||||
PsiElement(val)('val')
|
||||
PsiWhiteSpace(' ')
|
||||
RECEIVER_TYPE_ATTRIBUTES
|
||||
<empty list>
|
||||
PsiElement(IDENTIFIER)('foo')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(LBRACE)('{')
|
||||
PsiWhiteSpace('\n ')
|
||||
PROPERTY_GETTER
|
||||
PsiElement(get)('get')
|
||||
VALUE_PARAMETER_LIST
|
||||
PsiElement(LPAR)('(')
|
||||
PsiElement(RPAR)(')')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiErrorElement:Expecting function body
|
||||
PsiElement(MINUS)('-')
|
||||
PsiWhiteSpace('\n')
|
||||
PsiElement(RBRACE)('}')
|
||||
Reference in New Issue
Block a user