mirror of
https://github.com/servo/servo.git
synced 2025-07-22 23:03:42 +01:00
Create two-phase initialization for generated JS engine bindings (#34366)
* script: Generate a runtime initialization for static JS binding information. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Replace dummy static initializers with OnceLock. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Fix clippy warnings. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Only initialize statics for DOM interfaces with interface objects. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Remove one unnecessary Box::leak usage. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * Tidy. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Hide thread-unsafe OnceLock usage inside of a wrapper type. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Mark ThreadUnsafeOnceLock::get unsafe. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * script: Simplify ThreadUnsafeOnceLock internals. Signed-off-by: Josh Matthews <josh@joshmatthews.net> --------- Signed-off-by: Josh Matthews <josh@joshmatthews.net>
This commit is contained in:
parent
faefed9869
commit
3515b83a95
5 changed files with 296 additions and 108 deletions
|
@ -7,6 +7,7 @@
|
|||
use std::ffi::CString;
|
||||
use std::os::raw::{c_char, c_void};
|
||||
use std::ptr::NonNull;
|
||||
use std::sync::OnceLock;
|
||||
use std::{ptr, slice, str};
|
||||
|
||||
use js::conversions::ToJSValConvertible;
|
||||
|
@ -48,6 +49,37 @@ use crate::dom::bindings::trace::trace_object;
|
|||
use crate::dom::windowproxy::WindowProxyHandler;
|
||||
use crate::script_runtime::JSContext as SafeJSContext;
|
||||
|
||||
/// A OnceLock wrapping a type that is not considered threadsafe by the Rust compiler, but
|
||||
/// will be used in a threadsafe manner (it will not be mutated, after being initialized).
|
||||
///
|
||||
/// This is needed to allow using JS API types (which usually involve raw pointers) in static initializers,
|
||||
/// when Servo guarantees through the use of OnceLock that only one thread will ever initialize
|
||||
/// the value.
|
||||
pub struct ThreadUnsafeOnceLock<T>(OnceLock<T>);
|
||||
|
||||
impl<T> ThreadUnsafeOnceLock<T> {
|
||||
pub const fn new() -> Self {
|
||||
Self(OnceLock::new())
|
||||
}
|
||||
|
||||
/// Initialize the value inside this lock. Panics if the lock has been previously initialized.
|
||||
pub fn set(&self, val: T) {
|
||||
assert!(self.0.set(val).is_ok());
|
||||
}
|
||||
|
||||
/// Get a reference to the value inside this lock. Panics if the lock has not been initialized.
|
||||
///
|
||||
/// SAFETY:
|
||||
/// The caller must ensure that it does not mutate value contained inside this lock
|
||||
/// (using interior mutability).
|
||||
pub unsafe fn get(&self) -> &T {
|
||||
self.0.get().unwrap()
|
||||
}
|
||||
}
|
||||
|
||||
unsafe impl<T> Sync for ThreadUnsafeOnceLock<T> {}
|
||||
unsafe impl<T> Send for ThreadUnsafeOnceLock<T> {}
|
||||
|
||||
#[derive(JSTraceable, MallocSizeOf)]
|
||||
/// Static data associated with a global object.
|
||||
pub struct GlobalStaticData {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue