From ff06690140f07b36f4ddd38d838b5b561e086f5c Mon Sep 17 00:00:00 2001 From: Kevin Date: Mon, 16 Jan 2023 07:41:59 +0000 Subject: [PATCH] Clarity changes for the VM (#2531) Some small changes to the VM with the hopes of making it a bit more clear and concise. It changes the following: - Changes `code` to `code_block` and `code` to `bytecode` in `CallFrame` and `CodeBlock`, respectively. - Adds some creation methods to `CallFrame`. - Implements `Default` for `Vm`. --- boa_engine/src/builtins/console/mod.rs | 2 +- boa_engine/src/bytecompiler/mod.rs | 20 +-- boa_engine/src/context/mod.rs | 28 +--- boa_engine/src/vm/call_frame.rs | 40 +++++- boa_engine/src/vm/code_block.rs | 134 +++++------------- boa_engine/src/vm/flowgraph/mod.rs | 4 +- boa_engine/src/vm/mod.rs | 26 +++- boa_engine/src/vm/opcode/call/mod.rs | 4 +- .../src/vm/opcode/define/class/getter.rs | 4 +- .../src/vm/opcode/define/class/method.rs | 4 +- .../src/vm/opcode/define/class/setter.rs | 4 +- boa_engine/src/vm/opcode/define/mod.rs | 8 +- .../src/vm/opcode/define/own_property.rs | 2 +- boa_engine/src/vm/opcode/delete/mod.rs | 10 +- boa_engine/src/vm/opcode/get/function.rs | 8 +- boa_engine/src/vm/opcode/get/generator.rs | 4 +- boa_engine/src/vm/opcode/get/name.rs | 4 +- boa_engine/src/vm/opcode/get/private.rs | 2 +- boa_engine/src/vm/opcode/get/property.rs | 2 +- boa_engine/src/vm/opcode/push/class/field.rs | 2 +- .../src/vm/opcode/push/class/private.rs | 6 +- boa_engine/src/vm/opcode/push/environment.rs | 4 +- boa_engine/src/vm/opcode/push/literal.rs | 2 +- boa_engine/src/vm/opcode/set/name.rs | 6 +- boa_engine/src/vm/opcode/set/private.rs | 10 +- boa_engine/src/vm/opcode/set/property.rs | 15 +- 26 files changed, 163 insertions(+), 192 deletions(-) diff --git a/boa_engine/src/builtins/console/mod.rs b/boa_engine/src/builtins/console/mod.rs index bf3a2b32f0..b2b31b752e 100644 --- a/boa_engine/src/builtins/console/mod.rs +++ b/boa_engine/src/builtins/console/mod.rs @@ -319,7 +319,7 @@ impl Console { stack_trace.push( context .interner() - .resolve_expect(frame.code.name) + .resolve_expect(frame.code_block.name) .to_string(), ); } diff --git a/boa_engine/src/bytecompiler/mod.rs b/boa_engine/src/bytecompiler/mod.rs index 2223a38ff0..ec7a7b9bc6 100644 --- a/boa_engine/src/bytecompiler/mod.rs +++ b/boa_engine/src/bytecompiler/mod.rs @@ -349,8 +349,8 @@ impl<'b, 'icu> ByteCompiler<'b, 'icu> { } fn next_opcode_location(&mut self) -> u32 { - assert!(self.code_block.code.len() < u32::MAX as usize); - self.code_block.code.len() as u32 + assert!(self.code_block.bytecode.len() < u32::MAX as usize); + self.code_block.bytecode.len() as u32 } fn emit(&mut self, opcode: Opcode, operands: &[u32]) { @@ -361,15 +361,15 @@ impl<'b, 'icu> ByteCompiler<'b, 'icu> { } fn emit_u64(&mut self, value: u64) { - self.code_block.code.extend(value.to_ne_bytes()); + self.code_block.bytecode.extend(value.to_ne_bytes()); } fn emit_u32(&mut self, value: u32) { - self.code_block.code.extend(value.to_ne_bytes()); + self.code_block.bytecode.extend(value.to_ne_bytes()); } fn emit_u16(&mut self, value: u16) { - self.code_block.code.extend(value.to_ne_bytes()); + self.code_block.bytecode.extend(value.to_ne_bytes()); } fn emit_opcode(&mut self, opcode: Opcode) { @@ -377,7 +377,7 @@ impl<'b, 'icu> ByteCompiler<'b, 'icu> { } fn emit_u8(&mut self, value: u8) { - self.code_block.code.push(value); + self.code_block.bytecode.push(value); } fn emit_push_integer(&mut self, value: i32) { @@ -465,10 +465,10 @@ impl<'b, 'icu> ByteCompiler<'b, 'icu> { let index = index as usize; let bytes = target.to_ne_bytes(); - self.code_block.code[index + 1] = bytes[0]; - self.code_block.code[index + 2] = bytes[1]; - self.code_block.code[index + 3] = bytes[2]; - self.code_block.code[index + 4] = bytes[3]; + self.code_block.bytecode[index + 1] = bytes[0]; + self.code_block.bytecode[index + 2] = bytes[1]; + self.code_block.bytecode[index + 3] = bytes[2]; + self.code_block.bytecode[index + 4] = bytes[3]; } fn patch_jump(&mut self, label: Label) { diff --git a/boa_engine/src/context/mod.rs b/boa_engine/src/context/mod.rs index 022c0fbccf..2b6c7b3bcf 100644 --- a/boa_engine/src/context/mod.rs +++ b/boa_engine/src/context/mod.rs @@ -25,7 +25,7 @@ use crate::{ object::{FunctionObjectBuilder, GlobalPropertyMap, JsObject}, property::{Attribute, PropertyDescriptor, PropertyKey}, realm::Realm, - vm::{CallFrame, CodeBlock, FinallyReturn, GeneratorResumeKind, Vm}, + vm::{CallFrame, CodeBlock, Vm}, JsResult, JsValue, }; @@ -205,24 +205,7 @@ impl Context<'_> { pub fn execute(&mut self, code_block: Gc) -> JsResult { let _timer = Profiler::global().start_event("Execution", "Main"); - self.vm.push_frame(CallFrame { - code: code_block, - pc: 0, - catch: Vec::new(), - finally_return: FinallyReturn::None, - finally_jump: Vec::new(), - pop_on_return: 0, - loop_env_stack: Vec::from([0]), - try_env_stack: Vec::from([crate::vm::TryStackEntry { - num_env: 0, - num_loop_stack_entries: 0, - }]), - param_count: 0, - arg_count: 0, - generator_resume_kind: GeneratorResumeKind::Normal, - thrown: false, - async_generator: None, - }); + self.vm.push_frame(CallFrame::new(code_block)); self.realm.set_global_binding_number(); let result = self.run(); @@ -572,12 +555,7 @@ impl<'a> ContextBuilder<'a> { #[cfg(feature = "console")] console: Console::default(), intrinsics, - vm: Vm { - frames: Vec::with_capacity(16), - stack: Vec::with_capacity(1024), - trace: false, - stack_size_limit: 1024, - }, + vm: Vm::default(), #[cfg(feature = "intl")] icu: self.icu.unwrap_or_else(|| { let provider = BoaProvider::Buffer(boa_icu_provider::buffer()); diff --git a/boa_engine/src/vm/call_frame.rs b/boa_engine/src/vm/call_frame.rs index 764280e158..8f57b5d39d 100644 --- a/boa_engine/src/vm/call_frame.rs +++ b/boa_engine/src/vm/call_frame.rs @@ -8,7 +8,7 @@ use boa_gc::{Finalize, Gc, Trace}; /// A `CallFrame` holds the state of a function call. #[derive(Clone, Debug, Finalize, Trace)] pub struct CallFrame { - pub(crate) code: Gc, + pub(crate) code_block: Gc, pub(crate) pc: usize, #[unsafe_ignore_trace] pub(crate) catch: Vec, @@ -39,6 +39,44 @@ pub struct CallFrame { pub(crate) async_generator: Option, } +/// ---- `CallFrame` creation methods ---- +impl CallFrame { + /// Creates a new `CallFrame` with the provided `CodeBlock`. + pub(crate) fn new(code_block: Gc) -> Self { + Self { + code_block, + pc: 0, + catch: Vec::new(), + finally_return: FinallyReturn::None, + finally_jump: Vec::new(), + pop_on_return: 0, + loop_env_stack: Vec::from([0]), + try_env_stack: Vec::from([TryStackEntry { + num_env: 0, + num_loop_stack_entries: 0, + }]), + param_count: 0, + arg_count: 0, + generator_resume_kind: GeneratorResumeKind::Normal, + thrown: false, + async_generator: None, + } + } + + /// Updates a `CallFrame`'s `param_count` field with the value provided. + pub(crate) fn with_param_count(mut self, count: usize) -> Self { + self.param_count = count; + self + } + + /// Updates a `CallFrame`'s `arg_count` field with the value provided. + pub(crate) fn with_arg_count(mut self, count: usize) -> Self { + self.arg_count = count; + self + } +} + +/// ---- `CallFrame` stack methods ---- impl CallFrame { /// Tracks that one environment has been pushed in the current loop block. pub(crate) fn loop_env_stack_inc(&mut self) { diff --git a/boa_engine/src/vm/code_block.rs b/boa_engine/src/vm/code_block.rs index bdf8e7a222..43fd9ce512 100644 --- a/boa_engine/src/vm/code_block.rs +++ b/boa_engine/src/vm/code_block.rs @@ -15,8 +15,7 @@ use crate::{ js_string, object::{internal_methods::get_prototype_from_constructor, JsObject, ObjectData}, property::PropertyDescriptor, - vm::call_frame::GeneratorResumeKind, - vm::{call_frame::FinallyReturn, CallFrame, Opcode}, + vm::{CallFrame, Opcode}, Context, JsResult, JsString, JsValue, }; use boa_ast::{ @@ -78,7 +77,7 @@ pub struct CodeBlock { pub(crate) params: FormalParameterList, /// Bytecode - pub(crate) code: Vec, + pub(crate) bytecode: Vec, /// Literals pub(crate) literals: Vec, @@ -127,7 +126,7 @@ impl CodeBlock { #[must_use] pub fn new(name: Sym, length: u32, strict: bool) -> Self { Self { - code: Vec::new(), + bytecode: Vec::new(), literals: Vec::new(), names: Vec::new(), private_names: Vec::new(), @@ -162,7 +161,13 @@ impl CodeBlock { // // This has to be an unaligned read because we can't guarantee that // the types are aligned. - unsafe { self.code.as_ptr().add(offset).cast::().read_unaligned() } + unsafe { + self.bytecode + .as_ptr() + .add(offset) + .cast::() + .read_unaligned() + } } /// Read type T from code. @@ -171,7 +176,7 @@ impl CodeBlock { where T: Readable, { - assert!(offset + size_of::() - 1 < self.code.len()); + assert!(offset + size_of::() - 1 < self.bytecode.len()); // Safety: We checked that it is not an out-of-bounds read, // so this is safe. @@ -183,7 +188,7 @@ impl CodeBlock { /// /// Returns an empty `String` if no operands are present. pub(crate) fn instruction_operands(&self, pc: &mut usize, interner: &Interner) -> String { - let opcode: Opcode = self.code[*pc].try_into().expect("invalid opcode"); + let opcode: Opcode = self.bytecode[*pc].try_into().expect("invalid opcode"); *pc += size_of::(); match opcode { Opcode::SetFunctionName => { @@ -453,8 +458,8 @@ impl ToInternedString for CodeBlock { let mut pc = 0; let mut count = 0; - while pc < self.code.len() { - let opcode: Opcode = self.code[pc].try_into().expect("invalid opcode"); + while pc < self.bytecode.len() { + let opcode: Opcode = self.bytecode[pc].try_into().expect("invalid opcode"); let opcode = opcode.as_str(); let previous_pc = pc; let operands = self.instruction_operands(&mut pc, interner); @@ -854,24 +859,11 @@ impl JsObject { let param_count = code.params.as_ref().len(); - context.vm.push_frame(CallFrame { - code, - pc: 0, - catch: Vec::new(), - finally_return: FinallyReturn::None, - finally_jump: Vec::new(), - pop_on_return: 0, - loop_env_stack: Vec::from([0]), - try_env_stack: Vec::from([crate::vm::TryStackEntry { - num_env: 0, - num_loop_stack_entries: 0, - }]), - param_count, - arg_count, - generator_resume_kind: GeneratorResumeKind::Normal, - thrown: false, - async_generator: None, - }); + context.vm.push_frame( + CallFrame::new(code) + .with_param_count(param_count) + .with_arg_count(arg_count), + ); let result = context.run(); context.vm.pop_frame().expect("must have frame"); @@ -990,24 +982,11 @@ impl JsObject { let param_count = code.params.as_ref().len(); - context.vm.push_frame(CallFrame { - code, - pc: 0, - catch: Vec::new(), - finally_return: FinallyReturn::None, - finally_jump: Vec::new(), - pop_on_return: 0, - loop_env_stack: Vec::from([0]), - try_env_stack: Vec::from([crate::vm::TryStackEntry { - num_env: 0, - num_loop_stack_entries: 0, - }]), - param_count, - arg_count, - generator_resume_kind: GeneratorResumeKind::Normal, - thrown: false, - async_generator: None, - }); + context.vm.push_frame( + CallFrame::new(code) + .with_param_count(param_count) + .with_arg_count(arg_count), + ); let _result = context.run(); context.vm.pop_frame().expect("must have frame"); @@ -1119,24 +1098,9 @@ impl JsObject { let param_count = code.params.as_ref().len(); - let call_frame = CallFrame { - code, - pc: 0, - catch: Vec::new(), - finally_return: FinallyReturn::None, - finally_jump: Vec::new(), - pop_on_return: 0, - loop_env_stack: Vec::from([0]), - try_env_stack: Vec::from([crate::vm::TryStackEntry { - num_env: 0, - num_loop_stack_entries: 0, - }]), - param_count, - arg_count, - generator_resume_kind: GeneratorResumeKind::Normal, - thrown: false, - async_generator: None, - }; + let call_frame = CallFrame::new(code) + .with_param_count(param_count) + .with_arg_count(arg_count); let mut stack = args; std::mem::swap(&mut context.vm.stack, &mut stack); @@ -1275,24 +1239,9 @@ impl JsObject { let param_count = code.params.as_ref().len(); - let call_frame = CallFrame { - code, - pc: 0, - catch: Vec::new(), - finally_return: FinallyReturn::None, - finally_jump: Vec::new(), - pop_on_return: 0, - loop_env_stack: Vec::from([0]), - try_env_stack: Vec::from([crate::vm::TryStackEntry { - num_env: 0, - num_loop_stack_entries: 0, - }]), - param_count, - arg_count, - generator_resume_kind: GeneratorResumeKind::Normal, - thrown: false, - async_generator: None, - }; + let call_frame = CallFrame::new(code) + .with_param_count(param_count) + .with_arg_count(arg_count); let mut stack = args; std::mem::swap(&mut context.vm.stack, &mut stack); @@ -1494,24 +1443,11 @@ impl JsObject { let param_count = code.params.as_ref().len(); let has_binding_identifier = code.has_binding_identifier; - context.vm.push_frame(CallFrame { - code, - pc: 0, - catch: Vec::new(), - finally_return: FinallyReturn::None, - finally_jump: Vec::new(), - pop_on_return: 0, - loop_env_stack: Vec::from([0]), - try_env_stack: Vec::from([crate::vm::TryStackEntry { - num_env: 0, - num_loop_stack_entries: 0, - }]), - param_count, - arg_count, - generator_resume_kind: GeneratorResumeKind::Normal, - thrown: false, - async_generator: None, - }); + context.vm.push_frame( + CallFrame::new(code) + .with_param_count(param_count) + .with_arg_count(arg_count), + ); let result = context.run(); diff --git a/boa_engine/src/vm/flowgraph/mod.rs b/boa_engine/src/vm/flowgraph/mod.rs index 4b138c22d2..8699900756 100644 --- a/boa_engine/src/vm/flowgraph/mod.rs +++ b/boa_engine/src/vm/flowgraph/mod.rs @@ -31,8 +31,8 @@ impl CodeBlock { let mut returns = Vec::new(); let mut pc = 0; - while pc < self.code.len() { - let opcode: Opcode = self.code[pc].try_into().expect("invalid opcode"); + while pc < self.bytecode.len() { + let opcode: Opcode = self.bytecode[pc].try_into().expect("invalid opcode"); let opcode_str = opcode.as_str(); let previous_pc = pc; diff --git a/boa_engine/src/vm/mod.rs b/boa_engine/src/vm/mod.rs index d2c81b393c..b90ede4539 100644 --- a/boa_engine/src/vm/mod.rs +++ b/boa_engine/src/vm/mod.rs @@ -41,6 +41,17 @@ pub struct Vm { pub(crate) stack_size_limit: usize, } +impl Default for Vm { + fn default() -> Self { + Self { + frames: Vec::with_capacity(16), + stack: Vec::with_capacity(1024), + trace: false, + stack_size_limit: 1024, + } + } +} + impl Vm { /// Push a value on the stack. pub(crate) fn push(&mut self, value: T) @@ -62,7 +73,7 @@ impl Vm { #[track_caller] pub(crate) fn read(&mut self) -> T { - let value = self.frame().code.read::(self.frame().pc); + let value = self.frame().code_block.read::(self.frame().pc); self.frame_mut().pc += size_of::(); value } @@ -114,7 +125,7 @@ impl Context<'_> { fn execute_instruction(&mut self) -> JsResult { let opcode: Opcode = { let _timer = Profiler::global().start_event("Opcode retrieval", "vm"); - let opcode = self.vm.frame().code.code[self.vm.frame().pc] + let opcode = self.vm.frame().code_block.bytecode[self.vm.frame().pc] .try_into() .expect("could not convert code at PC to opcode"); self.vm.frame_mut().pc += 1; @@ -146,7 +157,10 @@ impl Context<'_> { println!( "{}\n", - self.vm.frame().code.to_interned_string(self.interner()) + self.vm + .frame() + .code_block + .to_interned_string(self.interner()) ); println!( "{msg:-^width$}", @@ -178,7 +192,7 @@ impl Context<'_> { .and_then(|f| f.get_promise_capability().cloned()) }); - while self.vm.frame().pc < self.vm.frame().code.code.len() { + while self.vm.frame().pc < self.vm.frame().code_block.bytecode.len() { #[cfg(feature = "fuzz")] { if self.instructions_remaining == 0 { @@ -192,14 +206,14 @@ impl Context<'_> { let opcode: Opcode = self .vm .frame() - .code + .code_block .read::(pc) .try_into() .expect("invalid opcode"); let operands = self .vm .frame() - .code + .code_block .instruction_operands(&mut pc, self.interner()); let instant = Instant::now(); diff --git a/boa_engine/src/vm/opcode/call/mod.rs b/boa_engine/src/vm/opcode/call/mod.rs index 3ab280915d..cd7f2b4797 100644 --- a/boa_engine/src/vm/opcode/call/mod.rs +++ b/boa_engine/src/vm/opcode/call/mod.rs @@ -44,7 +44,7 @@ impl Operation for CallEval { // A native function with the name "eval" implies, that is this the built-in eval function. let eval = matches!(object.borrow().as_function(), Some(Function::Native { .. })); - let strict = context.vm.frame().code.strict; + let strict = context.vm.frame().code_block.strict; if eval { if let Some(x) = arguments.get(0) { @@ -106,7 +106,7 @@ impl Operation for CallEvalSpread { // A native function with the name "eval" implies, that is this the built-in eval function. let eval = matches!(object.borrow().as_function(), Some(Function::Native { .. })); - let strict = context.vm.frame().code.strict; + let strict = context.vm.frame().code_block.strict; if eval { if let Some(x) = arguments.get(0) { diff --git a/boa_engine/src/vm/opcode/define/class/getter.rs b/boa_engine/src/vm/opcode/define/class/getter.rs index a118c2218c..fc758d4b0b 100644 --- a/boa_engine/src/vm/opcode/define/class/getter.rs +++ b/boa_engine/src/vm/opcode/define/class/getter.rs @@ -23,7 +23,7 @@ impl Operation for DefineClassStaticGetterByName { let class = class.as_object().expect("class must be object"); let key = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); { @@ -75,7 +75,7 @@ impl Operation for DefineClassGetterByName { let class_proto = class_proto.as_object().expect("class must be object"); let key = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); { diff --git a/boa_engine/src/vm/opcode/define/class/method.rs b/boa_engine/src/vm/opcode/define/class/method.rs index f2db0553ae..67290a51e9 100644 --- a/boa_engine/src/vm/opcode/define/class/method.rs +++ b/boa_engine/src/vm/opcode/define/class/method.rs @@ -23,7 +23,7 @@ impl Operation for DefineClassStaticMethodByName { let class = class.as_object().expect("class must be object"); let key = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); { @@ -70,7 +70,7 @@ impl Operation for DefineClassMethodByName { let class_proto = class_proto.as_object().expect("class must be object"); let key = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); { diff --git a/boa_engine/src/vm/opcode/define/class/setter.rs b/boa_engine/src/vm/opcode/define/class/setter.rs index f1c513e640..25d6105ace 100644 --- a/boa_engine/src/vm/opcode/define/class/setter.rs +++ b/boa_engine/src/vm/opcode/define/class/setter.rs @@ -23,7 +23,7 @@ impl Operation for DefineClassStaticSetterByName { let class = class.as_object().expect("class must be object"); let key = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); { @@ -75,7 +75,7 @@ impl Operation for DefineClassSetterByName { let class_proto = class_proto.as_object().expect("class must be object"); let key = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); { diff --git a/boa_engine/src/vm/opcode/define/mod.rs b/boa_engine/src/vm/opcode/define/mod.rs index cfa54e7f85..317919a263 100644 --- a/boa_engine/src/vm/opcode/define/mod.rs +++ b/boa_engine/src/vm/opcode/define/mod.rs @@ -23,7 +23,7 @@ impl Operation for DefVar { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; if binding_locator.is_global() { let key = context @@ -63,7 +63,7 @@ impl Operation for DefInitVar { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); let value = context.vm.pop(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; if binding_locator.is_silent() { return Ok(ShouldExit::False); } @@ -100,7 +100,7 @@ impl Operation for DefLet { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; context.realm.environments.put_value( binding_locator.environment_index(), binding_locator.binding_index(), @@ -126,7 +126,7 @@ macro_rules! implement_declaritives { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); let value = context.vm.pop(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; context.realm.environments.put_value( binding_locator.environment_index(), binding_locator.binding_index(), diff --git a/boa_engine/src/vm/opcode/define/own_property.rs b/boa_engine/src/vm/opcode/define/own_property.rs index a7c72467e2..471ecc963c 100644 --- a/boa_engine/src/vm/opcode/define/own_property.rs +++ b/boa_engine/src/vm/opcode/define/own_property.rs @@ -24,7 +24,7 @@ impl Operation for DefineOwnPropertyByName { } else { object.to_object(context)? }; - let name = context.vm.frame().code.names[index as usize]; + let name = context.vm.frame().code_block.names[index as usize]; let name = context .interner() .resolve_expect(name.sym()) diff --git a/boa_engine/src/vm/opcode/delete/mod.rs b/boa_engine/src/vm/opcode/delete/mod.rs index bdc7ee9746..0e5a79c695 100644 --- a/boa_engine/src/vm/opcode/delete/mod.rs +++ b/boa_engine/src/vm/opcode/delete/mod.rs @@ -17,7 +17,7 @@ impl Operation for DeletePropertyByName { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let key = context.vm.frame().code.names[index as usize]; + let key = context.vm.frame().code_block.names[index as usize]; let key = context .interner() .resolve_expect(key.sym()) @@ -25,7 +25,7 @@ impl Operation for DeletePropertyByName { .into(); let object = context.vm.pop(); let result = object.to_object(context)?.__delete__(&key, context)?; - if !result && context.vm.frame().code.strict { + if !result && context.vm.frame().code_block.strict { return Err(JsNativeError::typ() .with_message("Cannot delete property") .into()); @@ -52,7 +52,7 @@ impl Operation for DeletePropertyByValue { let result = object .to_object(context)? .__delete__(&key.to_property_key(context)?, context)?; - if !result && context.vm.frame().code.strict { + if !result && context.vm.frame().code_block.strict { return Err(JsNativeError::typ() .with_message("Cannot delete property") .into()); @@ -75,7 +75,7 @@ impl Operation for DeleteName { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; binding_locator.throw_mutate_immutable(context)?; let deleted = if binding_locator.is_global() @@ -93,7 +93,7 @@ impl Operation for DeleteName { context, )?; - if !deleted && context.vm.frame().code.strict { + if !deleted && context.vm.frame().code_block.strict { return Err(JsNativeError::typ() .with_message(format!( "property `{}` is non-configurable and cannot be deleted", diff --git a/boa_engine/src/vm/opcode/get/function.rs b/boa_engine/src/vm/opcode/get/function.rs index bb37860927..c361058954 100644 --- a/boa_engine/src/vm/opcode/get/function.rs +++ b/boa_engine/src/vm/opcode/get/function.rs @@ -16,7 +16,7 @@ impl Operation for GetArrowFunction { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let code = context.vm.frame().code.functions[index as usize].clone(); + let code = context.vm.frame().code_block.functions[index as usize].clone(); let function = create_function_object(code, false, true, None, context); context.vm.push(function); Ok(ShouldExit::False) @@ -36,7 +36,7 @@ impl Operation for GetAsyncArrowFunction { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let code = context.vm.frame().code.functions[index as usize].clone(); + let code = context.vm.frame().code_block.functions[index as usize].clone(); let function = create_function_object(code, true, true, None, context); context.vm.push(function); Ok(ShouldExit::False) @@ -56,7 +56,7 @@ impl Operation for GetFunction { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let code = context.vm.frame().code.functions[index as usize].clone(); + let code = context.vm.frame().code_block.functions[index as usize].clone(); let function = create_function_object(code, false, false, None, context); context.vm.push(function); Ok(ShouldExit::False) @@ -76,7 +76,7 @@ impl Operation for GetFunctionAsync { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let code = context.vm.frame().code.functions[index as usize].clone(); + let code = context.vm.frame().code_block.functions[index as usize].clone(); let function = create_function_object(code, true, false, None, context); context.vm.push(function); Ok(ShouldExit::False) diff --git a/boa_engine/src/vm/opcode/get/generator.rs b/boa_engine/src/vm/opcode/get/generator.rs index 63b3d0cfab..4b23dcdc04 100644 --- a/boa_engine/src/vm/opcode/get/generator.rs +++ b/boa_engine/src/vm/opcode/get/generator.rs @@ -16,7 +16,7 @@ impl Operation for GetGenerator { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let code = context.vm.frame().code.functions[index as usize].clone(); + let code = context.vm.frame().code_block.functions[index as usize].clone(); let function = create_generator_function_object(code, false, context); context.vm.push(function); Ok(ShouldExit::False) @@ -36,7 +36,7 @@ impl Operation for GetGeneratorAsync { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let code = context.vm.frame().code.functions[index as usize].clone(); + let code = context.vm.frame().code_block.functions[index as usize].clone(); let function = create_generator_function_object(code, true, context); context.vm.push(function); Ok(ShouldExit::False) diff --git a/boa_engine/src/vm/opcode/get/name.rs b/boa_engine/src/vm/opcode/get/name.rs index 6fb691a89f..747b04dc05 100644 --- a/boa_engine/src/vm/opcode/get/name.rs +++ b/boa_engine/src/vm/opcode/get/name.rs @@ -18,7 +18,7 @@ impl Operation for GetName { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; binding_locator.throw_mutate_immutable(context)?; let value = if binding_locator.is_global() { @@ -92,7 +92,7 @@ impl Operation for GetNameOrUndefined { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; binding_locator.throw_mutate_immutable(context)?; let value = if binding_locator.is_global() { if let Some(value) = context diff --git a/boa_engine/src/vm/opcode/get/private.rs b/boa_engine/src/vm/opcode/get/private.rs index 5bcca2536d..04f7db85ad 100644 --- a/boa_engine/src/vm/opcode/get/private.rs +++ b/boa_engine/src/vm/opcode/get/private.rs @@ -16,7 +16,7 @@ impl Operation for GetPrivateField { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let value = context.vm.pop(); let base_obj = value.to_object(context)?; let result = base_obj.private_get(&name, context)?; diff --git a/boa_engine/src/vm/opcode/get/property.rs b/boa_engine/src/vm/opcode/get/property.rs index 4b12397107..a3fd32a8f0 100644 --- a/boa_engine/src/vm/opcode/get/property.rs +++ b/boa_engine/src/vm/opcode/get/property.rs @@ -27,7 +27,7 @@ impl Operation for GetPropertyByName { let key: PropertyKey = context .interner() - .resolve_expect(context.vm.frame().code.names[index as usize].sym()) + .resolve_expect(context.vm.frame().code_block.names[index as usize].sym()) .into_common::(false) .into(); let result = object.__get__(&key, value, context)?; diff --git a/boa_engine/src/vm/opcode/push/class/field.rs b/boa_engine/src/vm/opcode/push/class/field.rs index 0f076ceafb..2715c1c738 100644 --- a/boa_engine/src/vm/opcode/push/class/field.rs +++ b/boa_engine/src/vm/opcode/push/class/field.rs @@ -58,7 +58,7 @@ impl Operation for PushClassFieldPrivate { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let field_function_value = context.vm.pop(); let class_value = context.vm.pop(); diff --git a/boa_engine/src/vm/opcode/push/class/private.rs b/boa_engine/src/vm/opcode/push/class/private.rs index 32132bb8fc..a827cc2a7c 100644 --- a/boa_engine/src/vm/opcode/push/class/private.rs +++ b/boa_engine/src/vm/opcode/push/class/private.rs @@ -18,7 +18,7 @@ impl Operation for PushClassPrivateMethod { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let method = context.vm.pop(); let method_object = method.as_callable().expect("method must be callable"); @@ -63,7 +63,7 @@ impl Operation for PushClassPrivateGetter { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let getter = context.vm.pop(); let getter_object = getter.as_callable().expect("getter must be callable"); let class = context.vm.pop(); @@ -101,7 +101,7 @@ impl Operation for PushClassPrivateSetter { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let setter = context.vm.pop(); let setter_object = setter.as_callable().expect("getter must be callable"); let class = context.vm.pop(); diff --git a/boa_engine/src/vm/opcode/push/environment.rs b/boa_engine/src/vm/opcode/push/environment.rs index 66a7fc4aa7..38525a1e5a 100644 --- a/boa_engine/src/vm/opcode/push/environment.rs +++ b/boa_engine/src/vm/opcode/push/environment.rs @@ -17,7 +17,7 @@ impl Operation for PushDeclarativeEnvironment { fn execute(context: &mut Context<'_>) -> JsResult { let num_bindings = context.vm.read::(); let compile_environments_index = context.vm.read::(); - let compile_environment = context.vm.frame().code.compile_environments + let compile_environment = context.vm.frame().code_block.compile_environments [compile_environments_index as usize] .clone(); context @@ -44,7 +44,7 @@ impl Operation for PushFunctionEnvironment { fn execute(context: &mut Context<'_>) -> JsResult { let num_bindings = context.vm.read::(); let compile_environments_index = context.vm.read::(); - let compile_environment = context.vm.frame().code.compile_environments + let compile_environment = context.vm.frame().code_block.compile_environments [compile_environments_index as usize] .clone(); context diff --git a/boa_engine/src/vm/opcode/push/literal.rs b/boa_engine/src/vm/opcode/push/literal.rs index 062dd404ba..4205e9d964 100644 --- a/boa_engine/src/vm/opcode/push/literal.rs +++ b/boa_engine/src/vm/opcode/push/literal.rs @@ -16,7 +16,7 @@ impl Operation for PushLiteral { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::() as usize; - let value = context.vm.frame().code.literals[index].clone(); + let value = context.vm.frame().code_block.literals[index].clone(); context.vm.push(value); Ok(ShouldExit::False) } diff --git a/boa_engine/src/vm/opcode/set/name.rs b/boa_engine/src/vm/opcode/set/name.rs index c40e1829e3..13a8a25313 100644 --- a/boa_engine/src/vm/opcode/set/name.rs +++ b/boa_engine/src/vm/opcode/set/name.rs @@ -17,7 +17,7 @@ impl Operation for SetName { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let binding_locator = context.vm.frame().code.bindings[index as usize]; + let binding_locator = context.vm.frame().code_block.bindings[index as usize]; let value = context.vm.pop(); if binding_locator.is_silent() { return Ok(ShouldExit::False); @@ -36,7 +36,7 @@ impl Operation for SetName { .into_common(false); let exists = context.global_bindings_mut().contains_key(&key); - if !exists && context.vm.frame().code.strict { + if !exists && context.vm.frame().code_block.strict { return Err(JsNativeError::reference() .with_message(format!( "assignment to undeclared variable {}", @@ -51,7 +51,7 @@ impl Operation for SetName { context, )?; - if !success && context.vm.frame().code.strict { + if !success && context.vm.frame().code_block.strict { return Err(JsNativeError::typ() .with_message(format!( "cannot set non-writable property: {}", diff --git a/boa_engine/src/vm/opcode/set/private.rs b/boa_engine/src/vm/opcode/set/private.rs index e25272192e..11d98cdf42 100644 --- a/boa_engine/src/vm/opcode/set/private.rs +++ b/boa_engine/src/vm/opcode/set/private.rs @@ -18,7 +18,7 @@ impl Operation for SetPrivateField { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let value = context.vm.pop(); let object = context.vm.pop(); let base_obj = object.to_object(context)?; @@ -41,7 +41,7 @@ impl Operation for DefinePrivateField { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let value = context.vm.pop(); let object = context.vm.pop(); let object = object @@ -68,7 +68,7 @@ impl Operation for SetPrivateMethod { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let value = context.vm.pop(); let value = value.as_callable().expect("method must be callable"); @@ -113,7 +113,7 @@ impl Operation for SetPrivateSetter { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let value = context.vm.pop(); let value = value.as_callable().expect("setter must be callable"); let object = context.vm.pop(); @@ -151,7 +151,7 @@ impl Operation for SetPrivateGetter { fn execute(context: &mut Context<'_>) -> JsResult { let index = context.vm.read::(); - let name = context.vm.frame().code.private_names[index as usize]; + let name = context.vm.frame().code_block.private_names[index as usize]; let value = context.vm.pop(); let value = value.as_callable().expect("getter must be callable"); let object = context.vm.pop(); diff --git a/boa_engine/src/vm/opcode/set/property.rs b/boa_engine/src/vm/opcode/set/property.rs index ef2fc65a00..6a9000dbd5 100644 --- a/boa_engine/src/vm/opcode/set/property.rs +++ b/boa_engine/src/vm/opcode/set/property.rs @@ -28,7 +28,7 @@ impl Operation for SetPropertyByName { object.to_object(context)? }; - let name = context.vm.frame().code.names[index as usize]; + let name = context.vm.frame().code_block.names[index as usize]; let name: PropertyKey = context .interner() .resolve_expect(name.sym()) @@ -37,7 +37,7 @@ impl Operation for SetPropertyByName { //object.set(name, value.clone(), context.vm.frame().code.strict, context)?; let succeeded = object.__set__(name.clone(), value.clone(), receiver, context)?; - if !succeeded && context.vm.frame().code.strict { + if !succeeded && context.vm.frame().code_block.strict { return Err(JsNativeError::typ() .with_message(format!("cannot set non-writable property: {name}")) .into()); @@ -69,7 +69,12 @@ impl Operation for SetPropertyByValue { }; let key = key.to_property_key(context)?; - object.set(key, value.clone(), context.vm.frame().code.strict, context)?; + object.set( + key, + value.clone(), + context.vm.frame().code_block.strict, + context, + )?; context.vm.stack.push(value); Ok(ShouldExit::False) } @@ -91,7 +96,7 @@ impl Operation for SetPropertyGetterByName { let value = context.vm.pop(); let object = context.vm.pop(); let object = object.to_object(context)?; - let name = context.vm.frame().code.names[index as usize]; + let name = context.vm.frame().code_block.names[index as usize]; let name = context .interner() .resolve_expect(name.sym()) @@ -168,7 +173,7 @@ impl Operation for SetPropertySetterByName { let value = context.vm.pop(); let object = context.vm.pop(); let object = object.to_object(context)?; - let name = context.vm.frame().code.names[index as usize]; + let name = context.vm.frame().code_block.names[index as usize]; let name = context .interner() .resolve_expect(name.sym())