diff --git a/lang/parser.y b/lang/parser.y index ca13ca0c..5a3e32a7 100644 --- a/lang/parser.y +++ b/lang/parser.y @@ -859,6 +859,7 @@ arg: } ; bind: + // `$s = "hey"` VAR_IDENTIFIER EQUALS expr { posLast(yylex, yyDollar) // our pos @@ -867,6 +868,8 @@ bind: Value: $3.expr, } } + // `$x bool = true` + // `$x int = if true { 42 } else { 13 }` | VAR_IDENTIFIER type EQUALS expr { posLast(yylex, yyDollar) // our pos diff --git a/lang/structs.go b/lang/structs.go index 3ba22657..3fccc088 100644 --- a/lang/structs.go +++ b/lang/structs.go @@ -5255,6 +5255,15 @@ func (obj *ExprVar) Unify() ([]interfaces.Invariant, error) { return nil, fmt.Errorf("var `%s` does not exist in this scope", obj.Name) } + // if this was set explicitly by the parser + if obj.typ != nil { + invar := &unification.EqualsInvariant{ + Expr: obj, + Type: obj.typ, + } + invariants = append(invariants, invar) + } + // don't recurse because we already got this through the bind statement //invars, err := expr.Unify() //if err != nil { @@ -5531,6 +5540,15 @@ func (obj *ExprIf) Type() (*types.Type, error) { func (obj *ExprIf) Unify() ([]interfaces.Invariant, error) { var invariants []interfaces.Invariant + // if this was set explicitly by the parser + if obj.typ != nil { + invar := &unification.EqualsInvariant{ + Expr: obj, + Type: obj.typ, + } + invariants = append(invariants, invar) + } + // conditional expression might have some children invariants to share condition, err := obj.Condition.Unify() if err != nil {