fix(vm): SUPER_CALL 后构造实例 proto 设为 new.target.prototype(子类化内建)

This commit is contained in:
爱特每羊队
2026-08-07 18:41:34 +08:00
parent f015e1c428
commit 45925b8701
+24 -2
View File
@@ -406,7 +406,13 @@ impl Vm {
let func: NativeFn = unsafe { native_fn_ptr_to_fn(super_obj.native_fn().unwrap()) };
match func(self, &args_buf[..len]) {
NativeResult::Ok(val) => {
self.regs[254] = if val.is_object() { val } else { derived_this };
// super() 返回实例的 [[Prototype]] 须设为 new.target.prototype
//(native 构造器不知道 new.target,由调用方设置)。
let instance = if val.is_object() { val } else { derived_this };
if instance.is_object() {
self.set_constructed_proto(instance, new_target_obj)?;
}
self.regs[254] = instance;
self.regs[rd] = self.regs[254];
}
NativeResult::Err(err_val) => {
@@ -422,7 +428,11 @@ impl Vm {
// (或回退到 derived_this)。
match self.call_function_sync(callee, this, &args) {
Ok(val) => {
self.regs[254] = if val.is_object() { val } else { derived_this };
let instance = if val.is_object() { val } else { derived_this };
if instance.is_object() {
self.set_constructed_proto(instance, new_target_obj)?;
}
self.regs[254] = instance;
self.regs[rd] = self.regs[254];
}
Err(e) => return Err(e),
@@ -505,6 +515,18 @@ impl Vm {
Ok(false)
}
/// super() 返回的构造实例其 [[Prototype]] 设为 new.target.prototype。
fn set_constructed_proto(&mut self, instance: JsValue, new_target_obj: &JsObject) -> Result<(), String> {
let proto_si = self.kernel_core.perm_interner().intern("prototype").0;
if let Some(proto_val) = self.resolve_property(new_target_obj, proto_si) {
if proto_val.is_object() {
let obj = unsafe { &mut *instance.as_js_object_ptr() };
obj.set_proto(proto_val).map_err(|e| e.to_string())?;
}
}
Ok(())
}
pub(crate) fn dispatch_super_get_prop(&mut self, rd: usize, a: usize, b: usize) -> Result<bool, String> {
vm_trace!("SUPER_GET_PROP rd={} a={} b={}", rd, a, b);
let key_val = self.regs[b];