package vm import "jinx/pkg/lang/vm/value" func (vm *VM) execPushInt(x int64) { vm.stack.Top().Push(value.NewInt(x)) } func (vm *VM) execPushFloat(x float64) { vm.stack.Top().Push(value.NewFloat(x)) } func (vm *VM) execPushString(str string) { vm.stack.Top().Push(value.NewString(str)) } func (vm *VM) execPushBool(b bool) { vm.stack.Top().Push(value.NewBool(b)) } func (vm *VM) execPushNull() { vm.stack.Top().Push(value.NewNull()) } func (vm *VM) execPushArray() { vm.stack.Top().Push(value.NewArray([]value.Value{})) } func (vm *VM) execGetLocal(offset int) { top := vm.stack.Top() top.Push(top.At(int(offset))) } func (vm *VM) execGetArg() { vm.stack.Top().Push(vm.stack.Prev().Pop()) } func (vm *VM) execAdd() { top := vm.stack.Top() x := top.Pop() y := top.Pop() var res value.Value switch x.Type().Kind { case value.IntType: xv := x.Data().(int64) switch y.Type().Kind { case value.IntType: res = value.NewInt(xv + y.Data().(int64)) case value.FloatType: res = value.NewFloat(float64(xv) + y.Data().(float64)) default: panic("invalid operand types") } case value.FloatType: xv := x.Data().(float64) switch y.Type().Kind { case value.IntType: res = value.NewFloat(xv + float64(y.Data().(int64))) case value.FloatType: res = value.NewFloat(xv + y.Data().(float64)) default: panic("invalid operand types") } case value.StringType: switch y.Type().Kind { case value.StringType: res = value.NewString(x.Data().(string) + y.Data().(string)) default: panic("invalid operand types") } default: panic("invalid operand types") } top.Push(res) } func (vm *VM) execSub() { top := vm.stack.Top() x := top.Pop() y := top.Pop() var res value.Value switch x.Type().Kind { case value.IntType: xv := x.Data().(int64) switch y.Type().Kind { case value.IntType: res = value.NewInt(xv - y.Data().(int64)) case value.FloatType: res = value.NewFloat(float64(xv) - y.Data().(float64)) default: panic("invalid operand types") } case value.FloatType: xv := x.Data().(float64) switch y.Type().Kind { case value.IntType: res = value.NewFloat(xv - float64(y.Data().(int64))) case value.FloatType: res = value.NewFloat(xv - y.Data().(float64)) default: panic("invalid operand types") } default: panic("invalid operand types") } top.Push(res) } func (vm *VM) execIndex() { top := vm.stack.Top() v := top.Pop() i := top.Pop() switch v.Type().Kind { case value.ArrayType: arr := v.Data().([]value.Value) idx := i.Data().(int64) if idx < 0 || idx >= int64(len(arr)) { panic("index out of bounds") } top.Push(arr[idx]) default: panic("invalid operand types") } }