feat: 为 VM 添加结构化日志
This commit is contained in:
@@ -1,4 +1,5 @@
|
||||
use crate::vm::{FrameContinuation, TryHandler, Vm};
|
||||
use crate::vm_trace;
|
||||
use oxide_bytecode::opcode;
|
||||
use oxide_types::object::PropAttributes;
|
||||
use oxide_types::value::JsValue;
|
||||
@@ -76,6 +77,7 @@ impl Vm {
|
||||
}
|
||||
|
||||
pub(crate) fn dispatch_define_accessor(&mut self, rd: usize, a: usize, b: usize) -> Result<(), String> {
|
||||
vm_trace!("DEFINE_ACCESSOR rd={} getter={} setter={}", rd, a, b);
|
||||
let prop_idx = self.bytecode[self.pc] as usize;
|
||||
self.pc += 1;
|
||||
if prop_idx >= self.immutables().len() {
|
||||
@@ -109,13 +111,23 @@ impl Vm {
|
||||
|
||||
pub(crate) fn dispatch_return(&mut self, rd: usize) -> Result<Option<JsValue>, String> {
|
||||
let result = self.regs[rd];
|
||||
crate::vm_debug!("RETURN depth={}", self.frames.len());
|
||||
crate::vm_debug!(
|
||||
"RETURN depth={} saved_pc={}",
|
||||
self.frames.len(),
|
||||
self.frames.last().map(|f| f.return_addr).unwrap_or(0)
|
||||
);
|
||||
if let Some(frame) = self.frames.pop() {
|
||||
let construct_result_reg = frame.construct_result_reg;
|
||||
let constructed_this = frame.constructed_this;
|
||||
let is_derived_constructor = frame.is_derived_constructor;
|
||||
let continuation = frame.continuation;
|
||||
let callee_this = self.regs[254];
|
||||
vm_trace!(
|
||||
"RETURN frame: continuation={:?}, derived={}, result_reg={}",
|
||||
continuation,
|
||||
is_derived_constructor,
|
||||
rd
|
||||
);
|
||||
self.restore_frame(frame);
|
||||
if let (Some(target_reg), Some(constructed_this)) = (construct_result_reg, constructed_this) {
|
||||
if is_derived_constructor && result.is_undefined() && callee_this.is_undefined() {
|
||||
@@ -124,24 +136,32 @@ impl Vm {
|
||||
}
|
||||
self.regs[target_reg as usize] = if result.is_object() { result } else { constructed_this };
|
||||
self.regs[0] = self.regs[target_reg as usize];
|
||||
vm_trace!("RETURN constructor: target_reg={} regs[0]={:?}", target_reg, self.regs[0]);
|
||||
} else {
|
||||
match continuation {
|
||||
FrameContinuation::None => self.regs[0] = result,
|
||||
FrameContinuation::AccessorGet { target_reg } => self.regs[target_reg as usize] = result,
|
||||
FrameContinuation::AccessorSet => {}
|
||||
FrameContinuation::AccessorGet { target_reg } => {
|
||||
self.regs[target_reg as usize] = result;
|
||||
vm_trace!("RETURN accessor_get: target_reg={}", target_reg);
|
||||
}
|
||||
FrameContinuation::AccessorSet => {
|
||||
vm_trace!("RETURN accessor_set");
|
||||
}
|
||||
}
|
||||
}
|
||||
Ok(None)
|
||||
} else {
|
||||
vm_trace!("RETURN top-level: regs[0]={:?}", result);
|
||||
Ok(Some(result))
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn dispatch_throw(&mut self, rd: usize) -> Result<bool, String> {
|
||||
crate::vm_debug!("THROW pc={}", self.pc);
|
||||
let exc_value = self.regs[rd];
|
||||
let kind = self.thrown_error_kind(exc_value);
|
||||
vm_trace!("THROW pc={} kind={}", self.pc, kind);
|
||||
self.exception_value = Some(exc_value);
|
||||
self.pending_error_kind = Some(self.thrown_error_kind(exc_value));
|
||||
self.pending_error_kind = Some(kind);
|
||||
self.unwind().map(|_| true)
|
||||
}
|
||||
|
||||
@@ -161,12 +181,14 @@ impl Vm {
|
||||
}
|
||||
|
||||
pub(crate) fn dispatch_try_end(&mut self) {
|
||||
vm_trace!("TRY_END");
|
||||
self.try_stack.pop();
|
||||
}
|
||||
|
||||
pub(crate) fn dispatch_try_finally_begin(&mut self, instr: u32) {
|
||||
let offset = opcode::offset16(instr) as isize;
|
||||
let finally_pc = ((self.pc as isize) + offset - 1) as usize;
|
||||
vm_trace!("TRY_FINALLY_BEGIN finally_pc={}", finally_pc);
|
||||
self.try_stack.push(TryHandler {
|
||||
catch_pc: None,
|
||||
finally_pc: Some(finally_pc),
|
||||
@@ -175,6 +197,7 @@ impl Vm {
|
||||
}
|
||||
|
||||
pub(crate) fn dispatch_try_finally_end(&mut self) -> Result<bool, String> {
|
||||
vm_trace!("TRY_FINALLY_END has_pending_exc={}", self.pending_exception.is_some());
|
||||
self.try_stack.pop();
|
||||
if self.pending_exception.is_some() && self.exception_value.is_none() {
|
||||
self.exception_value = self.pending_exception.take();
|
||||
|
||||
Reference in New Issue
Block a user