about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMel <einebeere@gmail.com>2022-08-16 19:49:59 +0000
committerMel <einebeere@gmail.com>2022-08-16 20:12:20 +0000
commit64d438c91ace51bfda7bff50d381b62f5785f72a (patch)
treeea1b6a23a6ad05c040603dd4d00887332391e197
parent8193e5c590177b91b51acd818e8a365ab6845988 (diff)
downloadjinx-64d438c91ace51bfda7bff50d381b62f5785f72a.tar.zst
jinx-64d438c91ace51bfda7bff50d381b62f5785f72a.zip
Ensure correct argument stack order in all cases
-rw-r--r--pkg/lang/compiler/compiler.go8
-rw-r--r--pkg/lang/compiler/compiler_test.go7
-rw-r--r--pkg/lang/modules/core/natives.go8
-rw-r--r--pkg/lang/vm/exec.go5
-rw-r--r--pkg/lang/vm/vm_test.go4
5 files changed, 14 insertions, 18 deletions
diff --git a/pkg/lang/compiler/compiler.go b/pkg/lang/compiler/compiler.go
index d647aff..631dfec 100644
--- a/pkg/lang/compiler/compiler.go
+++ b/pkg/lang/compiler/compiler.go
@@ -795,8 +795,8 @@ func (comp *Compiler) compileCallExpr(t *code.Builder, expr ast.ExprCall) error
 		return err
 	}
 
-	for i := 0; i < len(expr.Args); i++ {
-		if err := comp.compileExpr(t, expr.Args[i]); err != nil {
+	for _, arg := range expr.Args {
+		if err := comp.compileExpr(t, arg); err != nil {
 			return err
 		}
 	}
@@ -965,9 +965,7 @@ func (comp *Compiler) compileBlockNode(t *code.Builder, block ast.BlockNode) err
 }
 
 func (comp *Compiler) compileFn(t *code.Builder, block ast.BlockNode, args []ast.IdentNode, addMissingReturn bool) error {
-	// Arguments are declared in reverse
-	for i := len(args) - 1; i >= 0; i-- {
-		arg := args[i]
+	for _, arg := range args {
 		if _, ok := comp.scopes.Declare(arg.Value); !ok {
 			return fmt.Errorf("variable %s already declared", arg.Value)
 		}
diff --git a/pkg/lang/compiler/compiler_test.go b/pkg/lang/compiler/compiler_test.go
index 725620c..9e05230 100644
--- a/pkg/lang/compiler/compiler_test.go
+++ b/pkg/lang/compiler/compiler_test.go
@@ -457,7 +457,6 @@ func TestSimpleFunction(t *testing.T) {
 }
 
 func TestFunctionArgs(t *testing.T) {
-	// TODO: Are arguments in the correct order?
 	src := `
 	fn add(a, b) {
 		return a + b
@@ -478,8 +477,8 @@ func TestFunctionArgs(t *testing.T) {
 	halt
 
 	@add:
-	get_local 1
 	get_local 0
+	get_local 1
 	add
 	ret
 	`
@@ -581,11 +580,11 @@ func TestType(t *testing.T) {
 		anchor_type
 
 		get_local 2
-		get_local 1
+		get_local 0
 		set_member "name"
 
 		get_local 2
-		get_local 0
+		get_local 1
 		set_member "age"
 
 		get_local 2
diff --git a/pkg/lang/modules/core/natives.go b/pkg/lang/modules/core/natives.go
index 3035b80..c06b35c 100644
--- a/pkg/lang/modules/core/natives.go
+++ b/pkg/lang/modules/core/natives.go
@@ -44,16 +44,16 @@ var Natives = []any{
 			return value.Value{}, err
 		}
 
-		fn, err := ensureType[value.FunctionData](args[0], value.FunctionType)
+		nameData, err := ensureType[value.StringData](args[0], value.StringType)
 		if err != nil {
 			return value.Value{}, err
 		}
-
-		nameData, err := ensureType[value.StringData](args[1], value.StringType)
+		name, err := nameData.RawString(exe.Mem())
 		if err != nil {
 			return value.Value{}, err
 		}
-		name, err := nameData.RawString(exe.Mem())
+
+		fn, err := ensureType[value.FunctionData](args[1], value.FunctionType)
 		if err != nil {
 			return value.Value{}, err
 		}
diff --git a/pkg/lang/vm/exec.go b/pkg/lang/vm/exec.go
index ade6cc0..34cf444 100644
--- a/pkg/lang/vm/exec.go
+++ b/pkg/lang/vm/exec.go
@@ -836,9 +836,8 @@ func (vm *VM) execCall(argCount uint) error {
 	var err error
 
 	args := make([]value.Value, argCount)
-	for i := 0; i < int(argCount); i++ {
-		args[i], err = vm.stack.Pop()
-		if err != nil {
+	for i := int(argCount - 1); i >= 0; i-- {
+		if args[i], err = vm.stack.Pop(); err != nil {
 			return err
 		}
 	}
diff --git a/pkg/lang/vm/vm_test.go b/pkg/lang/vm/vm_test.go
index 17edb2e..178d756 100644
--- a/pkg/lang/vm/vm_test.go
+++ b/pkg/lang/vm/vm_test.go
@@ -326,11 +326,11 @@ func TestTypeConstruct(t *testing.T) {
 		anchor_type
 
 		get_local 2
-		get_local 1
+		get_local 0
 		set_member "name"
 
 		get_local 2
-		get_local 0
+		get_local 1
 		set_member "age"
 
 		ret