fix: 修复跨 VM 共享 Shape 指针问题
This commit is contained in:
@@ -7,7 +7,7 @@ use crate::shape_forge::ShapeId;
|
||||
#[derive(Debug, Clone)]
|
||||
pub struct PropTemplate {
|
||||
pub shape_id: ShapeId,
|
||||
pub ptr_bits: u64,
|
||||
pub position: u8,
|
||||
pub generation: u32,
|
||||
}
|
||||
|
||||
@@ -67,13 +67,13 @@ mod tests {
|
||||
let forge = PropForge::new();
|
||||
let t = PropTemplate {
|
||||
shape_id: 1,
|
||||
ptr_bits: 3,
|
||||
position: 3,
|
||||
generation: 10,
|
||||
};
|
||||
forge.upsert(1, t);
|
||||
let got = forge.get_template(1).unwrap();
|
||||
assert_eq!(got.shape_id, 1);
|
||||
assert_eq!(got.ptr_bits, 3);
|
||||
assert_eq!(got.position, 3);
|
||||
assert_eq!(got.generation, 10);
|
||||
}
|
||||
|
||||
@@ -84,7 +84,7 @@ mod tests {
|
||||
1,
|
||||
PropTemplate {
|
||||
shape_id: 1,
|
||||
ptr_bits: 3,
|
||||
position: 3,
|
||||
generation: 10,
|
||||
},
|
||||
);
|
||||
@@ -92,7 +92,7 @@ mod tests {
|
||||
1,
|
||||
PropTemplate {
|
||||
shape_id: 1,
|
||||
ptr_bits: 7,
|
||||
position: 7,
|
||||
generation: 5,
|
||||
},
|
||||
);
|
||||
@@ -107,7 +107,7 @@ mod tests {
|
||||
1,
|
||||
PropTemplate {
|
||||
shape_id: 1,
|
||||
ptr_bits: 3,
|
||||
position: 3,
|
||||
generation: 5,
|
||||
},
|
||||
);
|
||||
@@ -115,12 +115,12 @@ mod tests {
|
||||
1,
|
||||
PropTemplate {
|
||||
shape_id: 1,
|
||||
ptr_bits: 7,
|
||||
position: 7,
|
||||
generation: 10,
|
||||
},
|
||||
);
|
||||
let got = forge.get_template(1).unwrap();
|
||||
assert_eq!(got.generation, 10);
|
||||
assert_eq!(got.ptr_bits, 7);
|
||||
assert_eq!(got.position, 7);
|
||||
}
|
||||
}
|
||||
|
||||
+60
-42
@@ -571,6 +571,17 @@ impl Vm {
|
||||
self.kernel.string_forge().lookup(val.as_string_index())
|
||||
}
|
||||
|
||||
fn template_prop_ptr(&self, obj: &JsObject, template: &PropTemplate) -> Option<*const JsValue> {
|
||||
let pos = template.position as usize;
|
||||
obj.hash_props_vec().and_then(|vec| {
|
||||
if pos < vec.len() {
|
||||
Some(&*vec[pos] as *const JsValue)
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
fn resolve_property(&self, obj: &JsObject, prop_name_si: u32) -> Option<JsValue> {
|
||||
if let Some(pos) = self
|
||||
.kernel
|
||||
@@ -634,7 +645,7 @@ impl Vm {
|
||||
new_shape_id,
|
||||
PropTemplate {
|
||||
shape_id: new_shape_id,
|
||||
ptr_bits: ptr as u64,
|
||||
position: new_pos,
|
||||
generation: obj.generation(),
|
||||
},
|
||||
);
|
||||
@@ -954,12 +965,19 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
self.regs[a] = unsafe { *(ptr as *const JsValue) };
|
||||
let pos = template.position as usize;
|
||||
if let Some(vec) = obj.hash_props_vec() {
|
||||
if pos < vec.len() {
|
||||
let ptr = &*vec[pos] as *const JsValue;
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
self.regs[a] = unsafe { *(ptr) };
|
||||
} else {
|
||||
self.regs[a] = self
|
||||
.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined());
|
||||
}
|
||||
} else {
|
||||
self.regs[a] = self
|
||||
.resolve_property(obj, prop_name_si)
|
||||
@@ -1029,7 +1047,7 @@ impl Vm {
|
||||
new_shape_id,
|
||||
PropTemplate {
|
||||
shape_id: new_shape_id,
|
||||
ptr_bits: ptr as u64,
|
||||
position: new_pos,
|
||||
generation: obj.generation(),
|
||||
},
|
||||
);
|
||||
@@ -1306,12 +1324,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1367,7 +1385,7 @@ impl Vm {
|
||||
new_shape_id,
|
||||
PropTemplate {
|
||||
shape_id: new_shape_id,
|
||||
ptr_bits: ptr as u64,
|
||||
position: new_pos,
|
||||
generation: obj.generation(),
|
||||
},
|
||||
);
|
||||
@@ -1400,12 +1418,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1461,7 +1479,7 @@ impl Vm {
|
||||
new_shape_id,
|
||||
PropTemplate {
|
||||
shape_id: new_shape_id,
|
||||
ptr_bits: ptr as u64,
|
||||
position: new_pos,
|
||||
generation: obj.generation(),
|
||||
},
|
||||
);
|
||||
@@ -1564,12 +1582,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1628,12 +1646,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1683,12 +1701,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1738,12 +1756,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1793,12 +1811,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
@@ -1848,12 +1866,12 @@ impl Vm {
|
||||
} else if let Some(template) =
|
||||
self.kernel.prop_forge().get_template(obj.shape_id())
|
||||
{
|
||||
if template.ptr_bits != 0 {
|
||||
let ptr = template.ptr_bits;
|
||||
if let Some(ptr) = self.template_prop_ptr(obj, &template) {
|
||||
|
||||
self.bytecode[self.pc - 3] = obj.shape_id() & 0x00FF_FFFF;
|
||||
self.bytecode[self.pc - 2] = ptr as u32;
|
||||
self.bytecode[self.pc - 1] = (ptr >> 32) as u32;
|
||||
unsafe { *(ptr as *const JsValue) }
|
||||
self.bytecode[self.pc - 1] = (ptr as u64 >> 32) as u32;
|
||||
unsafe { *ptr }
|
||||
} else {
|
||||
self.resolve_property(obj, prop_name_si)
|
||||
.unwrap_or(JsValue::undefined())
|
||||
|
||||
Reference in New Issue
Block a user