avm1: Migrate `SharedObject` to `NativeObject`

This commit is contained in:
relrelb 2023-07-15 19:27:38 +03:00
parent 268403faad
commit 151ad97686
7 changed files with 140 additions and 202 deletions

85
Cargo.lock generated
View File

@ -61,6 +61,15 @@ dependencies = [
"version_check",
]
[[package]]
name = "aho-corasick"
version = "0.7.20"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cc936419f96fa211c1b9166887b38e5e40b19958e5b895be7c1f93adec7071ac"
dependencies = [
"memchr",
]
[[package]]
name = "aho-corasick"
version = "1.0.2"
@ -78,9 +87,9 @@ checksum = "250f629c0161ad8107cf89319e990051fae62832fd343083bea452d93e2205fd"
[[package]]
name = "allocator-api2"
version = "0.2.16"
version = "0.2.15"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0942ffc6dcaadf03badf6e6a2d0228460359d5e34b57ccdc720b7382dfbd5ec5"
checksum = "56fc6cf8dc8c4158eed8649f9b8b0ea1518eb62b544fe9490d66fa0b349eafe9"
[[package]]
name = "alsa"
@ -999,9 +1008,9 @@ dependencies = [
[[package]]
name = "darling"
version = "0.20.3"
version = "0.20.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0209d94da627ab5605dcccf08bb18afa5009cfbef48d8a8b7d7bdbc79be25c5e"
checksum = "0558d22a7b463ed0241e993f76f09f30b126687447751a8638587b864e4b3944"
dependencies = [
"darling_core",
"darling_macro",
@ -1009,9 +1018,9 @@ dependencies = [
[[package]]
name = "darling_core"
version = "0.20.3"
version = "0.20.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "177e3443818124b357d8e76f53be906d60937f0d3a90773a664fa63fa253e621"
checksum = "ab8bfa2e259f8ee1ce5e97824a3c55ec4404a0d772ca7fa96bf19f0752a046eb"
dependencies = [
"fnv",
"ident_case",
@ -1022,9 +1031,9 @@ dependencies = [
[[package]]
name = "darling_macro"
version = "0.20.3"
version = "0.20.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "836a9bbc7ad63342d6d6e7b815ccab164bc77a2d95d84bc3117a8c0d5c98e2d5"
checksum = "29a358ff9f12ec09c3e61fef9b5a9902623a695a46a917b07f269bff1445611a"
dependencies = [
"darling_core",
"quote",
@ -1932,11 +1941,11 @@ checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b"
[[package]]
name = "globset"
version = "0.4.11"
version = "0.4.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1391ab1f92ffcc08911957149833e682aa3fe252b9f45f966d2ef972274c97df"
checksum = "029d74589adefde59de1a0c4f4732695c32805624aec7b68d91503d4dba79afc"
dependencies = [
"aho-corasick",
"aho-corasick 0.7.20",
"bstr",
"fnv",
"log",
@ -2361,9 +2370,9 @@ dependencies = [
[[package]]
name = "itoa"
version = "1.0.9"
version = "1.0.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38"
checksum = "62b02a5381cc465bd3041d84623d0fa3b66738b52b8e2fc3bab8ad63ab032f4a"
[[package]]
name = "jni"
@ -2660,9 +2669,9 @@ dependencies = [
[[package]]
name = "lyon_path"
version = "1.0.4"
version = "1.0.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ca507745ba7ccbc76e5c44e7b63b1a29d2b0d6126f375806a5bbaf657c7d6c45"
checksum = "7da8358c012e5651e4619cfd0b5b75c0f77866181a01b0909aab4bae14adf660"
dependencies = [
"lyon_geom",
"num-traits",
@ -3435,9 +3444,9 @@ dependencies = [
[[package]]
name = "portable-atomic"
version = "1.4.1"
version = "1.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "edc55135a600d700580e406b4de0d59cb9ad25e344a3a091a97ded2622ec4ec6"
checksum = "d220334a184db82b31b83f5ff093e3315280fb2b6bbc032022b2304a509aab7a"
[[package]]
name = "pp-rs"
@ -3668,9 +3677,9 @@ version = "1.9.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b2eae68fc220f7cf2532e4494aded17545fce192d59cd996e0fe7887f4ceb575"
dependencies = [
"aho-corasick",
"aho-corasick 1.0.2",
"memchr",
"regex-automata 0.3.3",
"regex-automata 0.3.2",
"regex-syntax 0.7.4",
]
@ -3685,11 +3694,11 @@ dependencies = [
[[package]]
name = "regex-automata"
version = "0.3.3"
version = "0.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "39354c10dd07468c2e73926b23bb9c2caca74c5501e38a35da70406f1d923310"
checksum = "83d3daa6976cffb758ec878f108ba0e062a45b2d6ca3a2cca965338855476caf"
dependencies = [
"aho-corasick",
"aho-corasick 1.0.2",
"memchr",
"regex-syntax 0.7.4",
]
@ -4158,15 +4167,15 @@ dependencies = [
[[package]]
name = "rustversion"
version = "1.0.14"
version = "1.0.13"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7ffc183a10b4478d04cbbbfc96d0873219d962dd5accaff2ffbd4ceb7df837f4"
checksum = "dc31bd9b61a32c31f9650d18add92aa83a49ba979c143eefd27fe7177b05bd5f"
[[package]]
name = "ryu"
version = "1.0.15"
version = "1.0.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1ad4cc8da4ef723ed60bced201181d83791ad433213d8c24efffda1eec85d741"
checksum = "fe232bdf6be8c8de797b22184ee71118d63780ea42ac85b61d1baa6d3b782ae9"
[[package]]
name = "safe_arch"
@ -4228,9 +4237,9 @@ checksum = "1ef965a420fe14fdac7dd018862966a4c14094f900e1650bbc71ddd7d580c8af"
[[package]]
name = "semver"
version = "1.0.18"
version = "1.0.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b0293b4b29daaf487284529cc2f5675b8e57c61f70167ba415a463651fd6a918"
checksum = "bebd363326d05ec3e2f532ab7660680f3b02130d780c299bca73469d521bc0ed"
[[package]]
name = "serde"
@ -4277,9 +4286,9 @@ dependencies = [
[[package]]
name = "serde_json"
version = "1.0.103"
version = "1.0.100"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d03b412469450d4404fe8499a268edd7f8b79fecb074b0d812ad64ca21f4031b"
checksum = "0f1e14e89be7aa4c4b78bdbdc9eb5bf8517829a600ae8eaa39a6e1d960b5185c"
dependencies = [
"indexmap 2.0.0",
"itoa",
@ -4813,9 +4822,9 @@ dependencies = [
[[package]]
name = "toml_edit"
version = "0.19.14"
version = "0.19.12"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f8123f27e969974a3dfba720fdb560be359f57b44302d280ba72e76a74480e8a"
checksum = "c500344a19072298cd05a7224b3c0c629348b78692bf48466c5238656e315a78"
dependencies = [
"indexmap 2.0.0",
"serde",
@ -5036,9 +5045,9 @@ checksum = "92888ba5573ff080736b3648696b70cafad7d250551175acbaa4e0385b3e1460"
[[package]]
name = "unicode-ident"
version = "1.0.11"
version = "1.0.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "301abaae475aa91687eb82514b328ab47a211a533026cb25fc3e519b86adfc3c"
checksum = "22049a19f4a68748a168c0fc439f9516686aa045927ff767eca0a85101fb6e73"
[[package]]
name = "unicode-normalization"
@ -5451,9 +5460,9 @@ dependencies = [
[[package]]
name = "wide"
version = "0.7.11"
version = "0.7.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "aa469ffa65ef7e0ba0f164183697b89b854253fd31aeb92358b7b6155177d62f"
checksum = "40018623e2dba2602a9790faba8d33f2ebdebf4b86561b83928db735f8784728"
dependencies = [
"bytemuck",
"safe_arch",
@ -5701,9 +5710,9 @@ dependencies = [
[[package]]
name = "winnow"
version = "0.5.0"
version = "0.4.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "81fac9742fd1ad1bd9643b991319f72dd031016d44b77039a26977eb667141e7"
checksum = "81a2094c43cc94775293eaa0e499fbc30048a6d824ac82c0351a8c0bf9112529"
dependencies = [
"memchr",
]

View File

@ -32,7 +32,6 @@ pub use error::Error;
pub use flv::FlvValueAvm1Ext;
pub use function::{Executable, ExecutionReason};
pub use globals::context_menu::make_context_menu_state;
pub use globals::shared_object::flush;
pub use globals::sound::start as start_sound;
pub use globals::system::SystemProperties;
pub use object::array_object::ArrayObject;

View File

@ -487,7 +487,6 @@ pub struct SystemPrototypes<'gc> {
pub rectangle: Object<'gc>,
pub rectangle_constructor: Object<'gc>,
pub transform_constructor: Object<'gc>,
pub shared_object: Object<'gc>,
pub shared_object_constructor: Object<'gc>,
pub color_transform: Object<'gc>,
pub color_transform_constructor: Object<'gc>,
@ -924,14 +923,11 @@ pub fn create_globals<'gc>(
globals.define_value(gc_context, "Boolean", boolean.into(), Attribute::DONT_ENUM);
globals.define_value(gc_context, "Date", date.into(), Attribute::DONT_ENUM);
let shared_object_proto = shared_object::create_proto(context, object_proto, function_proto);
let shared_obj =
shared_object::create_shared_object_object(context, shared_object_proto, function_proto);
let shared_object = shared_object::create_constructor(context, object_proto, function_proto);
globals.define_value(
gc_context,
"SharedObject",
shared_obj.into(),
shared_object.into(),
Attribute::DONT_ENUM,
);
@ -1082,8 +1078,7 @@ pub fn create_globals<'gc>(
rectangle: rectangle_proto,
rectangle_constructor: rectangle,
transform_constructor: transform,
shared_object: shared_object_proto,
shared_object_constructor: shared_obj,
shared_object_constructor: shared_object,
color_transform: color_transform_proto,
color_transform_constructor: color_transform,
context_menu: context_menu_proto,

View File

@ -1,11 +1,8 @@
use crate::avm1::activation::Activation;
use crate::avm1::error::Error;
use crate::avm1::function::{Executable, FunctionObject};
use crate::avm1::object::shared_object::SharedObject;
use crate::avm1::object::NativeObject;
use crate::avm1::property::Attribute;
use crate::avm1::function::FunctionObject;
use crate::avm1::property_decl::{define_properties_on, Declaration};
use crate::avm1::{Object, ScriptObject, TObject, Value};
use crate::avm1::{
Activation, Attribute, Error, Executable, NativeObject, Object, ScriptObject, TObject, Value,
};
use crate::avm1_stub;
use crate::context::GcContext;
use crate::display_object::TDisplayObject;
@ -13,9 +10,28 @@ use crate::string::AvmString;
use flash_lso::amf0::read::AMF0Decoder;
use flash_lso::amf0::writer::{Amf0Writer, CacheKey, ObjWriter};
use flash_lso::types::{Lso, Reference, Value as AmfValue};
use gc_arena::{Collect, GcCell};
use std::borrow::Cow;
use std::collections::BTreeMap;
#[derive(Default, Clone, Collect)]
#[collect(require_static)]
pub struct SharedObject {
/// The local name of this shared object
name: Option<String>,
// In future this will also handle remote SharedObjects
}
impl SharedObject {
fn name(&self) -> String {
self.name.clone().unwrap_or_default()
}
fn set_name(&mut self, name: String) {
self.name = Some(name);
}
}
const PROTO_DECLS: &[Declaration] = declare_properties! {
"clear" => method(clear; DONT_ENUM | DONT_DELETE);
"close" => method(close; DONT_ENUM | DONT_DELETE);
@ -33,12 +49,9 @@ const OBJECT_DECLS: &[Declaration] = declare_properties! {
"getDiskUsage" => method(get_disk_usage; DONT_ENUM);
"getLocal" => method(get_local);
"getRemote" => method(get_remote);
"getMaxSize" => method(get_max_size);
"addListener" => method(add_listener);
"removeListener" => method(remove_listener);
};
pub fn delete_all<'gc>(
fn delete_all<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -47,7 +60,7 @@ pub fn delete_all<'gc>(
Ok(Value::Undefined)
}
pub fn get_disk_usage<'gc>(
fn get_disk_usage<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -259,7 +272,7 @@ fn new_lso<'gc>(activation: &mut Activation<'_, 'gc>, name: &str, data: Object<'
)
}
pub fn get_local<'gc>(
fn get_local<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
args: &[Value<'gc>],
@ -389,8 +402,11 @@ pub fn get_local<'gc>(
.coerce_to_object(activation);
// Set the internal name
let obj_so = this.as_shared_object().unwrap();
obj_so.set_name(activation.context.gc_context, full_name.clone());
if let NativeObject::SharedObject(shared_object) = this.native() {
shared_object
.write(activation.context.gc_context)
.set_name(full_name.clone());
}
let mut data = Value::Undefined;
@ -426,7 +442,7 @@ pub fn get_local<'gc>(
Ok(this.into())
}
pub fn get_remote<'gc>(
fn get_remote<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -435,51 +451,7 @@ pub fn get_remote<'gc>(
Ok(Value::Undefined)
}
pub fn get_max_size<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
avm1_stub!(activation, "SharedObject", "getMaxSize");
Ok(Value::Undefined)
}
pub fn add_listener<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
avm1_stub!(activation, "SharedObject", "addListener");
Ok(Value::Undefined)
}
pub fn remove_listener<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
avm1_stub!(activation, "SharedObject", "removeListener");
Ok(Value::Undefined)
}
pub fn create_shared_object_object<'gc>(
context: &mut GcContext<'_, 'gc>,
shared_object_proto: Object<'gc>,
fn_proto: Object<'gc>,
) -> Object<'gc> {
let shared_obj = FunctionObject::constructor(
context.gc_context,
Executable::Native(constructor),
constructor_to_fn!(constructor),
fn_proto,
shared_object_proto,
);
let object = shared_obj.raw_script_object();
define_properties_on(OBJECT_DECLS, context, object, fn_proto);
shared_obj
}
pub fn clear<'gc>(
fn clear<'gc>(
activation: &mut Activation<'_, 'gc>,
this: Object<'gc>,
_args: &[Value<'gc>],
@ -490,15 +462,15 @@ pub fn clear<'gc>(
data.delete(activation, *k);
}
let so = this.as_shared_object().unwrap();
let name = so.get_name();
if let NativeObject::SharedObject(shared_object) = this.native() {
let name = shared_object.read().name();
activation.context.storage.remove_key(&name);
}
Ok(Value::Undefined)
}
pub fn close<'gc>(
fn close<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -507,7 +479,7 @@ pub fn close<'gc>(
Ok(Value::Undefined)
}
pub fn connect<'gc>(
fn connect<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -516,14 +488,16 @@ pub fn connect<'gc>(
Ok(Value::Undefined)
}
pub fn flush<'gc>(
pub(crate) fn flush<'gc>(
activation: &mut Activation<'_, 'gc>,
this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
let NativeObject::SharedObject(shared_object) = this.native() else {
return Ok(Value::Undefined);
};
let name = shared_object.read().name();
let data = this.get("data", activation)?.coerce_to_object(activation);
let this_obj = this.as_shared_object().unwrap();
let name = this_obj.get_name();
let mut lso = new_lso(activation, &name, data);
flash_lso::write::write_to_bytes(&mut lso).unwrap_or_default();
// Flash does not write empty LSOs to disk
@ -535,14 +509,16 @@ pub fn flush<'gc>(
}
}
pub fn get_size<'gc>(
fn get_size<'gc>(
activation: &mut Activation<'_, 'gc>,
this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
let NativeObject::SharedObject(shared_object) = this.native() else {
return Ok(Value::Undefined);
};
let name = shared_object.read().name();
let data = this.get("data", activation)?.coerce_to_object(activation);
let this_obj = this.as_shared_object().unwrap();
let name = this_obj.get_name();
let mut lso = new_lso(activation, &name, data);
// Flash returns 0 for empty LSOs, but the actual number of bytes (including the header) otherwise
if lso.body.is_empty() {
@ -553,7 +529,7 @@ pub fn get_size<'gc>(
}
}
pub fn send<'gc>(
fn send<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -562,7 +538,7 @@ pub fn send<'gc>(
Ok(Value::Undefined)
}
pub fn set_fps<'gc>(
fn set_fps<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -571,7 +547,7 @@ pub fn set_fps<'gc>(
Ok(Value::Undefined)
}
pub fn on_status<'gc>(
fn on_status<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -580,7 +556,7 @@ pub fn on_status<'gc>(
Ok(Value::Undefined)
}
pub fn on_sync<'gc>(
fn on_sync<'gc>(
activation: &mut Activation<'_, 'gc>,
_this: Object<'gc>,
_args: &[Value<'gc>],
@ -589,21 +565,40 @@ pub fn on_sync<'gc>(
Ok(Value::Undefined)
}
pub fn create_proto<'gc>(
fn constructor<'gc>(
activation: &mut Activation<'_, 'gc>,
this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
this.set_native(
activation.context.gc_context,
NativeObject::SharedObject(GcCell::new(
activation.context.gc_context,
Default::default(),
)),
);
Ok(this.into())
}
pub fn create_constructor<'gc>(
context: &mut GcContext<'_, 'gc>,
proto: Object<'gc>,
fn_proto: Object<'gc>,
) -> Object<'gc> {
let shared_obj = SharedObject::empty_shared_obj(context.gc_context, proto);
let object = shared_obj.raw_script_object();
define_properties_on(PROTO_DECLS, context, object, fn_proto);
shared_obj.into()
}
pub fn constructor<'gc>(
_activation: &mut Activation<'_, 'gc>,
this: Object<'gc>,
_args: &[Value<'gc>],
) -> Result<Value<'gc>, Error<'gc>> {
Ok(this.into())
let shared_object_proto = ScriptObject::new(context.gc_context, Some(proto));
define_properties_on(PROTO_DECLS, context, shared_object_proto, fn_proto);
let constructor = FunctionObject::constructor(
context.gc_context,
Executable::Native(constructor),
constructor_to_fn!(constructor),
fn_proto,
shared_object_proto.into(),
);
define_properties_on(
OBJECT_DECLS,
context,
constructor.raw_script_object(),
fn_proto,
);
constructor
}

View File

@ -11,10 +11,10 @@ use crate::avm1::globals::displacement_map_filter::DisplacementMapFilter;
use crate::avm1::globals::drop_shadow_filter::DropShadowFilter;
use crate::avm1::globals::glow_filter::GlowFilter;
use crate::avm1::globals::gradient_filter::GradientFilter;
use crate::avm1::globals::shared_object::SharedObject;
use crate::avm1::globals::transform::TransformObject;
use crate::avm1::globals::xml::Xml;
use crate::avm1::object::array_object::ArrayObject;
use crate::avm1::object::shared_object::SharedObject;
use crate::avm1::object::super_object::SuperObject;
use crate::avm1::object::value_object::ValueObject;
use crate::avm1::{Activation, Attribute, Error, ScriptObject, SoundObject, StageObject, Value};
@ -32,7 +32,6 @@ use std::fmt::Debug;
pub mod array_object;
mod custom_object;
pub mod script_object;
pub mod shared_object;
pub mod sound_object;
pub mod stage_object;
pub mod super_object;
@ -59,6 +58,7 @@ pub enum NativeObject<'gc> {
BitmapData(BitmapDataWrapper<'gc>),
Xml(Xml<'gc>),
XmlNode(XmlNode<'gc>),
SharedObject(GcCell<'gc, SharedObject>),
}
/// Represents an object that can be directly interacted with by the AVM
@ -75,7 +75,6 @@ pub enum NativeObject<'gc> {
SuperObject(SuperObject<'gc>),
ValueObject(ValueObject<'gc>),
FunctionObject(FunctionObject<'gc>),
SharedObject(SharedObject<'gc>),
}
)]
pub trait TObject<'gc>: 'gc + Collect + Into<Object<'gc>> + Clone + Copy {
@ -591,11 +590,6 @@ pub trait TObject<'gc>: 'gc + Collect + Into<Object<'gc>> + Clone + Copy {
None
}
/// Get the underlying `SharedObject`, if it exists
fn as_shared_object(&self) -> Option<SharedObject<'gc>> {
None
}
fn as_ptr(&self) -> *const ObjectPtr;
/// Check if this object is in the prototype chain of the specified test object.

View File

@ -1,56 +0,0 @@
use crate::impl_custom_object;
use gc_arena::{Collect, GcCell, MutationContext};
use crate::avm1::{Object, ScriptObject, TObject};
use std::fmt;
/// A SharedObject
#[derive(Clone, Copy, Collect)]
#[collect(no_drop)]
pub struct SharedObject<'gc>(GcCell<'gc, SharedObjectData<'gc>>);
#[derive(Clone, Collect)]
#[collect(no_drop)]
pub struct SharedObjectData<'gc> {
/// The underlying script object.
base: ScriptObject<'gc>,
/// The local name of this shared object
name: Option<String>,
// In future this will also handle remote SharedObjects
}
impl fmt::Debug for SharedObject<'_> {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
let this = self.0.read();
f.debug_struct("SharedObject")
.field("name", &this.name)
.finish()
}
}
impl<'gc> SharedObject<'gc> {
pub fn empty_shared_obj(gc_context: MutationContext<'gc, '_>, proto: Object<'gc>) -> Self {
SharedObject(GcCell::new(
gc_context,
SharedObjectData {
base: ScriptObject::new(gc_context, Some(proto)),
name: None,
},
))
}
pub fn set_name(&self, gc_context: MutationContext<'gc, '_>, name: String) {
self.0.write(gc_context).name = Some(name);
}
pub fn get_name(&self) -> String {
self.0.read().name.as_ref().cloned().unwrap_or_default()
}
}
impl<'gc> TObject<'gc> for SharedObject<'gc> {
impl_custom_object!(base {
bare_object(as_shared_object -> SharedObject::empty_shared_obj);
});
}

View File

@ -1987,7 +1987,9 @@ impl Player {
Activation::try_from_stub(context.reborrow(), ActivationIdentifier::root("[Flush]"))
{
for so in avm1_activation.context.avm1_shared_objects.clone().values() {
if let Err(e) = crate::avm1::flush(&mut avm1_activation, *so, &[]) {
if let Err(e) =
crate::avm1::globals::shared_object::flush(&mut avm1_activation, *so, &[])
{
tracing::error!("Error flushing AVM1 shared object `{:?}`: {:?}", so, e);
}
}