builtins
This commit is contained in:
49
vm/vm.go
49
vm/vm.go
@@ -206,7 +206,7 @@ func (vm *VM) Run() error {
|
||||
numArgs := code.ReadUint8(ins[ip+1:])
|
||||
vm.currentFrame().ip += 1
|
||||
|
||||
err := vm.callFunction(int(numArgs))
|
||||
err := vm.executeCall(int(numArgs))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
@@ -249,6 +249,17 @@ func (vm *VM) Run() error {
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
case code.OpGetBuiltin:
|
||||
builtinIndex := code.ReadUint8(ins[ip+1:])
|
||||
vm.currentFrame().ip += 1
|
||||
|
||||
definition := object.Builtins[builtinIndex]
|
||||
|
||||
err := vm.push(definition.Builtin)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -465,12 +476,19 @@ func (vm *VM) executeMinusOperator() error {
|
||||
return vm.push(&object.Integer{Value: -value})
|
||||
}
|
||||
|
||||
func (vm *VM) callFunction(numArgs int) error {
|
||||
fn, ok := vm.stack[vm.sp-1-numArgs].(*object.CompiledFunction)
|
||||
if !ok {
|
||||
return fmt.Errorf("calling non-function")
|
||||
func (vm *VM) executeCall(numArgs int) error {
|
||||
callee := vm.stack[vm.sp-1-numArgs]
|
||||
switch callee := callee.(type) {
|
||||
case *object.CompiledFunction:
|
||||
return vm.callFunction(callee, numArgs)
|
||||
case *object.Builtin:
|
||||
return vm.callBuiltin(callee, numArgs)
|
||||
default:
|
||||
return fmt.Errorf("calling non-function and non-built-in")
|
||||
}
|
||||
}
|
||||
|
||||
func (vm *VM) callFunction(fn *object.CompiledFunction, numArgs int) error {
|
||||
if numArgs != fn.NumParameters {
|
||||
return fmt.Errorf("wrong number of arguments: want=%d, got=%d", fn.NumParameters, numArgs)
|
||||
}
|
||||
@@ -482,6 +500,27 @@ func (vm *VM) callFunction(numArgs int) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (vm *VM) callBuiltin(builtin *object.Builtin, numArgs int) error {
|
||||
args := vm.stack[vm.sp-numArgs : vm.sp]
|
||||
|
||||
result := builtin.Fn(args...)
|
||||
vm.sp = vm.sp - numArgs - 1
|
||||
|
||||
if result != nil {
|
||||
err := vm.push(result)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
} else {
|
||||
err := vm.push(Null)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func nativeBoolToBooleanObject(input bool) *object.Boolean {
|
||||
if input {
|
||||
return True
|
||||
|
||||
Reference in New Issue
Block a user