diff --git a/src/core/CompileCall.go b/src/core/CompileCall.go index e9c94b2..3d4ad40 100644 --- a/src/core/CompileCall.go +++ b/src/core/CompileCall.go @@ -52,17 +52,6 @@ func (f *Function) CompileCall(root *expression.Expression) ([]types.Type, error fn, exists = f.All.Functions[pkg+"."+name] if !exists { - typ := types.ByName(name, f.Package, f.All.Structs) - - if typ != nil { - if len(root.Children) != 2 { - return nil, errors.New(&errors.ParameterCountMismatch{Function: name, Count: len(root.Children), ExpectedCount: 1}, f.File, nameNode.Token.End()) - } - - _, err := f.ExpressionToRegister(root.Children[1], f.CPU.Output[0]) - return []types.Type{typ}, err - } - return nil, errors.New(&errors.UnknownFunction{Name: name}, f.File, nameNode.Token.Position) } diff --git a/src/core/EvaluateCall.go b/src/core/EvaluateCall.go index 6defe4f..ad092a0 100644 --- a/src/core/EvaluateCall.go +++ b/src/core/EvaluateCall.go @@ -1,12 +1,56 @@ package core import ( + "git.urbach.dev/cli/q/src/errors" "git.urbach.dev/cli/q/src/eval" "git.urbach.dev/cli/q/src/expression" + "git.urbach.dev/cli/q/src/token" + "git.urbach.dev/cli/q/src/types" ) // EvaluateCall evaluates a function call. -func (f *Function) EvaluateCall(expr *expression.Expression) (*eval.Register, error) { +func (f *Function) EvaluateCall(expr *expression.Expression) (eval.Value, error) { + if expr.Children[0].Token.Kind == token.Identifier { + nameNode := expr.Children[0] + name := nameNode.String(f.File.Bytes) + typ := types.ByName(name, f.Package, f.All.Structs) + + if typ != nil { + if len(expr.Children) != 2 { + return nil, errors.New(&errors.ParameterCountMismatch{Function: name, Count: len(expr.Children), ExpectedCount: 1}, f.File, nameNode.Token.End()) + } + + value, err := f.Evaluate(expr.Children[1]) + + if err != nil { + return nil, err + } + + switch value := value.(type) { + case *eval.Register: + if value.IsAlive() { + value = &eval.Register{ + Typ: typ, + Register: value.Register, + Alive: value.Alive, + } + + return value, nil + } + + value.Typ = typ + case *eval.Number: + value.Typ = typ + case *eval.Memory: + value.Typ = typ + case *eval.Label: + value.Typ = typ + } + + return value, nil + } + } + typ, err := f.CompileCall(expr) if err != nil { diff --git a/src/core/ExpressionToRegister.go b/src/core/ExpressionToRegister.go index bd40f05..1efbfa8 100644 --- a/src/core/ExpressionToRegister.go +++ b/src/core/ExpressionToRegister.go @@ -28,8 +28,8 @@ func (f *Function) ExpressionToRegister(node *expression.Expression, register cp } switch node.Token.Kind { - case token.Array: - value, err := f.EvaluateArray(node) + case token.Call: + value, err := f.EvaluateCall(node) if err != nil { return nil, err @@ -48,8 +48,8 @@ func (f *Function) ExpressionToRegister(node *expression.Expression, register cp f.ValueToRegister(value, register) return value.Type(), nil - case token.Call: - value, err := f.EvaluateCall(node) + case token.Array: + value, err := f.EvaluateArray(node) if err != nil { return nil, err