Line data Source code
1 : /* THIS FILE IS AUTOGENERATED FROM ServiceWorker.webidl BY Codegen.py - DO NOT EDIT */
2 :
3 : #include "EventHandlerBinding.h"
4 : #include "EventTargetBinding.h"
5 : #include "ServiceWorkerBinding.h"
6 : #include "WrapperFactory.h"
7 : #include "jsapi.h"
8 : #include "mozilla/OwningNonNull.h"
9 : #include "mozilla/dom/BindingUtils.h"
10 : #include "mozilla/dom/DOMJSClass.h"
11 : #include "mozilla/dom/NonRefcountedDOMObject.h"
12 : #include "mozilla/dom/Nullable.h"
13 : #include "mozilla/dom/XrayExpandoClass.h"
14 : #include "mozilla/dom/workers/bindings/ServiceWorker.h"
15 :
16 : namespace mozilla {
17 : namespace dom {
18 :
19 : namespace ServiceWorkerStateValues {
20 : extern const EnumEntry strings[6] = {
21 : {"installing", 10},
22 : {"installed", 9},
23 : {"activating", 10},
24 : {"activated", 9},
25 : {"redundant", 9},
26 : { nullptr, 0 }
27 : };
28 : } // namespace ServiceWorkerStateValues
29 :
30 : bool
31 0 : ToJSValue(JSContext* aCx, ServiceWorkerState aArgument, JS::MutableHandle<JS::Value> aValue)
32 : {
33 0 : MOZ_ASSERT(uint32_t(aArgument) < ArrayLength(ServiceWorkerStateValues::strings));
34 : JSString* resultStr =
35 0 : JS_NewStringCopyN(aCx, ServiceWorkerStateValues::strings[uint32_t(aArgument)].value,
36 0 : ServiceWorkerStateValues::strings[uint32_t(aArgument)].length);
37 0 : if (!resultStr) {
38 0 : return false;
39 : }
40 0 : aValue.setString(resultStr);
41 0 : return true;
42 : }
43 :
44 :
45 : namespace ServiceWorkerBinding {
46 :
47 : static_assert(IsRefcounted<NativeType>::value == IsRefcounted<EventTargetBinding::NativeType>::value,
48 : "Can't inherit from an interface with a different ownership model.");
49 :
50 : static bool
51 0 : get_scriptURL(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, JSJitGetterCallArgs args)
52 : {
53 0 : DOMString result;
54 0 : self->GetScriptURL(result);
55 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
56 0 : if (!xpc::NonVoidStringToJsval(cx, result, args.rval())) {
57 0 : return false;
58 : }
59 0 : return true;
60 : }
61 :
62 : static const JSJitInfo scriptURL_getterinfo = {
63 : { (JSJitGetterOp)get_scriptURL },
64 : { prototypes::id::ServiceWorker },
65 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
66 : JSJitInfo::Getter,
67 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
68 : JSVAL_TYPE_STRING, /* returnType. Not relevant for setters. */
69 : false, /* isInfallible. False in setters. */
70 : false, /* isMovable. Not relevant for setters. */
71 : false, /* isEliminatable. Not relevant for setters. */
72 : false, /* isAlwaysInSlot. Only relevant for getters. */
73 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
74 : false, /* isTypedMethod. Only relevant for methods. */
75 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
76 : };
77 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
78 : static_assert(0 < 1, "There is no slot for us");
79 :
80 : static bool
81 0 : get_state(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, JSJitGetterCallArgs args)
82 : {
83 0 : ServiceWorkerState result(self->State());
84 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
85 0 : if (!ToJSValue(cx, result, args.rval())) {
86 0 : return false;
87 : }
88 0 : return true;
89 : }
90 :
91 : static const JSJitInfo state_getterinfo = {
92 : { (JSJitGetterOp)get_state },
93 : { prototypes::id::ServiceWorker },
94 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
95 : JSJitInfo::Getter,
96 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
97 : JSVAL_TYPE_STRING, /* returnType. Not relevant for setters. */
98 : false, /* isInfallible. False in setters. */
99 : false, /* isMovable. Not relevant for setters. */
100 : false, /* isEliminatable. Not relevant for setters. */
101 : false, /* isAlwaysInSlot. Only relevant for getters. */
102 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
103 : false, /* isTypedMethod. Only relevant for methods. */
104 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
105 : };
106 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
107 : static_assert(0 < 1, "There is no slot for us");
108 :
109 : static bool
110 0 : get_onstatechange(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, JSJitGetterCallArgs args)
111 : {
112 0 : RefPtr<EventHandlerNonNull> result(self->GetOnstatechange());
113 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
114 0 : if (result) {
115 0 : args.rval().setObjectOrNull(GetCallbackFromCallbackObject(result));
116 0 : if (!MaybeWrapObjectOrNullValue(cx, args.rval())) {
117 0 : return false;
118 : }
119 0 : return true;
120 : } else {
121 0 : args.rval().setNull();
122 0 : return true;
123 : }
124 : }
125 :
126 : static bool
127 0 : set_onstatechange(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, JSJitSetterCallArgs args)
128 : {
129 0 : RootedCallback<RefPtr<binding_detail::FastEventHandlerNonNull>> arg0(cx);
130 0 : if (args[0].isObject()) {
131 : { // scope for tempRoot
132 0 : JS::Rooted<JSObject*> tempRoot(cx, &args[0].toObject());
133 0 : arg0 = new binding_detail::FastEventHandlerNonNull(tempRoot);
134 : }
135 : } else {
136 0 : arg0 = nullptr;
137 : }
138 0 : self->SetOnstatechange(Constify(arg0));
139 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
140 :
141 0 : return true;
142 : }
143 :
144 : static const JSJitInfo onstatechange_getterinfo = {
145 : { (JSJitGetterOp)get_onstatechange },
146 : { prototypes::id::ServiceWorker },
147 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
148 : JSJitInfo::Getter,
149 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
150 : JSVAL_TYPE_UNKNOWN, /* returnType. Not relevant for setters. */
151 : false, /* isInfallible. False in setters. */
152 : false, /* isMovable. Not relevant for setters. */
153 : false, /* isEliminatable. Not relevant for setters. */
154 : false, /* isAlwaysInSlot. Only relevant for getters. */
155 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
156 : false, /* isTypedMethod. Only relevant for methods. */
157 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
158 : };
159 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
160 : static_assert(0 < 1, "There is no slot for us");
161 : static const JSJitInfo onstatechange_setterinfo = {
162 : { (JSJitGetterOp)set_onstatechange },
163 : { prototypes::id::ServiceWorker },
164 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
165 : JSJitInfo::Setter,
166 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
167 : JSVAL_TYPE_UNDEFINED, /* returnType. Not relevant for setters. */
168 : false, /* isInfallible. False in setters. */
169 : false, /* isMovable. Not relevant for setters. */
170 : false, /* isEliminatable. Not relevant for setters. */
171 : false, /* isAlwaysInSlot. Only relevant for getters. */
172 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
173 : false, /* isTypedMethod. Only relevant for methods. */
174 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
175 : };
176 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
177 : static_assert(0 < 1, "There is no slot for us");
178 :
179 : static bool
180 0 : postMessage(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, const JSJitMethodCallArgs& args)
181 : {
182 0 : if (MOZ_UNLIKELY(args.length() < 1)) {
183 0 : return ThrowErrorMessage(cx, MSG_MISSING_ARGUMENTS, "ServiceWorker.postMessage");
184 : }
185 0 : JS::Rooted<JS::Value> arg0(cx);
186 0 : arg0 = args[0];
187 0 : binding_detail::AutoSequence<JSObject*> arg1;
188 0 : SequenceRooter<JSObject*> arg1_holder(cx, &arg1);
189 0 : if (args.hasDefined(1)) {
190 0 : if (args[1].isObject()) {
191 0 : JS::ForOfIterator iter(cx);
192 0 : if (!iter.init(args[1], JS::ForOfIterator::AllowNonIterable)) {
193 0 : return false;
194 : }
195 0 : if (!iter.valueIsIterable()) {
196 0 : ThrowErrorMessage(cx, MSG_NOT_SEQUENCE, "Argument 2 of ServiceWorker.postMessage");
197 0 : return false;
198 : }
199 0 : binding_detail::AutoSequence<JSObject*> &arr = arg1;
200 0 : JS::Rooted<JS::Value> temp(cx);
201 : while (true) {
202 : bool done;
203 0 : if (!iter.next(&temp, &done)) {
204 0 : return false;
205 : }
206 0 : if (done) {
207 0 : break;
208 : }
209 0 : JSObject** slotPtr = arr.AppendElement(mozilla::fallible);
210 0 : if (!slotPtr) {
211 0 : JS_ReportOutOfMemory(cx);
212 0 : return false;
213 : }
214 0 : JSObject*& slot = *slotPtr;
215 0 : if (temp.isObject()) {
216 0 : slot = &temp.toObject();
217 : } else {
218 0 : ThrowErrorMessage(cx, MSG_NOT_OBJECT, "Element of argument 2 of ServiceWorker.postMessage");
219 0 : return false;
220 : }
221 0 : }
222 : } else {
223 0 : ThrowErrorMessage(cx, MSG_NOT_SEQUENCE, "Argument 2 of ServiceWorker.postMessage");
224 0 : return false;
225 : }
226 : } else {
227 : /* Array is already empty; nothing to do */
228 : }
229 0 : binding_detail::FastErrorResult rv;
230 0 : self->PostMessage(cx, arg0, Constify(arg1), rv);
231 0 : if (MOZ_UNLIKELY(rv.MaybeSetPendingException(cx))) {
232 0 : return false;
233 : }
234 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
235 0 : args.rval().setUndefined();
236 0 : return true;
237 : }
238 :
239 : static const JSJitInfo postMessage_methodinfo = {
240 : { (JSJitGetterOp)postMessage },
241 : { prototypes::id::ServiceWorker },
242 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
243 : JSJitInfo::Method,
244 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
245 : JSVAL_TYPE_UNDEFINED, /* returnType. Not relevant for setters. */
246 : false, /* isInfallible. False in setters. */
247 : false, /* isMovable. Not relevant for setters. */
248 : false, /* isEliminatable. Not relevant for setters. */
249 : false, /* isAlwaysInSlot. Only relevant for getters. */
250 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
251 : false, /* isTypedMethod. Only relevant for methods. */
252 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
253 : };
254 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
255 : static_assert(0 < 1, "There is no slot for us");
256 :
257 : static bool
258 0 : get_onerror(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, JSJitGetterCallArgs args)
259 : {
260 0 : RefPtr<EventHandlerNonNull> result(self->GetOnerror());
261 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
262 0 : if (result) {
263 0 : args.rval().setObjectOrNull(GetCallbackFromCallbackObject(result));
264 0 : if (!MaybeWrapObjectOrNullValue(cx, args.rval())) {
265 0 : return false;
266 : }
267 0 : return true;
268 : } else {
269 0 : args.rval().setNull();
270 0 : return true;
271 : }
272 : }
273 :
274 : static bool
275 0 : set_onerror(JSContext* cx, JS::Handle<JSObject*> obj, mozilla::dom::workers::ServiceWorker* self, JSJitSetterCallArgs args)
276 : {
277 0 : RootedCallback<RefPtr<binding_detail::FastEventHandlerNonNull>> arg0(cx);
278 0 : if (args[0].isObject()) {
279 : { // scope for tempRoot
280 0 : JS::Rooted<JSObject*> tempRoot(cx, &args[0].toObject());
281 0 : arg0 = new binding_detail::FastEventHandlerNonNull(tempRoot);
282 : }
283 : } else {
284 0 : arg0 = nullptr;
285 : }
286 0 : self->SetOnerror(Constify(arg0));
287 0 : MOZ_ASSERT(!JS_IsExceptionPending(cx));
288 :
289 0 : return true;
290 : }
291 :
292 : static const JSJitInfo onerror_getterinfo = {
293 : { (JSJitGetterOp)get_onerror },
294 : { prototypes::id::ServiceWorker },
295 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
296 : JSJitInfo::Getter,
297 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
298 : JSVAL_TYPE_UNKNOWN, /* returnType. Not relevant for setters. */
299 : false, /* isInfallible. False in setters. */
300 : false, /* isMovable. Not relevant for setters. */
301 : false, /* isEliminatable. Not relevant for setters. */
302 : false, /* isAlwaysInSlot. Only relevant for getters. */
303 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
304 : false, /* isTypedMethod. Only relevant for methods. */
305 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
306 : };
307 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
308 : static_assert(0 < 1, "There is no slot for us");
309 : static const JSJitInfo onerror_setterinfo = {
310 : { (JSJitGetterOp)set_onerror },
311 : { prototypes::id::ServiceWorker },
312 : { PrototypeTraits<prototypes::id::ServiceWorker>::Depth },
313 : JSJitInfo::Setter,
314 : JSJitInfo::AliasEverything, /* aliasSet. Not relevant for setters. */
315 : JSVAL_TYPE_UNDEFINED, /* returnType. Not relevant for setters. */
316 : false, /* isInfallible. False in setters. */
317 : false, /* isMovable. Not relevant for setters. */
318 : false, /* isEliminatable. Not relevant for setters. */
319 : false, /* isAlwaysInSlot. Only relevant for getters. */
320 : false, /* isLazilyCachedInSlot. Only relevant for getters. */
321 : false, /* isTypedMethod. Only relevant for methods. */
322 : 0 /* Reserved slot index, if we're stored in a slot, else 0. */
323 : };
324 : static_assert(0 <= JSJitInfo::maxSlotIndex, "We won't fit");
325 : static_assert(0 < 1, "There is no slot for us");
326 :
327 : static bool
328 0 : _addProperty(JSContext* cx, JS::Handle<JSObject*> obj, JS::Handle<jsid> id, JS::Handle<JS::Value> val)
329 : {
330 0 : mozilla::dom::workers::ServiceWorker* self = UnwrapPossiblyNotInitializedDOMObject<mozilla::dom::workers::ServiceWorker>(obj);
331 : // We don't want to preserve if we don't have a wrapper, and we
332 : // obviously can't preserve if we're not initialized.
333 0 : if (self && self->GetWrapperPreserveColor()) {
334 0 : PreserveWrapper(self);
335 : }
336 0 : return true;
337 : }
338 :
339 : static void
340 0 : _finalize(js::FreeOp* fop, JSObject* obj)
341 : {
342 0 : mozilla::dom::workers::ServiceWorker* self = UnwrapPossiblyNotInitializedDOMObject<mozilla::dom::workers::ServiceWorker>(obj);
343 0 : if (self) {
344 0 : ClearWrapper(self, self, obj);
345 0 : AddForDeferredFinalization<mozilla::dom::workers::ServiceWorker>(self);
346 : }
347 0 : }
348 :
349 : static void
350 0 : _objectMoved(JSObject* obj, const JSObject* old)
351 : {
352 0 : mozilla::dom::workers::ServiceWorker* self = UnwrapPossiblyNotInitializedDOMObject<mozilla::dom::workers::ServiceWorker>(obj);
353 0 : if (self) {
354 0 : UpdateWrapper(self, self, obj, old);
355 : }
356 0 : }
357 :
358 : // We deliberately use brace-elision to make Visual Studio produce better initalization code.
359 : #if defined(__clang__)
360 : #pragma clang diagnostic push
361 : #pragma clang diagnostic ignored "-Wmissing-braces"
362 : #endif
363 : static const JSFunctionSpec sMethods_specs[] = {
364 : JS_FNSPEC("postMessage", GenericBindingMethod, reinterpret_cast<const JSJitInfo*>(&postMessage_methodinfo), 1, JSPROP_ENUMERATE, nullptr),
365 : JS_FS_END
366 : };
367 : #if defined(__clang__)
368 : #pragma clang diagnostic pop
369 : #endif
370 :
371 :
372 : // Can't be const because the pref-enabled boolean needs to be writable
373 : static Prefable<const JSFunctionSpec> sMethods[] = {
374 : { nullptr, &sMethods_specs[0] },
375 : { nullptr, nullptr }
376 : };
377 :
378 : static_assert(1 <= 1ull << NUM_BITS_PROPERTY_INFO_PREF_INDEX,
379 : "We have a prefable index that is >= (1 << NUM_BITS_PROPERTY_INFO_PREF_INDEX)");
380 : static_assert(1 <= 1ull << NUM_BITS_PROPERTY_INFO_SPEC_INDEX,
381 : "We have a spec index that is >= (1 << NUM_BITS_PROPERTY_INFO_SPEC_INDEX)");
382 :
383 : // We deliberately use brace-elision to make Visual Studio produce better initalization code.
384 : #if defined(__clang__)
385 : #pragma clang diagnostic push
386 : #pragma clang diagnostic ignored "-Wmissing-braces"
387 : #endif
388 : static const JSPropertySpec sAttributes_specs[] = {
389 : { "scriptURL", JSPROP_SHARED | JSPROP_ENUMERATE, GenericBindingGetter, &scriptURL_getterinfo, nullptr, nullptr },
390 : { "state", JSPROP_SHARED | JSPROP_ENUMERATE, GenericBindingGetter, &state_getterinfo, nullptr, nullptr },
391 : { "onstatechange", JSPROP_SHARED | JSPROP_ENUMERATE, GenericBindingGetter, &onstatechange_getterinfo, GenericBindingSetter, &onstatechange_setterinfo },
392 : { "onerror", JSPROP_SHARED | JSPROP_ENUMERATE, GenericBindingGetter, &onerror_getterinfo, GenericBindingSetter, &onerror_setterinfo },
393 : { nullptr, 0, nullptr, nullptr, nullptr, nullptr }
394 : };
395 : #if defined(__clang__)
396 : #pragma clang diagnostic pop
397 : #endif
398 :
399 :
400 : // Can't be const because the pref-enabled boolean needs to be writable
401 : static Prefable<const JSPropertySpec> sAttributes[] = {
402 : { nullptr, &sAttributes_specs[0] },
403 : { nullptr, nullptr }
404 : };
405 :
406 : static_assert(1 <= 1ull << NUM_BITS_PROPERTY_INFO_PREF_INDEX,
407 : "We have a prefable index that is >= (1 << NUM_BITS_PROPERTY_INFO_PREF_INDEX)");
408 : static_assert(4 <= 1ull << NUM_BITS_PROPERTY_INFO_SPEC_INDEX,
409 : "We have a spec index that is >= (1 << NUM_BITS_PROPERTY_INFO_SPEC_INDEX)");
410 :
411 :
412 : static uint16_t sNativeProperties_sortedPropertyIndices[5];
413 : static PropertyInfo sNativeProperties_propertyInfos[5];
414 :
415 : static const NativePropertiesN<2> sNativeProperties = {
416 : false, 0,
417 : false, 0,
418 : true, 0 /* sMethods */,
419 : true, 1 /* sAttributes */,
420 : false, 0,
421 : false, 0,
422 : false, 0,
423 : -1,
424 : 5,
425 : sNativeProperties_sortedPropertyIndices,
426 : {
427 : { sMethods, &sNativeProperties_propertyInfos[0] },
428 : { sAttributes, &sNativeProperties_propertyInfos[1] }
429 : }
430 : };
431 : static_assert(5 < 1ull << CHAR_BIT * sizeof(sNativeProperties.propertyInfoCount),
432 : "We have a property info count that is oversized");
433 :
434 : static const DOMIfaceAndProtoJSClass sInterfaceObjectClass = {
435 : {
436 : "Function",
437 : JSCLASS_IS_DOMIFACEANDPROTOJSCLASS | JSCLASS_HAS_RESERVED_SLOTS(DOM_INTERFACE_SLOTS_BASE),
438 : &sBoringInterfaceObjectClassClassOps,
439 : JS_NULL_CLASS_SPEC,
440 : JS_NULL_CLASS_EXT,
441 : &sInterfaceObjectClassObjectOps
442 : },
443 : eInterface,
444 : true,
445 : prototypes::id::ServiceWorker,
446 : PrototypeTraits<prototypes::id::ServiceWorker>::Depth,
447 : sNativePropertyHooks,
448 : "function ServiceWorker() {\n [native code]\n}",
449 : EventTargetBinding::GetConstructorObject
450 : };
451 :
452 : static const DOMIfaceAndProtoJSClass sPrototypeClass = {
453 : {
454 : "ServiceWorkerPrototype",
455 : JSCLASS_IS_DOMIFACEANDPROTOJSCLASS | JSCLASS_HAS_RESERVED_SLOTS(DOM_INTERFACE_PROTO_SLOTS_BASE),
456 : JS_NULL_CLASS_OPS,
457 : JS_NULL_CLASS_SPEC,
458 : JS_NULL_CLASS_EXT,
459 : JS_NULL_OBJECT_OPS
460 : },
461 : eInterfacePrototype,
462 : false,
463 : prototypes::id::ServiceWorker,
464 : PrototypeTraits<prototypes::id::ServiceWorker>::Depth,
465 : sNativePropertyHooks,
466 : "[object ServiceWorkerPrototype]",
467 : EventTargetBinding::GetProtoObject
468 : };
469 :
470 : bool
471 1 : ConstructorEnabled(JSContext* aCx, JS::Handle<JSObject*> aObj)
472 : {
473 1 : return mozilla::dom::workers::ServiceWorkerVisible(aCx, aObj);
474 : }
475 :
476 : JSObject*
477 0 : DefineDOMInterface(JSContext* aCx, JS::Handle<JSObject*> aGlobal, JS::Handle<jsid> id, bool aDefineOnGlobal)
478 : {
479 0 : return GetConstructorObjectHandle(aCx, aDefineOnGlobal);
480 : }
481 :
482 : static const js::ClassOps sClassOps = {
483 : _addProperty, /* addProperty */
484 : nullptr, /* delProperty */
485 : nullptr, /* getProperty */
486 : nullptr, /* setProperty */
487 : nullptr, /* enumerate */
488 : nullptr, /* newEnumerate */
489 : nullptr, /* resolve */
490 : nullptr, /* mayResolve */
491 : _finalize, /* finalize */
492 : nullptr, /* call */
493 : nullptr, /* hasInstance */
494 : nullptr, /* construct */
495 : nullptr, /* trace */
496 : };
497 :
498 : static const js::ClassExtension sClassExtension = {
499 : nullptr, /* weakmapKeyDelegateOp */
500 : _objectMoved /* objectMovedOp */
501 : };
502 :
503 : static const DOMJSClass sClass = {
504 : { "ServiceWorker",
505 : JSCLASS_IS_DOMJSCLASS | JSCLASS_FOREGROUND_FINALIZE | JSCLASS_HAS_RESERVED_SLOTS(1),
506 : &sClassOps,
507 : JS_NULL_CLASS_SPEC,
508 : &sClassExtension,
509 : JS_NULL_OBJECT_OPS
510 : },
511 : { prototypes::id::EventTarget, prototypes::id::ServiceWorker, prototypes::id::_ID_Count, prototypes::id::_ID_Count, prototypes::id::_ID_Count, prototypes::id::_ID_Count, prototypes::id::_ID_Count, prototypes::id::_ID_Count },
512 : IsBaseOf<nsISupports, mozilla::dom::workers::ServiceWorker >::value,
513 : sNativePropertyHooks,
514 : FindAssociatedGlobalForNative<mozilla::dom::workers::ServiceWorker>::Get,
515 : GetProtoObjectHandle,
516 : GetCCParticipant<mozilla::dom::workers::ServiceWorker>::Get()
517 : };
518 : static_assert(1 == DOM_INSTANCE_RESERVED_SLOTS,
519 : "Must have the right minimal number of reserved slots.");
520 : static_assert(1 >= 1,
521 : "Must have enough reserved slots.");
522 :
523 : const JSClass*
524 0 : GetJSClass()
525 : {
526 0 : return sClass.ToJSClass();
527 : }
528 :
529 : bool
530 0 : Wrap(JSContext* aCx, mozilla::dom::workers::ServiceWorker* aObject, nsWrapperCache* aCache, JS::Handle<JSObject*> aGivenProto, JS::MutableHandle<JSObject*> aReflector)
531 : {
532 : MOZ_ASSERT(static_cast<mozilla::dom::workers::ServiceWorker*>(aObject) ==
533 : reinterpret_cast<mozilla::dom::workers::ServiceWorker*>(aObject),
534 : "Multiple inheritance for mozilla::dom::workers::ServiceWorker is broken.");
535 : MOZ_ASSERT(static_cast<mozilla::dom::EventTarget*>(aObject) ==
536 : reinterpret_cast<mozilla::dom::EventTarget*>(aObject),
537 : "Multiple inheritance for mozilla::dom::EventTarget is broken.");
538 0 : MOZ_ASSERT(ToSupportsIsCorrect(aObject));
539 0 : MOZ_ASSERT_IF(aGivenProto, js::IsObjectInContextCompartment(aGivenProto, aCx));
540 0 : MOZ_ASSERT(!aCache->GetWrapper(),
541 : "You should probably not be using Wrap() directly; use "
542 : "GetOrCreateDOMReflector instead");
543 :
544 0 : MOZ_ASSERT(ToSupportsIsOnPrimaryInheritanceChain(aObject, aCache),
545 : "nsISupports must be on our primary inheritance chain");
546 :
547 0 : JS::Rooted<JSObject*> global(aCx, FindAssociatedGlobal(aCx, aObject->GetParentObject()));
548 0 : if (!global) {
549 0 : return false;
550 : }
551 0 : MOZ_ASSERT(JS_IsGlobalObject(global));
552 0 : MOZ_ASSERT(JS::ObjectIsNotGray(global));
553 :
554 : // That might have ended up wrapping us already, due to the wonders
555 : // of XBL. Check for that, and bail out as needed.
556 0 : aReflector.set(aCache->GetWrapper());
557 0 : if (aReflector) {
558 : #ifdef DEBUG
559 0 : binding_detail::AssertReflectorHasGivenProto(aCx, aReflector, aGivenProto);
560 : #endif // DEBUG
561 0 : return true;
562 : }
563 :
564 0 : JSAutoCompartment ac(aCx, global);
565 0 : JS::Handle<JSObject*> canonicalProto = GetProtoObjectHandle(aCx);
566 0 : if (!canonicalProto) {
567 0 : return false;
568 : }
569 0 : JS::Rooted<JSObject*> proto(aCx);
570 0 : if (aGivenProto) {
571 0 : proto = aGivenProto;
572 : // Unfortunately, while aGivenProto was in the compartment of aCx
573 : // coming in, we changed compartments to that of "parent" so may need
574 : // to wrap the proto here.
575 0 : if (js::GetContextCompartment(aCx) != js::GetObjectCompartment(proto)) {
576 0 : if (!JS_WrapObject(aCx, &proto)) {
577 0 : return false;
578 : }
579 : }
580 : } else {
581 0 : proto = canonicalProto;
582 : }
583 :
584 0 : BindingJSObjectCreator<mozilla::dom::workers::ServiceWorker> creator(aCx);
585 0 : creator.CreateObject(aCx, sClass.ToJSClass(), proto, aObject, aReflector);
586 0 : if (!aReflector) {
587 0 : return false;
588 : }
589 :
590 0 : aCache->SetWrapper(aReflector);
591 0 : creator.InitializationSucceeded();
592 :
593 0 : MOZ_ASSERT(aCache->GetWrapperPreserveColor() &&
594 : aCache->GetWrapperPreserveColor() == aReflector);
595 : // If proto != canonicalProto, we have to preserve our wrapper;
596 : // otherwise we won't be able to properly recreate it later, since
597 : // we won't know what proto to use. Note that we don't check
598 : // aGivenProto here, since it's entirely possible (and even
599 : // somewhat common) to have a non-null aGivenProto which is the
600 : // same as canonicalProto.
601 0 : if (proto != canonicalProto) {
602 0 : PreserveWrapper(aObject);
603 : }
604 :
605 0 : return true;
606 : }
607 :
608 : const NativePropertyHooks sNativePropertyHooks[] = { {
609 : nullptr,
610 : nullptr,
611 : nullptr,
612 : { sNativeProperties.Upcast(), nullptr },
613 : prototypes::id::ServiceWorker,
614 : constructors::id::ServiceWorker,
615 : EventTargetBinding::sNativePropertyHooks,
616 : &DefaultXrayExpandoObjectClass
617 : } };
618 :
619 : void
620 0 : CreateInterfaceObjects(JSContext* aCx, JS::Handle<JSObject*> aGlobal, ProtoAndIfaceCache& aProtoAndIfaceCache, bool aDefineOnGlobal)
621 : {
622 0 : JS::Handle<JSObject*> parentProto(EventTargetBinding::GetProtoObjectHandle(aCx));
623 0 : if (!parentProto) {
624 0 : return;
625 : }
626 :
627 0 : JS::Handle<JSObject*> constructorProto(EventTargetBinding::GetConstructorObjectHandle(aCx));
628 0 : if (!constructorProto) {
629 0 : return;
630 : }
631 :
632 : static bool sIdsInited = false;
633 0 : if (!sIdsInited && NS_IsMainThread()) {
634 0 : if (!InitIds(aCx, sNativeProperties.Upcast())) {
635 0 : return;
636 : }
637 0 : sIdsInited = true;
638 : }
639 :
640 0 : JS::Heap<JSObject*>* protoCache = &aProtoAndIfaceCache.EntrySlotOrCreate(prototypes::id::ServiceWorker);
641 0 : JS::Heap<JSObject*>* interfaceCache = &aProtoAndIfaceCache.EntrySlotOrCreate(constructors::id::ServiceWorker);
642 0 : dom::CreateInterfaceObjects(aCx, aGlobal, parentProto,
643 : &sPrototypeClass.mBase, protoCache,
644 : constructorProto, &sInterfaceObjectClass.mBase, 0, nullptr,
645 : interfaceCache,
646 : sNativeProperties.Upcast(),
647 : nullptr,
648 : "ServiceWorker", aDefineOnGlobal,
649 : nullptr,
650 0 : false);
651 : }
652 :
653 : JS::Handle<JSObject*>
654 0 : GetProtoObjectHandle(JSContext* aCx)
655 : {
656 : /* Get the interface prototype object for this class. This will create the
657 : object as needed. */
658 0 : bool aDefineOnGlobal = true;
659 :
660 : /* Make sure our global is sane. Hopefully we can remove this sometime */
661 0 : JSObject* global = JS::CurrentGlobalOrNull(aCx);
662 0 : if (!(js::GetObjectClass(global)->flags & JSCLASS_DOM_GLOBAL)) {
663 0 : return nullptr;
664 : }
665 :
666 : /* Check to see whether the interface objects are already installed */
667 0 : ProtoAndIfaceCache& protoAndIfaceCache = *GetProtoAndIfaceCache(global);
668 0 : if (!protoAndIfaceCache.HasEntryInSlot(prototypes::id::ServiceWorker)) {
669 0 : JS::Rooted<JSObject*> rootedGlobal(aCx, global);
670 0 : CreateInterfaceObjects(aCx, rootedGlobal, protoAndIfaceCache, aDefineOnGlobal);
671 : }
672 :
673 : /*
674 : * The object might _still_ be null, but that's OK.
675 : *
676 : * Calling fromMarkedLocation() is safe because protoAndIfaceCache is
677 : * traced by TraceProtoAndIfaceCache() and its contents are never
678 : * changed after they have been set.
679 : *
680 : * Calling address() avoids the read read barrier that does gray
681 : * unmarking, but it's not possible for the object to be gray here.
682 : */
683 :
684 0 : const JS::Heap<JSObject*>& entrySlot = protoAndIfaceCache.EntrySlotMustExist(prototypes::id::ServiceWorker);
685 0 : MOZ_ASSERT(JS::ObjectIsNotGray(entrySlot));
686 0 : return JS::Handle<JSObject*>::fromMarkedLocation(entrySlot.address());
687 : }
688 :
689 : JS::Handle<JSObject*>
690 0 : GetConstructorObjectHandle(JSContext* aCx, bool aDefineOnGlobal)
691 : {
692 : /* Get the interface object for this class. This will create the object as
693 : needed. */
694 :
695 : /* Make sure our global is sane. Hopefully we can remove this sometime */
696 0 : JSObject* global = JS::CurrentGlobalOrNull(aCx);
697 0 : if (!(js::GetObjectClass(global)->flags & JSCLASS_DOM_GLOBAL)) {
698 0 : return nullptr;
699 : }
700 :
701 : /* Check to see whether the interface objects are already installed */
702 0 : ProtoAndIfaceCache& protoAndIfaceCache = *GetProtoAndIfaceCache(global);
703 0 : if (!protoAndIfaceCache.HasEntryInSlot(constructors::id::ServiceWorker)) {
704 0 : JS::Rooted<JSObject*> rootedGlobal(aCx, global);
705 0 : CreateInterfaceObjects(aCx, rootedGlobal, protoAndIfaceCache, aDefineOnGlobal);
706 : }
707 :
708 : /*
709 : * The object might _still_ be null, but that's OK.
710 : *
711 : * Calling fromMarkedLocation() is safe because protoAndIfaceCache is
712 : * traced by TraceProtoAndIfaceCache() and its contents are never
713 : * changed after they have been set.
714 : *
715 : * Calling address() avoids the read read barrier that does gray
716 : * unmarking, but it's not possible for the object to be gray here.
717 : */
718 :
719 0 : const JS::Heap<JSObject*>& entrySlot = protoAndIfaceCache.EntrySlotMustExist(constructors::id::ServiceWorker);
720 0 : MOZ_ASSERT(JS::ObjectIsNotGray(entrySlot));
721 0 : return JS::Handle<JSObject*>::fromMarkedLocation(entrySlot.address());
722 : }
723 :
724 : JSObject*
725 0 : GetConstructorObject(JSContext* aCx)
726 : {
727 0 : return GetConstructorObjectHandle(aCx);
728 : }
729 :
730 : } // namespace ServiceWorkerBinding
731 :
732 :
733 :
734 : } // namespace dom
735 : } // namespace mozilla
|