mirror of
https://github.com/servo/servo.git
synced 2025-07-24 15:50:21 +01:00
Make generated bindings generic over DOM types (#35169)
* bindings: Start making generated bindings methods generic over DOM trait. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * bindings: Make binding initialization generic over the DOM types trait. Signed-off-by: Josh Matthews <josh@joshmatthews.net> * bindings: Start making proxyhandler code generic over DOM types. Signed-off-by: Josh Matthews <josh@joshmatthews.net> --------- Signed-off-by: Josh Matthews <josh@joshmatthews.net>
This commit is contained in:
parent
8748071329
commit
d5d7b0d34f
6 changed files with 72 additions and 52 deletions
|
@ -42,7 +42,7 @@ use crate::dom::bindings::principals::ServoJSPrincipalsRef;
|
||||||
use crate::dom::bindings::reflector::DomObject;
|
use crate::dom::bindings::reflector::DomObject;
|
||||||
use crate::dom::bindings::str::DOMString;
|
use crate::dom::bindings::str::DOMString;
|
||||||
use crate::dom::bindings::utils::delete_property_by_id;
|
use crate::dom::bindings::utils::delete_property_by_id;
|
||||||
use crate::dom::globalscope::GlobalScope;
|
use crate::dom::globalscope::{GlobalScope, GlobalScopeHelpers};
|
||||||
use crate::realms::{AlreadyInRealm, InRealm};
|
use crate::realms::{AlreadyInRealm, InRealm};
|
||||||
use crate::script_runtime::JSContext as SafeJSContext;
|
use crate::script_runtime::JSContext as SafeJSContext;
|
||||||
|
|
||||||
|
@ -376,7 +376,7 @@ pub(crate) unsafe extern "C" fn maybe_cross_origin_get_prototype_if_ordinary_raw
|
||||||
/// Implementation of `[[GetPrototypeOf]]` for [`Location`].
|
/// Implementation of `[[GetPrototypeOf]]` for [`Location`].
|
||||||
///
|
///
|
||||||
/// [`Location`]: https://html.spec.whatwg.org/multipage/#location-getprototypeof
|
/// [`Location`]: https://html.spec.whatwg.org/multipage/#location-getprototypeof
|
||||||
pub(crate) unsafe fn maybe_cross_origin_get_prototype(
|
pub(crate) unsafe fn maybe_cross_origin_get_prototype<D: crate::DomTypes>(
|
||||||
cx: SafeJSContext,
|
cx: SafeJSContext,
|
||||||
proxy: RawHandleObject,
|
proxy: RawHandleObject,
|
||||||
get_proto_object: unsafe fn(cx: SafeJSContext, global: HandleObject, rval: MutableHandleObject),
|
get_proto_object: unsafe fn(cx: SafeJSContext, global: HandleObject, rval: MutableHandleObject),
|
||||||
|
@ -385,7 +385,7 @@ pub(crate) unsafe fn maybe_cross_origin_get_prototype(
|
||||||
// > 1. If ! IsPlatformObjectSameOrigin(this) is true, then return ! OrdinaryGetPrototypeOf(this).
|
// > 1. If ! IsPlatformObjectSameOrigin(this) is true, then return ! OrdinaryGetPrototypeOf(this).
|
||||||
if is_platform_object_same_origin(cx, proxy) {
|
if is_platform_object_same_origin(cx, proxy) {
|
||||||
let ac = JSAutoRealm::new(*cx, proxy.get());
|
let ac = JSAutoRealm::new(*cx, proxy.get());
|
||||||
let global = GlobalScope::from_context(*cx, InRealm::Entered(&ac));
|
let global = D::GlobalScope::from_context(*cx, InRealm::Entered(&ac));
|
||||||
get_proto_object(
|
get_proto_object(
|
||||||
cx,
|
cx,
|
||||||
global.reflector().get_jsobject(),
|
global.reflector().get_jsobject(),
|
||||||
|
|
|
@ -3272,3 +3272,15 @@ unsafe fn global_scope_from_global_static(global: *mut JSObject) -> DomRoot<Glob
|
||||||
);
|
);
|
||||||
root_from_object_static(global).unwrap()
|
root_from_object_static(global).unwrap()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(unsafe_code)]
|
||||||
|
pub(crate) trait GlobalScopeHelpers<D: crate::DomTypes> {
|
||||||
|
unsafe fn from_context(cx: *mut JSContext, realm: InRealm) -> DomRoot<D::GlobalScope>;
|
||||||
|
}
|
||||||
|
|
||||||
|
#[allow(unsafe_code)]
|
||||||
|
impl GlobalScopeHelpers<crate::DomTypeHolder> for GlobalScope {
|
||||||
|
unsafe fn from_context(cx: *mut JSContext, realm: InRealm) -> DomRoot<Self> {
|
||||||
|
GlobalScope::from_context(cx, realm)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -69,8 +69,8 @@ pub fn init() -> JSEngineSetup {
|
||||||
|
|
||||||
// Create the global vtables used by the (generated) DOM
|
// Create the global vtables used by the (generated) DOM
|
||||||
// bindings to implement JS proxies.
|
// bindings to implement JS proxies.
|
||||||
RegisterBindings::RegisterProxyHandlers();
|
RegisterBindings::RegisterProxyHandlers::<crate::DomTypeHolder>();
|
||||||
RegisterBindings::InitAllStatics();
|
RegisterBindings::InitAllStatics::<crate::DomTypeHolder>();
|
||||||
|
|
||||||
js::glue::InitializeMemoryReporter(Some(is_dom_object));
|
js::glue::InitializeMemoryReporter(Some(is_dom_object));
|
||||||
}
|
}
|
||||||
|
|
|
@ -180,6 +180,10 @@ DOMInterfaces = {
|
||||||
'canGc': ['PlayEffect', 'Reset'],
|
'canGc': ['PlayEffect', 'Reset'],
|
||||||
},
|
},
|
||||||
|
|
||||||
|
'GlobalScope': {
|
||||||
|
'additionalTraits': ['crate::dom::globalscope::GlobalScopeHelpers<Self>'],
|
||||||
|
},
|
||||||
|
|
||||||
'GPU': {
|
'GPU': {
|
||||||
'inRealms': ['RequestAdapter'],
|
'inRealms': ['RequestAdapter'],
|
||||||
'canGc': ['RequestAdapter', 'WgslLanguageFeatures'],
|
'canGc': ['RequestAdapter', 'WgslLanguageFeatures'],
|
||||||
|
|
|
@ -1630,7 +1630,7 @@ class PropertyDefiner:
|
||||||
specsArray = f"static {name}_specs: ThreadUnsafeOnceLock<&[&[{specType}]]> = ThreadUnsafeOnceLock::new();\n"
|
specsArray = f"static {name}_specs: ThreadUnsafeOnceLock<&[&[{specType}]]> = ThreadUnsafeOnceLock::new();\n"
|
||||||
|
|
||||||
initSpecs = f"""
|
initSpecs = f"""
|
||||||
pub(crate) fn init_{name}_specs() {{
|
pub(crate) fn init_{name}_specs<D: DomTypes>() {{
|
||||||
{name}_specs.set(Box::leak(Box::new([{joinedSpecs}])));
|
{name}_specs.set(Box::leak(Box::new([{joinedSpecs}])));
|
||||||
}}"""
|
}}"""
|
||||||
|
|
||||||
|
@ -1638,7 +1638,7 @@ pub(crate) fn init_{name}_specs() {{
|
||||||
prefArray = f"static {name}: ThreadUnsafeOnceLock<&[Guard<&[{specType}]>]> = ThreadUnsafeOnceLock::new();\n"
|
prefArray = f"static {name}: ThreadUnsafeOnceLock<&[Guard<&[{specType}]>]> = ThreadUnsafeOnceLock::new();\n"
|
||||||
|
|
||||||
initPrefs = f"""
|
initPrefs = f"""
|
||||||
pub(crate) fn init_{name}_prefs() {{
|
pub(crate) fn init_{name}_prefs<D: DomTypes>() {{
|
||||||
{name}.set(Box::leak(Box::new([{joinedPrefableSpecs}])));
|
{name}.set(Box::leak(Box::new([{joinedPrefableSpecs}])));
|
||||||
}}"""
|
}}"""
|
||||||
|
|
||||||
|
@ -1667,7 +1667,7 @@ pub(crate) fn init_{name}_prefs() {{
|
||||||
joinedSpecs = ',\n'.join(specsArray)
|
joinedSpecs = ',\n'.join(specsArray)
|
||||||
initialSpecs = f"static {name}: ThreadUnsafeOnceLock<&[{specType}]> = ThreadUnsafeOnceLock::new();\n"
|
initialSpecs = f"static {name}: ThreadUnsafeOnceLock<&[{specType}]> = ThreadUnsafeOnceLock::new();\n"
|
||||||
initSpecs = f"""
|
initSpecs = f"""
|
||||||
pub(crate) fn init_{name}() {{
|
pub(crate) fn init_{name}<D: DomTypes>() {{
|
||||||
{name}.set(Box::leak(Box::new([{joinedSpecs}])));
|
{name}.set(Box::leak(Box::new([{joinedSpecs}])));
|
||||||
}}"""
|
}}"""
|
||||||
return dedent(f"{initialSpecs}{initSpecs}")
|
return dedent(f"{initialSpecs}{initSpecs}")
|
||||||
|
@ -1843,7 +1843,7 @@ class MethodDefiner(PropertyDefiner):
|
||||||
accessor = "Some(generic_static_promise_method)"
|
accessor = "Some(generic_static_promise_method)"
|
||||||
else:
|
else:
|
||||||
jitinfo = "ptr::null()"
|
jitinfo = "ptr::null()"
|
||||||
accessor = f'Some({m.get("nativeName", m["name"])})'
|
accessor = f'Some({m.get("nativeName", m["name"])}::<D>)'
|
||||||
if m["name"].startswith("@@"):
|
if m["name"].startswith("@@"):
|
||||||
assert not self.crossorigin
|
assert not self.crossorigin
|
||||||
name = f'JSPropertySpec_Name {{ symbol_: SymbolCode::{m["name"][2:]} as usize + 1 }}'
|
name = f'JSPropertySpec_Name {{ symbol_: SymbolCode::{m["name"][2:]} as usize + 1 }}'
|
||||||
|
@ -1933,7 +1933,7 @@ class AttrDefiner(PropertyDefiner):
|
||||||
return "JSNativeWrapper { op: None, info: ptr::null() }"
|
return "JSNativeWrapper { op: None, info: ptr::null() }"
|
||||||
|
|
||||||
if self.static:
|
if self.static:
|
||||||
accessor = f'get_{self.descriptor.internalNameFor(attr.identifier.name)}'
|
accessor = f'get_{self.descriptor.internalNameFor(attr.identifier.name)}::<D>'
|
||||||
jitinfo = "ptr::null()"
|
jitinfo = "ptr::null()"
|
||||||
else:
|
else:
|
||||||
if attr.type.isPromise():
|
if attr.type.isPromise():
|
||||||
|
@ -1959,7 +1959,7 @@ class AttrDefiner(PropertyDefiner):
|
||||||
return "JSNativeWrapper { op: None, info: ptr::null() }"
|
return "JSNativeWrapper { op: None, info: ptr::null() }"
|
||||||
|
|
||||||
if self.static:
|
if self.static:
|
||||||
accessor = f'set_{self.descriptor.internalNameFor(attr.identifier.name)}'
|
accessor = f'set_{self.descriptor.internalNameFor(attr.identifier.name)}::<D>'
|
||||||
jitinfo = "ptr::null()"
|
jitinfo = "ptr::null()"
|
||||||
else:
|
else:
|
||||||
if attr.hasLegacyLenientThis():
|
if attr.hasLegacyLenientThis():
|
||||||
|
@ -2661,6 +2661,8 @@ def DomTypes(descriptors, descriptorProvider, dictionaries, callbacks, typedefs,
|
||||||
iface_name = descriptor.interface.identifier.name
|
iface_name = descriptor.interface.identifier.name
|
||||||
traits = []
|
traits = []
|
||||||
|
|
||||||
|
traits += descriptor.additionalTraits
|
||||||
|
|
||||||
chain = descriptor.prototypeChain
|
chain = descriptor.prototypeChain
|
||||||
upcast = descriptor.hasDescendants()
|
upcast = descriptor.hasDescendants()
|
||||||
|
|
||||||
|
@ -3247,9 +3249,9 @@ class CGAbstractExternMethod(CGAbstractMethod):
|
||||||
Abstract base class for codegen of implementation-only (no
|
Abstract base class for codegen of implementation-only (no
|
||||||
declaration) static methods.
|
declaration) static methods.
|
||||||
"""
|
"""
|
||||||
def __init__(self, descriptor, name, returnType, args, doesNotPanic=False):
|
def __init__(self, descriptor, name, returnType, args, doesNotPanic=False, templateArgs=None):
|
||||||
CGAbstractMethod.__init__(self, descriptor, name, returnType, args,
|
CGAbstractMethod.__init__(self, descriptor, name, returnType, args,
|
||||||
inline=False, extern=True, doesNotPanic=doesNotPanic)
|
inline=False, extern=True, doesNotPanic=doesNotPanic, templateArgs=templateArgs)
|
||||||
|
|
||||||
|
|
||||||
class PropertyArrays():
|
class PropertyArrays():
|
||||||
|
@ -3304,7 +3306,7 @@ class CGCrossOriginProperties(CGThing):
|
||||||
"""
|
"""
|
||||||
static CROSS_ORIGIN_PROPERTIES: ThreadUnsafeOnceLock<CrossOriginProperties> = ThreadUnsafeOnceLock::new();
|
static CROSS_ORIGIN_PROPERTIES: ThreadUnsafeOnceLock<CrossOriginProperties> = ThreadUnsafeOnceLock::new();
|
||||||
|
|
||||||
pub(crate) fn init_cross_origin_properties() {
|
pub(crate) fn init_cross_origin_properties<D: DomTypes>() {
|
||||||
CROSS_ORIGIN_PROPERTIES.set(CrossOriginProperties {
|
CROSS_ORIGIN_PROPERTIES.set(CrossOriginProperties {
|
||||||
attributes: unsafe { sCrossOriginAttributes.get() },
|
attributes: unsafe { sCrossOriginAttributes.get() },
|
||||||
methods: unsafe { sCrossOriginMethods.get() },
|
methods: unsafe { sCrossOriginMethods.get() },
|
||||||
|
@ -3324,7 +3326,7 @@ class CGCollectJSONAttributesMethod(CGAbstractMethod):
|
||||||
Argument('*mut libc::c_void', 'this'),
|
Argument('*mut libc::c_void', 'this'),
|
||||||
Argument('HandleObject', 'result')]
|
Argument('HandleObject', 'result')]
|
||||||
CGAbstractMethod.__init__(self, descriptor, 'CollectJSONAttributes',
|
CGAbstractMethod.__init__(self, descriptor, 'CollectJSONAttributes',
|
||||||
'bool', args, pub=True, unsafe=True)
|
'bool', args, pub=True, unsafe=True, templateArgs=["D: DomTypes"])
|
||||||
self.toJSONMethod = toJSONMethod
|
self.toJSONMethod = toJSONMethod
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
|
@ -3346,7 +3348,7 @@ let global = incumbent_global.reflector().get_jsobject();\n"""
|
||||||
global));
|
global));
|
||||||
if is_satisfied {
|
if is_satisfied {
|
||||||
rooted!(in(cx) let mut temp = UndefinedValue());
|
rooted!(in(cx) let mut temp = UndefinedValue());
|
||||||
if !get_${name}(cx, obj, this, JSJitGetterCallArgs { _base: temp.handle_mut().into() }) {
|
if !get_${name}::<D>(cx, obj, this, JSJitGetterCallArgs { _base: temp.handle_mut().into() }) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
if !JS_DefineProperty(cx, result,
|
if !JS_DefineProperty(cx, result,
|
||||||
|
@ -3691,7 +3693,7 @@ class CGDefineProxyHandler(CGAbstractMethod):
|
||||||
assert descriptor.proxy
|
assert descriptor.proxy
|
||||||
CGAbstractMethod.__init__(self, descriptor, 'DefineProxyHandler',
|
CGAbstractMethod.__init__(self, descriptor, 'DefineProxyHandler',
|
||||||
'*const libc::c_void', [],
|
'*const libc::c_void', [],
|
||||||
pub=True, unsafe=True)
|
pub=True, unsafe=True, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def define(self):
|
def define(self):
|
||||||
return CGAbstractMethod.define(self)
|
return CGAbstractMethod.define(self)
|
||||||
|
@ -3711,7 +3713,7 @@ class CGDefineProxyHandler(CGAbstractMethod):
|
||||||
customSetPrototype = 'None'
|
customSetPrototype = 'None'
|
||||||
if self.descriptor.isMaybeCrossOriginObject():
|
if self.descriptor.isMaybeCrossOriginObject():
|
||||||
customGetPrototypeIfOrdinary = 'Some(proxyhandler::maybe_cross_origin_get_prototype_if_ordinary_rawcx)'
|
customGetPrototypeIfOrdinary = 'Some(proxyhandler::maybe_cross_origin_get_prototype_if_ordinary_rawcx)'
|
||||||
customGetPrototype = 'Some(getPrototype)'
|
customGetPrototype = 'Some(getPrototype::<D>)'
|
||||||
customSetPrototype = 'Some(proxyhandler::maybe_cross_origin_set_prototype_rawcx)'
|
customSetPrototype = 'Some(proxyhandler::maybe_cross_origin_set_prototype_rawcx)'
|
||||||
# The base class `BaseProxyHandler`'s `setImmutablePrototype` (not to be
|
# The base class `BaseProxyHandler`'s `setImmutablePrototype` (not to be
|
||||||
# confused with ECMAScript's `[[SetImmutablePrototype]]`) always fails.
|
# confused with ECMAScript's `[[SetImmutablePrototype]]`) always fails.
|
||||||
|
@ -4096,13 +4098,13 @@ class CGAbstractStaticBindingMethod(CGAbstractMethod):
|
||||||
function to do the rest of the work. This function should return a
|
function to do the rest of the work. This function should return a
|
||||||
CGThing which is already properly indented.
|
CGThing which is already properly indented.
|
||||||
"""
|
"""
|
||||||
def __init__(self, descriptor, name):
|
def __init__(self, descriptor, name, templateArgs=None):
|
||||||
args = [
|
args = [
|
||||||
Argument('*mut JSContext', 'cx'),
|
Argument('*mut JSContext', 'cx'),
|
||||||
Argument('libc::c_uint', 'argc'),
|
Argument('libc::c_uint', 'argc'),
|
||||||
Argument('*mut JSVal', 'vp'),
|
Argument('*mut JSVal', 'vp'),
|
||||||
]
|
]
|
||||||
CGAbstractMethod.__init__(self, descriptor, name, "bool", args, extern=True)
|
CGAbstractMethod.__init__(self, descriptor, name, "bool", args, extern=True, templateArgs=templateArgs)
|
||||||
self.exposureSet = descriptor.interface.exposureSet
|
self.exposureSet = descriptor.interface.exposureSet
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
|
@ -4141,7 +4143,7 @@ class CGSpecializedMethod(CGAbstractExternMethod):
|
||||||
Argument('RawHandleObject', '_obj'),
|
Argument('RawHandleObject', '_obj'),
|
||||||
Argument('*mut libc::c_void', 'this'),
|
Argument('*mut libc::c_void', 'this'),
|
||||||
Argument('*const JSJitMethodCallArgs', 'args')]
|
Argument('*const JSJitMethodCallArgs', 'args')]
|
||||||
CGAbstractExternMethod.__init__(self, descriptor, name, 'bool', args)
|
CGAbstractExternMethod.__init__(self, descriptor, name, 'bool', args, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
nativeName = CGSpecializedMethod.makeNativeName(self.descriptor,
|
nativeName = CGSpecializedMethod.makeNativeName(self.descriptor,
|
||||||
|
@ -4178,12 +4180,12 @@ class CGMethodPromiseWrapper(CGAbstractExternMethod):
|
||||||
Argument('RawHandleObject', '_obj'),
|
Argument('RawHandleObject', '_obj'),
|
||||||
Argument('*mut libc::c_void', 'this'),
|
Argument('*mut libc::c_void', 'this'),
|
||||||
Argument('*const JSJitMethodCallArgs', 'args')]
|
Argument('*const JSJitMethodCallArgs', 'args')]
|
||||||
CGAbstractExternMethod.__init__(self, descriptor, name, 'bool', args)
|
CGAbstractExternMethod.__init__(self, descriptor, name, 'bool', args, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
return CGGeneric(fill(
|
return CGGeneric(fill(
|
||||||
"""
|
"""
|
||||||
let ok = ${methodName}(${args});
|
let ok = ${methodName}::<D>(${args});
|
||||||
if ok {
|
if ok {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -4213,12 +4215,12 @@ class CGGetterPromiseWrapper(CGAbstractExternMethod):
|
||||||
Argument('RawHandleObject', '_obj'),
|
Argument('RawHandleObject', '_obj'),
|
||||||
Argument('*mut libc::c_void', 'this'),
|
Argument('*mut libc::c_void', 'this'),
|
||||||
Argument('JSJitGetterCallArgs', 'args')]
|
Argument('JSJitGetterCallArgs', 'args')]
|
||||||
CGAbstractExternMethod.__init__(self, descriptor, name, 'bool', args)
|
CGAbstractExternMethod.__init__(self, descriptor, name, 'bool', args, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
return CGGeneric(fill(
|
return CGGeneric(fill(
|
||||||
"""
|
"""
|
||||||
let ok = ${methodName}(${args});
|
let ok = ${methodName}::<D>(${args});
|
||||||
if ok {
|
if ok {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -4261,7 +4263,7 @@ class CGDefaultToJSONMethod(CGSpecializedMethod):
|
||||||
|
|
||||||
parents = len(jsonDescriptors) - 1
|
parents = len(jsonDescriptors) - 1
|
||||||
form = """
|
form = """
|
||||||
if !${parentclass}CollectJSONAttributes(cx, _obj, this, result.handle()) {
|
if !${parentclass}CollectJSONAttributes::<D>(cx, _obj, this, result.handle()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
"""
|
"""
|
||||||
|
@ -4283,7 +4285,7 @@ class CGStaticMethod(CGAbstractStaticBindingMethod):
|
||||||
def __init__(self, descriptor, method):
|
def __init__(self, descriptor, method):
|
||||||
self.method = method
|
self.method = method
|
||||||
name = method.identifier.name
|
name = method.identifier.name
|
||||||
CGAbstractStaticBindingMethod.__init__(self, descriptor, name)
|
CGAbstractStaticBindingMethod.__init__(self, descriptor, name, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def generate_code(self):
|
def generate_code(self):
|
||||||
nativeName = CGSpecializedMethod.makeNativeName(self.descriptor,
|
nativeName = CGSpecializedMethod.makeNativeName(self.descriptor,
|
||||||
|
@ -4306,7 +4308,7 @@ class CGSpecializedGetter(CGAbstractExternMethod):
|
||||||
Argument('RawHandleObject', '_obj'),
|
Argument('RawHandleObject', '_obj'),
|
||||||
Argument('*mut libc::c_void', 'this'),
|
Argument('*mut libc::c_void', 'this'),
|
||||||
Argument('JSJitGetterCallArgs', 'args')]
|
Argument('JSJitGetterCallArgs', 'args')]
|
||||||
CGAbstractExternMethod.__init__(self, descriptor, name, "bool", args)
|
CGAbstractExternMethod.__init__(self, descriptor, name, "bool", args, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
nativeName = CGSpecializedGetter.makeNativeName(self.descriptor,
|
nativeName = CGSpecializedGetter.makeNativeName(self.descriptor,
|
||||||
|
@ -4339,7 +4341,7 @@ class CGStaticGetter(CGAbstractStaticBindingMethod):
|
||||||
def __init__(self, descriptor, attr):
|
def __init__(self, descriptor, attr):
|
||||||
self.attr = attr
|
self.attr = attr
|
||||||
name = f'get_{attr.identifier.name}'
|
name = f'get_{attr.identifier.name}'
|
||||||
CGAbstractStaticBindingMethod.__init__(self, descriptor, name)
|
CGAbstractStaticBindingMethod.__init__(self, descriptor, name, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def generate_code(self):
|
def generate_code(self):
|
||||||
nativeName = CGSpecializedGetter.makeNativeName(self.descriptor,
|
nativeName = CGSpecializedGetter.makeNativeName(self.descriptor,
|
||||||
|
@ -4363,7 +4365,7 @@ class CGSpecializedSetter(CGAbstractExternMethod):
|
||||||
Argument('RawHandleObject', 'obj'),
|
Argument('RawHandleObject', 'obj'),
|
||||||
Argument('*mut libc::c_void', 'this'),
|
Argument('*mut libc::c_void', 'this'),
|
||||||
Argument('JSJitSetterCallArgs', 'args')]
|
Argument('JSJitSetterCallArgs', 'args')]
|
||||||
CGAbstractExternMethod.__init__(self, descriptor, name, "bool", args)
|
CGAbstractExternMethod.__init__(self, descriptor, name, "bool", args, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
nativeName = CGSpecializedSetter.makeNativeName(self.descriptor,
|
nativeName = CGSpecializedSetter.makeNativeName(self.descriptor,
|
||||||
|
@ -4390,7 +4392,7 @@ class CGStaticSetter(CGAbstractStaticBindingMethod):
|
||||||
def __init__(self, descriptor, attr):
|
def __init__(self, descriptor, attr):
|
||||||
self.attr = attr
|
self.attr = attr
|
||||||
name = f'set_{attr.identifier.name}'
|
name = f'set_{attr.identifier.name}'
|
||||||
CGAbstractStaticBindingMethod.__init__(self, descriptor, name)
|
CGAbstractStaticBindingMethod.__init__(self, descriptor, name, templateArgs=["D: DomTypes"])
|
||||||
|
|
||||||
def generate_code(self):
|
def generate_code(self):
|
||||||
nativeName = CGSpecializedSetter.makeNativeName(self.descriptor,
|
nativeName = CGSpecializedSetter.makeNativeName(self.descriptor,
|
||||||
|
@ -4502,7 +4504,7 @@ class CGMemberJITInfo(CGThing):
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
""",
|
""",
|
||||||
opValue=f"Some({opName})",
|
opValue=f"Some({opName}::<D>)",
|
||||||
name=self.descriptor.name,
|
name=self.descriptor.name,
|
||||||
depth=self.descriptor.interface.inheritanceDepth(),
|
depth=self.descriptor.interface.inheritanceDepth(),
|
||||||
opType=opType,
|
opType=opType,
|
||||||
|
@ -4530,7 +4532,7 @@ class CGMemberJITInfo(CGThing):
|
||||||
$*{argTypesDecl}
|
$*{argTypesDecl}
|
||||||
static ${infoName}: ThreadUnsafeOnceLock<JSTypedMethodJitInfo> = ThreadUnsafeOnceLock::new();
|
static ${infoName}: ThreadUnsafeOnceLock<JSTypedMethodJitInfo> = ThreadUnsafeOnceLock::new();
|
||||||
|
|
||||||
pub(crate) fn init_${infoName}() {
|
pub(crate) fn init_${infoName}<D: DomTypes>() {
|
||||||
${infoName}.set(JSTypedMethodJitInfo {
|
${infoName}.set(JSTypedMethodJitInfo {
|
||||||
base: ${jitInfoInit},
|
base: ${jitInfoInit},
|
||||||
argTypes: &${argTypes} as *const _ as *const JSJitInfo_ArgType,
|
argTypes: &${argTypes} as *const _ as *const JSJitInfo_ArgType,
|
||||||
|
@ -4545,7 +4547,7 @@ class CGMemberJITInfo(CGThing):
|
||||||
return f"""
|
return f"""
|
||||||
static {infoName}: ThreadUnsafeOnceLock<JSJitInfo> = ThreadUnsafeOnceLock::new();
|
static {infoName}: ThreadUnsafeOnceLock<JSJitInfo> = ThreadUnsafeOnceLock::new();
|
||||||
|
|
||||||
pub(crate) fn init_{infoName}() {{
|
pub(crate) fn init_{infoName}<D: DomTypes>() {{
|
||||||
{infoName}.set({jitInfoInitializer(False)});
|
{infoName}.set({jitInfoInitializer(False)});
|
||||||
}}"""
|
}}"""
|
||||||
|
|
||||||
|
@ -4823,10 +4825,10 @@ class CGStaticMethodJitinfo(CGGeneric):
|
||||||
f"""
|
f"""
|
||||||
static {method.identifier.name}_methodinfo: ThreadUnsafeOnceLock<JSJitInfo> = ThreadUnsafeOnceLock::new();
|
static {method.identifier.name}_methodinfo: ThreadUnsafeOnceLock<JSJitInfo> = ThreadUnsafeOnceLock::new();
|
||||||
|
|
||||||
pub(crate) fn init_{method.identifier.name}_methodinfo() {{
|
pub(crate) fn init_{method.identifier.name}_methodinfo<D: DomTypes>() {{
|
||||||
{method.identifier.name}_methodinfo.set(JSJitInfo {{
|
{method.identifier.name}_methodinfo.set(JSJitInfo {{
|
||||||
__bindgen_anon_1: JSJitInfo__bindgen_ty_1 {{
|
__bindgen_anon_1: JSJitInfo__bindgen_ty_1 {{
|
||||||
staticMethod: Some({method.identifier.name})
|
staticMethod: Some({method.identifier.name}::<D>)
|
||||||
}},
|
}},
|
||||||
__bindgen_anon_2: JSJitInfo__bindgen_ty_2 {{
|
__bindgen_anon_2: JSJitInfo__bindgen_ty_2 {{
|
||||||
protoID: PrototypeList::ID::Last as u16,
|
protoID: PrototypeList::ID::Last as u16,
|
||||||
|
@ -6303,7 +6305,7 @@ class CGDOMJSProxyHandler_getPrototype(CGAbstractExternMethod):
|
||||||
def __init__(self, descriptor):
|
def __init__(self, descriptor):
|
||||||
args = [Argument('*mut JSContext', 'cx'), Argument('RawHandleObject', 'proxy'),
|
args = [Argument('*mut JSContext', 'cx'), Argument('RawHandleObject', 'proxy'),
|
||||||
Argument('RawMutableHandleObject', 'proto')]
|
Argument('RawMutableHandleObject', 'proto')]
|
||||||
CGAbstractExternMethod.__init__(self, descriptor, "getPrototype", "bool", args)
|
CGAbstractExternMethod.__init__(self, descriptor, "getPrototype", "bool", args, templateArgs=["D: DomTypes"])
|
||||||
assert descriptor.isMaybeCrossOriginObject()
|
assert descriptor.isMaybeCrossOriginObject()
|
||||||
self.descriptor = descriptor
|
self.descriptor = descriptor
|
||||||
|
|
||||||
|
@ -6311,7 +6313,7 @@ class CGDOMJSProxyHandler_getPrototype(CGAbstractExternMethod):
|
||||||
return dedent(
|
return dedent(
|
||||||
"""
|
"""
|
||||||
let cx = SafeJSContext::from_ptr(cx);
|
let cx = SafeJSContext::from_ptr(cx);
|
||||||
proxyhandler::maybe_cross_origin_get_prototype(cx, proxy, GetProtoObject, proto)
|
proxyhandler::maybe_cross_origin_get_prototype::<D>(cx, proxy, GetProtoObject, proto)
|
||||||
""")
|
""")
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
|
@ -6667,8 +6669,8 @@ class CGInitStatics(CGThing):
|
||||||
arrays = [getattr(properties, name) for name in all_names]
|
arrays = [getattr(properties, name) for name in all_names]
|
||||||
nonempty = map(lambda x: x.variableName(), filter(lambda x: x.length() != 0, arrays))
|
nonempty = map(lambda x: x.variableName(), filter(lambda x: x.length() != 0, arrays))
|
||||||
specs = [[
|
specs = [[
|
||||||
f'init_{name}_specs();',
|
f'init_{name}_specs::<D>();',
|
||||||
f'init_{name}_prefs();',
|
f'init_{name}_prefs::<D>();',
|
||||||
] for name in nonempty]
|
] for name in nonempty]
|
||||||
flat_specs = [x for xs in specs for x in xs]
|
flat_specs = [x for xs in specs for x in xs]
|
||||||
specs = '\n'.join(flat_specs)
|
specs = '\n'.join(flat_specs)
|
||||||
|
@ -6690,13 +6692,13 @@ class CGInitStatics(CGThing):
|
||||||
relevantMethods
|
relevantMethods
|
||||||
)
|
)
|
||||||
|
|
||||||
methods = [f'{module}::init_{internal(m)}_methodinfo();' for m in relevantMethods]
|
methods = [f'{module}::init_{internal(m)}_methodinfo::<D>();' for m in relevantMethods]
|
||||||
getters = [
|
getters = [
|
||||||
f'init_{internal(m)}_getterinfo();'
|
f'init_{internal(m)}_getterinfo::<D>();'
|
||||||
for m in descriptor.interface.members if m.isAttr() and not m.isStatic()
|
for m in descriptor.interface.members if m.isAttr() and not m.isStatic()
|
||||||
]
|
]
|
||||||
setters = [
|
setters = [
|
||||||
f'init_{internal(m)}_setterinfo();'
|
f'init_{internal(m)}_setterinfo::<D>();'
|
||||||
for m in descriptor.interface.members
|
for m in descriptor.interface.members
|
||||||
if m.isAttr() and (
|
if m.isAttr() and (
|
||||||
not m.readonly
|
not m.readonly
|
||||||
|
@ -6708,9 +6710,9 @@ class CGInitStatics(CGThing):
|
||||||
getters = '\n'.join(getters)
|
getters = '\n'.join(getters)
|
||||||
setters = '\n'.join(setters)
|
setters = '\n'.join(setters)
|
||||||
crossorigin = [
|
crossorigin = [
|
||||||
"init_sCrossOriginMethods();",
|
"init_sCrossOriginMethods::<D>();",
|
||||||
"init_sCrossOriginAttributes();",
|
"init_sCrossOriginAttributes::<D>();",
|
||||||
"init_cross_origin_properties();"
|
"init_cross_origin_properties::<D>();"
|
||||||
] if descriptor.isMaybeCrossOriginObject() else []
|
] if descriptor.isMaybeCrossOriginObject() else []
|
||||||
crossorigin_joined = '\n'.join(crossorigin)
|
crossorigin_joined = '\n'.join(crossorigin)
|
||||||
interface = (
|
interface = (
|
||||||
|
@ -6729,7 +6731,7 @@ class CGInitStatics(CGThing):
|
||||||
)
|
)
|
||||||
|
|
||||||
self.code = f"""
|
self.code = f"""
|
||||||
pub(crate) fn init_statics() {{
|
pub(crate) fn init_statics<D: DomTypes>() {{
|
||||||
{interface}
|
{interface}
|
||||||
{nonproxy}
|
{nonproxy}
|
||||||
{methods}
|
{methods}
|
||||||
|
@ -7315,13 +7317,13 @@ class CGInitAllStatics(CGAbstractMethod):
|
||||||
descriptors = (config.getDescriptors(isCallback=False, register=True)
|
descriptors = (config.getDescriptors(isCallback=False, register=True)
|
||||||
+ config.getDescriptors(isCallback=True, hasInterfaceObject=True, register=True))
|
+ config.getDescriptors(isCallback=True, hasInterfaceObject=True, register=True))
|
||||||
CGAbstractMethod.__init__(self, None, 'InitAllStatics', 'void', [],
|
CGAbstractMethod.__init__(self, None, 'InitAllStatics', 'void', [],
|
||||||
pub=True, docs=docs)
|
pub=True, docs=docs, templateArgs=["D: DomTypes"])
|
||||||
self.descriptors = descriptors
|
self.descriptors = descriptors
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
return CGList([
|
return CGList([
|
||||||
CGGeneric(f" Bindings::{toBindingModuleFileFromDescriptor(desc)}::{toBindingNamespace(desc.name)}"
|
CGGeneric(f" Bindings::{toBindingModuleFileFromDescriptor(desc)}::{toBindingNamespace(desc.name)}"
|
||||||
"::init_statics();")
|
"::init_statics::<D>();")
|
||||||
for desc in self.descriptors
|
for desc in self.descriptors
|
||||||
], "\n")
|
], "\n")
|
||||||
|
|
||||||
|
@ -7330,14 +7332,14 @@ class CGRegisterProxyHandlersMethod(CGAbstractMethod):
|
||||||
def __init__(self, descriptors):
|
def __init__(self, descriptors):
|
||||||
docs = "Create the global vtables used by the generated DOM bindings to implement JS proxies."
|
docs = "Create the global vtables used by the generated DOM bindings to implement JS proxies."
|
||||||
CGAbstractMethod.__init__(self, None, 'RegisterProxyHandlers', 'void', [],
|
CGAbstractMethod.__init__(self, None, 'RegisterProxyHandlers', 'void', [],
|
||||||
unsafe=True, pub=True, docs=docs)
|
unsafe=True, pub=True, docs=docs, templateArgs=["D: DomTypes"])
|
||||||
self.descriptors = descriptors
|
self.descriptors = descriptors
|
||||||
|
|
||||||
def definition_body(self):
|
def definition_body(self):
|
||||||
return CGList([
|
return CGList([
|
||||||
CGGeneric(f"proxy_handlers::{desc.name}.store(\n"
|
CGGeneric(f"proxy_handlers::{desc.name}.store(\n"
|
||||||
f" Bindings::{toBindingModuleFile(desc.name)}::{toBindingNamespace(desc.name)}"
|
f" Bindings::{toBindingModuleFile(desc.name)}::{toBindingNamespace(desc.name)}"
|
||||||
"::DefineProxyHandler() as *mut _,\n"
|
"::DefineProxyHandler::<D>() as *mut _,\n"
|
||||||
" std::sync::atomic::Ordering::Release,\n"
|
" std::sync::atomic::Ordering::Release,\n"
|
||||||
");")
|
");")
|
||||||
for desc in self.descriptors
|
for desc in self.descriptors
|
||||||
|
@ -7359,7 +7361,6 @@ class CGRegisterProxyHandlers(CGThing):
|
||||||
f"{body}}}\n"
|
f"{body}}}\n"
|
||||||
),
|
),
|
||||||
CGRegisterProxyHandlersMethod(descriptors),
|
CGRegisterProxyHandlersMethod(descriptors),
|
||||||
CGInitAllStatics(config),
|
|
||||||
], "\n")
|
], "\n")
|
||||||
|
|
||||||
def define(self):
|
def define(self):
|
||||||
|
@ -8290,10 +8291,12 @@ class GlobalGenRoots():
|
||||||
# TODO - Generate the methods we want
|
# TODO - Generate the methods we want
|
||||||
code = CGList([
|
code = CGList([
|
||||||
CGRegisterProxyHandlers(config),
|
CGRegisterProxyHandlers(config),
|
||||||
|
CGInitAllStatics(config),
|
||||||
], "\n")
|
], "\n")
|
||||||
|
|
||||||
return CGImports(code, descriptors=[], callbacks=[], dictionaries=[], enums=[], typedefs=[], imports=[
|
return CGImports(code, descriptors=[], callbacks=[], dictionaries=[], enums=[], typedefs=[], imports=[
|
||||||
'crate::dom::bindings::codegen::Bindings',
|
'crate::dom::bindings::codegen::Bindings',
|
||||||
|
'crate::DomTypes',
|
||||||
], config=config)
|
], config=config)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
|
|
|
@ -245,6 +245,7 @@ class Descriptor(DescriptorProvider):
|
||||||
self.path = desc.get('path', pathDefault)
|
self.path = desc.get('path', pathDefault)
|
||||||
self.inRealmMethods = [name for name in desc.get('inRealms', [])]
|
self.inRealmMethods = [name for name in desc.get('inRealms', [])]
|
||||||
self.canGcMethods = [name for name in desc.get('canGc', [])]
|
self.canGcMethods = [name for name in desc.get('canGc', [])]
|
||||||
|
self.additionalTraits = [name for name in desc.get('additionalTraits', [])]
|
||||||
self.bindingPath = f"{getModuleFromObject(self.interface)}::{ifaceName}_Binding"
|
self.bindingPath = f"{getModuleFromObject(self.interface)}::{ifaceName}_Binding"
|
||||||
self.outerObjectHook = desc.get('outerObjectHook', 'None')
|
self.outerObjectHook = desc.get('outerObjectHook', 'None')
|
||||||
self.proxy = False
|
self.proxy = False
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue