diff --git a/typechecker/Ceylon.g b/typechecker/Ceylon.g index 32fce70b056..89e23846c51 100644 --- a/typechecker/Ceylon.g +++ b/typechecker/Ceylon.g @@ -1955,6 +1955,37 @@ functionOrExpression returns [Expression expression] $expression.setTerm($f.function); } | e=expression { $expression = $e.expression; } + | l=let + { $expression = new Expression(null); + $expression.setTerm($l.let); } + ; + +let returns [LetExpression let] + @init { LetClause lc=null; } + : LET + { $let = new LetExpression(null); + lc = new LetClause($LET); + $let.setLetClause(lc); } + LPAREN + { lc.setEndToken($LPAREN); } + ( + v1=specifiedVariable + { lc.setEndToken(null); + lc.addVariable($v1.variable); } + ( + COMMA + { lc.setEndToken($COMMA); } + v2=specifiedVariable + { lc.setEndToken(null); + lc.addVariable($v2.variable); } + )* + )? + RPAREN + { lc.setEndToken($RPAREN); } + disjunctionExpression + { Expression e = new Expression(null); + e.setTerm($disjunctionExpression.term); + lc.setExpression(e); } ; anonymousFunction returns [FunctionArgument function] @@ -3282,15 +3313,15 @@ resources returns [ResourceList resources] : LPAREN { $resources = new ResourceList($LPAREN); } ( - r1=resource - { $resources.addResource($r1.resource); } - ( - c=COMMA - { $resources.setEndToken($c); } - r2=resource - { $resources.addResource($r2.resource); - $resources.setEndToken(null); } - )* + r1=resource + { $resources.addResource($r1.resource); } + ( + c=COMMA + { $resources.setEndToken($c); } + r2=resource + { $resources.addResource($r2.resource); + $resources.setEndToken(null); } + )* )? RPAREN { $resources.setEndToken($RPAREN); } diff --git a/typechecker/Ceylon.nodes b/typechecker/Ceylon.nodes index 3ba66883f23..82c6df9f08d 100644 --- a/typechecker/Ceylon.nodes +++ b/typechecker/Ceylon.nodes @@ -409,6 +409,12 @@ ^(DYNAMIC_CLAUSE:CONTROL_CLAUSE BLOCK?) +^(LET_EXPRESSION:TERM + LET_CLAUSE) +^(LET_CLAUSE:CONTROL_CLAUSE + VARIABLE* + EXPRESSION) + ^(IF_STATEMENT:CONTROL_STATEMENT IF_CLAUSE ELSE_CLAUSE?) diff --git a/typechecker/src/com/redhat/ceylon/compiler/typechecker/analyzer/ExpressionVisitor.java b/typechecker/src/com/redhat/ceylon/compiler/typechecker/analyzer/ExpressionVisitor.java index 4fe23d6c171..52568380331 100644 --- a/typechecker/src/com/redhat/ceylon/compiler/typechecker/analyzer/ExpressionVisitor.java +++ b/typechecker/src/com/redhat/ceylon/compiler/typechecker/analyzer/ExpressionVisitor.java @@ -76,6 +76,7 @@ import com.redhat.ceylon.compiler.typechecker.model.Value; import com.redhat.ceylon.compiler.typechecker.tree.Node; import com.redhat.ceylon.compiler.typechecker.tree.Tree; +import com.redhat.ceylon.compiler.typechecker.tree.Tree.Expression; import com.redhat.ceylon.compiler.typechecker.tree.Tree.ImportPath; import com.redhat.ceylon.compiler.typechecker.tree.Tree.PositionalArgument; import com.redhat.ceylon.compiler.typechecker.tree.Tree.TypeVariance; @@ -4330,6 +4331,14 @@ else if (that instanceof Tree.RemainderAssignOp) { visitInOperator(that); } + @Override public void visit(Tree.LetExpression that) { + super.visit(that); + Tree.Expression e = that.getLetClause().getExpression(); + if (e!=null) { + that.setTypeModel(e.getTypeModel()); + } + } + @Override public void visit(Tree.BaseType that) { super.visit(that);