-
-
Notifications
You must be signed in to change notification settings - Fork 860
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
avm2: Implement support for native methods in playerglobal #7244
Conversation
cc2fe1d
to
3653144
Compare
3653144
to
9c6fe81
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd mark this as approved but the prior PR this depends on hasn't been merged in first. But this is absolutely fantastic work. Much appreciated.
9c6fe81
to
e7f8fac
Compare
@kmeisthax Now that the other PR has been merged, do you think that this is ready to merge? |
7b80213
to
9974af4
Compare
4610a11
to
33d2a95
Compare
// instance methods, class methods, and freestanding functions. | ||
// We're going to insert them into an `FnvHashMap`, so the order | ||
// that we visit them in doesn't matter. | ||
for (i, instance) in abc.instances.iter().enumerate() { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not entirely sure how it's matters, but it seems like nativegen.py
recursively traverses through Script
-> Method
/Class
, rather than a linear Instance
scan.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nothing depends on the iteration order, since we just use the method ids.
core/build_playerglobal/src/lib.rs
Outdated
let mut reader = swf::avm2::read::Reader::new(data); | ||
let abc = reader.read()?; | ||
|
||
let mut rust_paths = FnvHashMap::default(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about turning this FnvHashMap
into a simple Vec
? This way we can get rid of the fnv
dependency.
I suggest turning this into a native_methods: Vec<&Method>
, which will be gathered in check_trait
.
Then the Rust-path logic of check_trait
will be moved out of it, next to the Rust code generation.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We need the parent in order to construct the Rust path, so I think it would be simpler to keep that in check_trait
. However, I can change it to directly construct a Vec<Option<TokenStream>>
with 'holes' for missing methods.
008df66
to
dec04b1
Compare
@relrelb I've addressed your comments |
00f8367
to
6ad342e
Compare
@relrelb Are there any other changes that you'd like me to make? |
core/src/avm2/script.rs
Outdated
|
||
let mut method = None; | ||
if is_global { | ||
if let Some(native) = activation.avm2().native_table[method_index.0 as usize] { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe this can be included in the generated NATIVE_TABLE
itself? Though it would require Method
to be constructible at a const
context.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think this is nearly as easy, with GC in the way.
One minor thing I think we could do would be move the props (esp signature
) from BytecodeMethod
to the NativeMethod
without cloning them.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've refactored this to move out of signature
.
d00a061
to
07c4195
Compare
@relrelb I've addressed your most recent comments. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for your work! Looks good here, okay with you @relrelb ?
let make_native_table = quote! { | ||
const NATIVE_TABLE: &[Option<crate::avm2::method::NativeMethodImpl>] = &[ | ||
#(#rust_paths,)* | ||
]; | ||
} | ||
.to_string(); | ||
|
||
// Each table entry ends with ') ,' - insert a newline so that | ||
// each entry is on its own line. This makes error messages more readable. | ||
let make_native_table = make_native_table.replace(") ,", ") ,\n"); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wonder if it's worth using, for example, prettyplease
to make the output nicer in the future. Overkill for this specific case, but I expect we will be generating more and more code that it might be worthwhile at some point.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, it might be worth adding along with custom instance allocator support (which I'm working on in a follow-up PR).
5431644
to
72db741
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good, able to merge in my opinion, just please rebase/square before merging.
This commit adds support for marking methods as `native` in ActionScript classes defined in playerglobal. The `build_playerglobal` now checks for native methods, and generates Rust code linking them to a corresponding Rust function definition in the codebase. To test this functionality, I've reimplemented several functions as native methods (and moved related code to pure ActionScript).
72db741
to
880ea71
Compare
The Nightly failure is due to the regression rust-lang/rust#99286 |
This commit adds support for marking methods as
native
in ActionScript classes defined in playerglobal. The
build_playerglobal
now checks for native methods, andgenerates Rust code linking them to a corresponding Rust
function definition in the codebase.
To test this functionality, I've reimplemented several
functions as native methods (and moved related code to
pure ActionScript).