Skip to content

Commit 759ad3e

Browse files
author
bors-servo
authored
Auto merge of #25562 - pshaughn:window-getter, r=<try>
Attempt at window named getter, sharing name_map infrastructure with document named getter I think I have the window named getter working well enough to look at CI results. This has #25548 as a base but also pulls in most of #21869.
2 parents 0dccfd1 + 0d1e16f commit 759ad3e

31 files changed

+941
-183
lines changed

Cargo.lock

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,3 +32,6 @@ mio = { git = "https://github.com/servo/mio.git", branch = "servo" }
3232
winapi = { git = "https://github.com/servo/winapi-rs", branch = "patch-1" }
3333
spirv_cross = { git = "https://github.com/kvark/spirv_cross", branch = "wgpu" }
3434
backtrace = { git = "https://github.com/MeFisto94/backtrace-rs", branch = "fix-strtab-freeing-crash" }
35+
36+
[patch."https://github.com/servo/rust-mozjs"]
37+
mozjs = { git = "https://github.com/jdm/rust-mozjs", branch = "proxyopt2" }

components/script/dom/bindings/codegen/CodegenRust.py

Lines changed: 25 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -2641,7 +2641,7 @@ def CreateBindingJSObject(descriptor):
26412641
rooted!(in(*cx) let private = PrivateValue(raw as *const libc::c_void));
26422642
let obj = NewProxyObject(*cx, handler,
26432643
Handle::from_raw(UndefinedHandleValue),
2644-
proto.get());
2644+
proto.get(), ptr::null(), false);
26452645
assert!(!obj.is_null());
26462646
SetProxyReservedSlot(obj, 0, &private.get());
26472647
rooted!(in(*cx) let obj = obj);\
@@ -3007,6 +3007,14 @@ def definition_body(self):
30073007
%s;
30083008
assert!(!prototype_proto.is_null());""" % getPrototypeProto)]
30093009

3010+
if self.descriptor.hasNamedPropertiesObject():
3011+
assert self.descriptor.isGlobal()
3012+
assert not self.haveUnscopables
3013+
code.append(CGGeneric("""\
3014+
rooted!(in(*cx) let mut prototype_proto_proto = prototype_proto.get());
3015+
dom::types::%s::create_named_properties_object(cx, prototype_proto_proto.handle(), prototype_proto.handle_mut());
3016+
assert!(!prototype_proto.is_null());""" % name))
3017+
30103018
properties = {
30113019
"id": name,
30123020
"unscopables": "unscopable_names" if self.haveUnscopables else "&[]",
@@ -3033,6 +3041,9 @@ def definition_body(self):
30333041

30343042
code.append(CGGeneric("""
30353043
rooted!(in(*cx) let mut prototype = ptr::null_mut::<JSObject>());
3044+
"""))
3045+
3046+
code.append(CGGeneric("""
30363047
create_interface_prototype_object(cx,
30373048
global.into(),
30383049
prototype_proto.handle().into(),
@@ -3042,6 +3053,9 @@ def definition_body(self):
30423053
%(consts)s,
30433054
%(unscopables)s,
30443055
prototype.handle_mut().into());
3056+
""" % proto_properties))
3057+
3058+
code.append(CGGeneric("""
30453059
assert!(!prototype.is_null());
30463060
assert!((*cache)[PrototypeList::ID::%(id)s as usize].is_null());
30473061
(*cache)[PrototypeList::ID::%(id)s as usize] = prototype.get();
@@ -5147,8 +5161,8 @@ def getBody(self):
51475161
attrs = "JSPROP_ENUMERATE"
51485162
if self.descriptor.operations['IndexedSetter'] is None:
51495163
attrs += " | JSPROP_READONLY"
5150-
fillDescriptor = ("desc.value = result_root.get();\n"
5151-
"fill_property_descriptor(MutableHandle::from_raw(desc), proxy.get(), (%s) as u32);\n"
5164+
fillDescriptor = ("fill_property_descriptor(MutableHandle::from_raw(desc), "
5165+
"proxy.get(), result_root.get(), (%s) as u32);\n"
51525166
"return true;" % attrs)
51535167
templateValues = {
51545168
'jsvalRef': 'result_root.handle_mut()',
@@ -5161,8 +5175,7 @@ def getBody(self):
51615175
CGIndenter(CGProxyIndexedGetter(self.descriptor, templateValues)).define() + "\n" +
51625176
"}\n")
51635177

5164-
namedGetter = self.descriptor.operations['NamedGetter']
5165-
if namedGetter:
5178+
if self.descriptor.operations['NamedGetter']:
51665179
attrs = []
51675180
if not self.descriptor.interface.getExtendedAttribute("LegacyUnenumerableNamedProperties"):
51685181
attrs.append("JSPROP_ENUMERATE")
@@ -5172,8 +5185,8 @@ def getBody(self):
51725185
attrs = " | ".join(attrs)
51735186
else:
51745187
attrs = "0"
5175-
fillDescriptor = ("desc.value = result_root.get();\n"
5176-
"fill_property_descriptor(MutableHandle::from_raw(desc), proxy.get(), (%s) as u32);\n"
5188+
fillDescriptor = ("fill_property_descriptor(MutableHandle::from_raw(desc), "
5189+
"proxy.get(), result_root.get(), (%s) as u32);\n"
51775190
"return true;" % attrs)
51785191
templateValues = {
51795192
'jsvalRef': 'result_root.handle_mut()',
@@ -5419,11 +5432,10 @@ def getBody(self):
54195432
" return true;\n" +
54205433
"}\n\n")
54215434

5422-
namedGetter = self.descriptor.operations['NamedGetter']
54235435
condition = "RUST_JSID_IS_STRING(id) || RUST_JSID_IS_INT(id)"
54245436
if indexedGetter:
54255437
condition = "index.is_none() && (%s)" % condition
5426-
if namedGetter:
5438+
if self.descriptor.operations['NamedGetter']:
54275439
named = """\
54285440
if %s {
54295441
let mut has_on_proto = false;
@@ -5506,8 +5518,7 @@ def getBody(self):
55065518
else:
55075519
getIndexedOrExpando = getFromExpando + "\n"
55085520

5509-
namedGetter = self.descriptor.operations['NamedGetter']
5510-
if namedGetter:
5521+
if self.descriptor.operations['NamedGetter']:
55115522
condition = "RUST_JSID_IS_STRING(id) || RUST_JSID_IS_INT(id)"
55125523
# From step 1:
55135524
# If O supports indexed properties and P is an array index, then:
@@ -5859,6 +5870,7 @@ def contains_unsafe_arg(arguments):
58595870
return functools.reduce((lambda x, y: x or y[1] == '*mut JSContext'), arguments, False)
58605871

58615872
methods = []
5873+
58625874
for name, arguments, rettype in members():
58635875
arguments = list(arguments)
58645876
methods.append(CGGeneric("%sfn %s(&self%s) -> %s;\n" % (
@@ -6179,6 +6191,7 @@ def reexportedName(name):
61796191

61806192
defaultToJSONMethod = None
61816193
unscopableNames = []
6194+
61826195
for m in descriptor.interface.members:
61836196
if (m.isMethod() and
61846197
(not m.isIdentifierLess() or m == descriptor.operations["Stringifier"])):
@@ -6214,7 +6227,7 @@ def reexportedName(name):
62146227
elif m.getExtendedAttribute("Replaceable"):
62156228
cgThings.append(CGSpecializedReplaceableSetter(descriptor, m))
62166229

6217-
if (not m.isStatic() and not descriptor.interface.isCallback()):
6230+
if not m.isStatic() and not descriptor.interface.isCallback():
62186231
cgThings.append(CGMemberJITInfo(descriptor, m))
62196232

62206233
if defaultToJSONMethod:

components/script/dom/bindings/codegen/Configuration.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -269,8 +269,10 @@ def addOperation(operation, m):
269269
continue
270270

271271
def addIndexedOrNamedOperation(operation, m):
272-
self.proxy = True
272+
if not self.isGlobal():
273+
self.proxy = True
273274
if m.isIndexed():
275+
assert not self.isGlobal()
274276
operation = 'Indexed' + operation
275277
else:
276278
assert m.isNamed()
@@ -355,6 +357,15 @@ def binaryNameFor(self, name):
355357
def internalNameFor(self, name):
356358
return self._internalNames.get(name, name)
357359

360+
def hasNamedPropertiesObject(self):
361+
if self.interface.isExternal():
362+
return False
363+
364+
return self.isGlobal() and self.supportsNamedProperties()
365+
366+
def supportsNamedProperties(self):
367+
return self.operations['NamedGetter'] is not None
368+
358369
def getExtendedAttributes(self, member, getter=False, setter=False):
359370
def maybeAppendInfallibleToAttrs(attrs, throws):
360371
if throws is None:

components/script/dom/bindings/proxyhandler.rs

Lines changed: 30 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,22 +8,26 @@
88

99
use crate::dom::bindings::conversions::is_dom_proxy;
1010
use crate::dom::bindings::utils::delete_property_by_id;
11+
use crate::script_runtime::JSContext as SafeJSContext;
1112
use js::glue::GetProxyHandlerFamily;
1213
use js::glue::{GetProxyPrivate, SetProxyPrivate};
1314
use js::jsapi::GetStaticPrototype;
1415
use js::jsapi::Handle as RawHandle;
1516
use js::jsapi::HandleId as RawHandleId;
1617
use js::jsapi::HandleObject as RawHandleObject;
1718
use js::jsapi::JS_DefinePropertyById;
19+
use js::jsapi::JS_HasPropertyById;
1820
use js::jsapi::MutableHandleObject as RawMutableHandleObject;
1921
use js::jsapi::ObjectOpResult;
2022
use js::jsapi::{DOMProxyShadowsResult, JSContext, JSObject, PropertyDescriptor};
2123
use js::jsapi::{JSErrNum, SetDOMProxyInformation};
24+
use js::jsval::JSVal;
2225
use js::jsval::ObjectValue;
2326
use js::jsval::UndefinedValue;
27+
use js::rust::wrappers::GetObjectProto;
2428
use js::rust::wrappers::JS_AlreadyHasOwnPropertyById;
2529
use js::rust::wrappers::JS_NewObjectWithGivenProto;
26-
use js::rust::{Handle, HandleObject, MutableHandle, MutableHandleObject};
30+
use js::rust::{Handle, HandleObject, IntoHandle, MutableHandle, MutableHandleObject};
2731
use std::ptr;
2832

2933
/// Determine if this id shadows any existing properties for this proxy.
@@ -163,13 +167,37 @@ pub unsafe fn ensure_expando_object(
163167

164168
/// Set the property descriptor's object to `obj` and set it to enumerable,
165169
/// and writable if `readonly` is true.
166-
pub fn fill_property_descriptor(
170+
pub unsafe fn fill_property_descriptor(
167171
mut desc: MutableHandle<PropertyDescriptor>,
168172
obj: *mut JSObject,
173+
v: JSVal,
169174
attrs: u32,
170175
) {
171176
desc.obj = obj;
177+
desc.value = v;
172178
desc.attrs = attrs;
173179
desc.getter = None;
174180
desc.setter = None;
175181
}
182+
183+
pub fn has_property_on_prototype(
184+
cx: SafeJSContext,
185+
proxy: HandleObject,
186+
id: RawHandleId,
187+
) -> Result<bool, ()> {
188+
unsafe {
189+
rooted!(in(*cx) let mut proto = ptr::null_mut::<JSObject>());
190+
if !GetObjectProto(*cx, proxy, proto.handle_mut()) {
191+
return Err(());
192+
}
193+
if proto.is_null() {
194+
return Ok(false);
195+
}
196+
let mut has = false;
197+
if JS_HasPropertyById(*cx, proto.handle().into_handle(), id, &mut has) {
198+
Ok(has)
199+
} else {
200+
Err(())
201+
}
202+
}
203+
}

0 commit comments

Comments
 (0)