avm2: Don't skip method binding in `callproperty` if the method requires `arguments`, as it may access `callee`.

This commit is contained in:
David Wendt 2021-10-23 19:25:22 -04:00 committed by Mike Welsh
parent 1b5869e15a
commit 272b1784b8
2 changed files with 28 additions and 6 deletions

View File

@ -367,4 +367,12 @@ impl<'gc> Method<'gc> {
Method::Bytecode(bm) => Ok(bm), Method::Bytecode(bm) => Ok(bm),
} }
} }
/// Check if this method needs `arguments`.
pub fn needs_arguments_object(&self) -> bool {
match self {
Method::Native { .. } => false,
Method::Bytecode(bm) => bm.method().needs_arguments_object,
}
}
} }

View File

@ -411,32 +411,46 @@ pub trait TObject<'gc>: 'gc + Collect + Debug + Into<Object<'gc>> + Clone + Copy
TraitKind::Method { method, .. } => Some(method.clone()), TraitKind::Method { method, .. } => Some(method.clone()),
_ => None, _ => None,
}) { }) {
let scope = superclass_object.instance_scope(); if !method.needs_arguments_object() {
let scope = superclass_object.instance_scope();
return Executable::from_method(method, scope, None, activation.context.gc_context) return Executable::from_method(
method,
scope,
None,
activation.context.gc_context,
)
.exec( .exec(
Some(self.into()), Some(self.into()),
arguments, arguments,
activation, activation,
Some(superclass_object), Some(superclass_object),
superclass_object.into(), superclass_object.into(), //Deliberately invalid.
); );
}
} }
} }
if let Some(class) = self.as_class_object() { if let Some(class) = self.as_class_object() {
if let Some(method_trait) = class.class_method(&name)? { if let Some(method_trait) = class.class_method(&name)? {
let method = method_trait.as_method().unwrap(); let method = method_trait.as_method().unwrap();
let scope = class.class_scope(); if !method.needs_arguments_object() {
let scope = class.class_scope();
return Executable::from_method(method, scope, None, activation.context.gc_context) return Executable::from_method(
method,
scope,
None,
activation.context.gc_context,
)
.exec( .exec(
Some(self.into()), Some(self.into()),
arguments, arguments,
activation, activation,
Some(class), Some(class),
class.into(), class.into(), //Deliberately invalid.
); );
}
} }
} }