From 9084677dd44d10a3a1b326fc1aff91dfea9c78cf Mon Sep 17 00:00:00 2001 From: Andrew Morris Date: Tue, 4 Apr 2023 09:51:49 +1000 Subject: [PATCH] Track const in stack frames --- .../array_mapping_frame.rs | 5 +++-- .../array_higher_functions/array_reduce.rs | 3 ++- .../array_reduce_right.rs | 4 +++- .../src/array_higher_functions/array_sort.rs | 7 +++++- valuescript_vm/src/bytecode_stack_frame.rs | 22 ++++++++++++------- valuescript_vm/src/first_stack_frame.rs | 2 +- valuescript_vm/src/stack_frame.rs | 2 +- valuescript_vm/src/vs_function.rs | 1 + 8 files changed, 31 insertions(+), 15 deletions(-) diff --git a/valuescript_vm/src/array_higher_functions/array_mapping_frame.rs b/valuescript_vm/src/array_higher_functions/array_mapping_frame.rs index 5b95f38..6f1d2d2 100644 --- a/valuescript_vm/src/array_higher_functions/array_mapping_frame.rs +++ b/valuescript_vm/src/array_higher_functions/array_mapping_frame.rs @@ -39,8 +39,9 @@ impl ArrayMappingFrame { } impl StackFrameTrait for ArrayMappingFrame { - fn write_this(&mut self, this: Val) { + fn write_this(&mut self, _const: bool, this: Val) -> Result<(), Val> { self.this = this.as_array_data(); + Ok(()) } fn write_param(&mut self, param: Val) { @@ -103,7 +104,7 @@ impl StackFrameTrait for ArrayMappingFrame { } } LoadFunctionResult::StackFrame(mut new_frame) => { - new_frame.write_this(self.this_arg.clone()); + new_frame.write_this(true, self.this_arg.clone())?; new_frame.write_param(el.clone()); new_frame.write_param(Val::Number(array_i as f64)); new_frame.write_param(Val::Array(array_data.clone())); diff --git a/valuescript_vm/src/array_higher_functions/array_reduce.rs b/valuescript_vm/src/array_higher_functions/array_reduce.rs index 68ecbfd..f0d9ffc 100644 --- a/valuescript_vm/src/array_higher_functions/array_reduce.rs +++ b/valuescript_vm/src/array_higher_functions/array_reduce.rs @@ -29,8 +29,9 @@ struct ReduceFrame { } impl StackFrameTrait for ReduceFrame { - fn write_this(&mut self, this: Val) { + fn write_this(&mut self, _const: bool, this: Val) -> Result<(), Val> { self.this = this.as_array_data(); + Ok(()) } fn write_param(&mut self, param: Val) { diff --git a/valuescript_vm/src/array_higher_functions/array_reduce_right.rs b/valuescript_vm/src/array_higher_functions/array_reduce_right.rs index 3211155..e97326c 100644 --- a/valuescript_vm/src/array_higher_functions/array_reduce_right.rs +++ b/valuescript_vm/src/array_higher_functions/array_reduce_right.rs @@ -29,13 +29,15 @@ struct ReduceRightFrame { } impl StackFrameTrait for ReduceRightFrame { - fn write_this(&mut self, this: Val) { + fn write_this(&mut self, _const: bool, this: Val) -> Result<(), Val> { self.this = this.as_array_data(); match &self.this { None => {} Some(ad) => self.array_i = ad.elements.len(), }; + + Ok(()) } fn write_param(&mut self, param: Val) { diff --git a/valuescript_vm/src/array_higher_functions/array_sort.rs b/valuescript_vm/src/array_higher_functions/array_sort.rs index cdfc61b..7957c66 100644 --- a/valuescript_vm/src/array_higher_functions/array_sort.rs +++ b/valuescript_vm/src/array_higher_functions/array_sort.rs @@ -206,8 +206,13 @@ enum SortTreeNodeData { } impl StackFrameTrait for SortFrame { - fn write_this(&mut self, this: Val) { + fn write_this(&mut self, const_: bool, this: Val) -> Result<(), Val> { + if const_ { + return type_error!("Cannot sort const array"); + } + self.this = this.as_array_data(); + Ok(()) } fn write_param(&mut self, param: Val) { diff --git a/valuescript_vm/src/bytecode_stack_frame.rs b/valuescript_vm/src/bytecode_stack_frame.rs index 79c68e4..066d031 100644 --- a/valuescript_vm/src/bytecode_stack_frame.rs +++ b/valuescript_vm/src/bytecode_stack_frame.rs @@ -17,6 +17,7 @@ use crate::vs_value::{LoadFunctionResult, Val, ValTrait}; pub struct BytecodeStackFrame { pub decoder: BytecodeDecoder, pub registers: Vec, + pub const_this: bool, pub param_start: usize, pub param_end: usize, pub this_target: Option, @@ -91,8 +92,10 @@ impl BytecodeStackFrame { } impl StackFrameTrait for BytecodeStackFrame { - fn write_this(&mut self, this: Val) { + fn write_this(&mut self, _const: bool, this: Val) -> Result<(), Val> { self.registers[1] = this; + self.const_this = _const; + Ok(()) } fn write_param(&mut self, param: Val) { @@ -217,11 +220,11 @@ impl StackFrameTrait for BytecodeStackFrame { self.this_target = this_target; if this_target.is_some() { - new_frame.write_this(self.registers[this_target.unwrap()].clone()); + new_frame.write_this(false, self.registers[this_target.unwrap()].clone())?; } } else { self.this_target = None; - new_frame.write_this(self.decoder.decode_val(&self.registers)); + new_frame.write_this(false, self.decoder.decode_val(&self.registers))?; } self.transfer_parameters(&mut new_frame); @@ -302,10 +305,13 @@ impl StackFrameTrait for BytecodeStackFrame { LoadFunctionResult::StackFrame(mut new_frame) => { self.transfer_parameters(&mut new_frame); - new_frame.write_this(match &obj { - ThisArg::Register(reg_i) => self.registers[reg_i.clone()].clone(), - ThisArg::Val(val) => val.clone(), - }); + new_frame.write_this( + false, + match &obj { + ThisArg::Register(reg_i) => self.registers[reg_i.clone()].clone(), + ThisArg::Val(val) => val.clone(), + }, + )?; self.return_target = self.decoder.decode_register_index(); @@ -386,7 +392,7 @@ impl StackFrameTrait for BytecodeStackFrame { } LoadFunctionResult::StackFrame(mut new_frame) => { self.transfer_parameters(&mut new_frame); - new_frame.write_this(instance); + new_frame.write_this(false, instance)?; self.return_target = None; self.this_target = self.decoder.decode_register_index(); diff --git a/valuescript_vm/src/first_stack_frame.rs b/valuescript_vm/src/first_stack_frame.rs index 9862cd1..96d6142 100644 --- a/valuescript_vm/src/first_stack_frame.rs +++ b/valuescript_vm/src/first_stack_frame.rs @@ -17,7 +17,7 @@ impl FirstStackFrame { } impl StackFrameTrait for FirstStackFrame { - fn write_this(&mut self, _this: Val) { + fn write_this(&mut self, _const: bool, _this: Val) -> Result<(), Val> { panic!("Not appropriate for FirstStackFrame"); } diff --git a/valuescript_vm/src/stack_frame.rs b/valuescript_vm/src/stack_frame.rs index 2b32c8f..a5ff93c 100644 --- a/valuescript_vm/src/stack_frame.rs +++ b/valuescript_vm/src/stack_frame.rs @@ -17,7 +17,7 @@ pub enum FrameStepOk { pub type FrameStepResult = Result; pub trait StackFrameTrait { - fn write_this(&mut self, this: Val); + fn write_this(&mut self, const_: bool, this: Val) -> Result<(), Val>; fn write_param(&mut self, param: Val); fn step(&mut self) -> FrameStepResult; fn apply_call_result(&mut self, call_result: CallResult); diff --git a/valuescript_vm/src/vs_function.rs b/valuescript_vm/src/vs_function.rs index cc3c490..e936035 100644 --- a/valuescript_vm/src/vs_function.rs +++ b/valuescript_vm/src/vs_function.rs @@ -51,6 +51,7 @@ impl VsFunction { pos: self.start, }, registers, + const_this: true, param_start: self.binds.len() + 2, param_end: self.parameter_count + 2, this_target: None,