Spaces:
Paused
Paused
| ; | |
| // Returns "Type(value) is Object" in ES terminology. | |
| function isObject(value) { | |
| return (typeof value === "object" && value !== null) || typeof value === "function"; | |
| } | |
| const call = Function.call.bind(Function.call); | |
| // Like `Object.assign`, but using `[[GetOwnProperty]]` and `[[DefineOwnProperty]]` | |
| // instead of `[[Get]]` and `[[Set]]` and only allowing objects | |
| function define(target, source) { | |
| for (const key of Reflect.ownKeys(source)) { | |
| const descriptor = Reflect.getOwnPropertyDescriptor(source, key); | |
| if (descriptor && !Reflect.defineProperty(target, key, descriptor)) { | |
| throw new TypeError(`Cannot redefine property: ${String(key)}`); | |
| } | |
| } | |
| } | |
| function newObjectInRealm(globalObject, object) { | |
| const ctorRegistry = initCtorRegistry(globalObject); | |
| return Object.defineProperties( | |
| Object.create(ctorRegistry["%Object.prototype%"]), | |
| Object.getOwnPropertyDescriptors(object) | |
| ); | |
| } | |
| const wrapperSymbol = Symbol("wrapper"); | |
| const implSymbol = Symbol("impl"); | |
| const sameObjectCaches = Symbol("SameObject caches"); | |
| const ctorRegistrySymbol = Symbol.for("[webidl2js] constructor registry"); | |
| const AsyncIteratorPrototype = Object.getPrototypeOf(Object.getPrototypeOf(async function* () {}).prototype); | |
| function initCtorRegistry(globalObject) { | |
| if (Object.hasOwn(globalObject, ctorRegistrySymbol)) { | |
| return globalObject[ctorRegistrySymbol]; | |
| } | |
| const ctorRegistry = Object.create(null); | |
| // In addition to registering all the WebIDL2JS-generated types in the constructor registry, | |
| // we also register a few intrinsics that we make use of in generated code, since they are not | |
| // easy to grab from the globalObject variable. | |
| ctorRegistry["%Object.prototype%"] = globalObject.Object.prototype; | |
| ctorRegistry["%IteratorPrototype%"] = Object.getPrototypeOf( | |
| Object.getPrototypeOf(new globalObject.Array()[Symbol.iterator]()) | |
| ); | |
| try { | |
| ctorRegistry["%AsyncIteratorPrototype%"] = Object.getPrototypeOf( | |
| Object.getPrototypeOf( | |
| globalObject.eval("(async function* () {})").prototype | |
| ) | |
| ); | |
| } catch { | |
| ctorRegistry["%AsyncIteratorPrototype%"] = AsyncIteratorPrototype; | |
| } | |
| globalObject[ctorRegistrySymbol] = ctorRegistry; | |
| return ctorRegistry; | |
| } | |
| function getSameObject(wrapper, prop, creator) { | |
| if (!wrapper[sameObjectCaches]) { | |
| wrapper[sameObjectCaches] = Object.create(null); | |
| } | |
| if (prop in wrapper[sameObjectCaches]) { | |
| return wrapper[sameObjectCaches][prop]; | |
| } | |
| wrapper[sameObjectCaches][prop] = creator(); | |
| return wrapper[sameObjectCaches][prop]; | |
| } | |
| function wrapperForImpl(impl) { | |
| return impl ? impl[wrapperSymbol] : null; | |
| } | |
| function implForWrapper(wrapper) { | |
| return wrapper ? wrapper[implSymbol] : null; | |
| } | |
| function tryWrapperForImpl(impl) { | |
| const wrapper = wrapperForImpl(impl); | |
| return wrapper ? wrapper : impl; | |
| } | |
| function tryImplForWrapper(wrapper) { | |
| const impl = implForWrapper(wrapper); | |
| return impl ? impl : wrapper; | |
| } | |
| const iterInternalSymbol = Symbol("internal"); | |
| function isArrayIndexPropName(P) { | |
| if (typeof P !== "string") { | |
| return false; | |
| } | |
| const i = P >>> 0; | |
| if (i === 2 ** 32 - 1) { | |
| return false; | |
| } | |
| const s = `${i}`; | |
| if (P !== s) { | |
| return false; | |
| } | |
| return true; | |
| } | |
| const arrayBufferByteLengthGetter = | |
| Object.getOwnPropertyDescriptor(ArrayBuffer.prototype, "byteLength").get; | |
| function isArrayBuffer(value) { | |
| try { | |
| arrayBufferByteLengthGetter.call(value); | |
| return true; | |
| } catch { | |
| return false; | |
| } | |
| } | |
| const sharedArrayBufferByteLengthGetter = | |
| Object.getOwnPropertyDescriptor(SharedArrayBuffer.prototype, "byteLength").get; | |
| function isSharedArrayBuffer(value) { | |
| try { | |
| sharedArrayBufferByteLengthGetter.call(value); | |
| return true; | |
| } catch { | |
| return false; | |
| } | |
| } | |
| function iteratorResult([key, value], kind) { | |
| let result; | |
| switch (kind) { | |
| case "key": | |
| result = key; | |
| break; | |
| case "value": | |
| result = value; | |
| break; | |
| case "key+value": | |
| result = [key, value]; | |
| break; | |
| } | |
| return { value: result, done: false }; | |
| } | |
| function ordinarySetWithOwnDescriptor(target, property, value, receiver, ownDesc) { | |
| if (ownDesc === undefined) { | |
| const parent = Reflect.getPrototypeOf(target); | |
| if (parent !== null) { | |
| return Reflect.set(parent, property, value, receiver); | |
| } | |
| ownDesc = { writable: true, enumerable: true, configurable: true, value: undefined }; | |
| } | |
| if (isDataDescriptor(ownDesc)) { | |
| if (!ownDesc.writable) { | |
| return false; | |
| } | |
| if (!isObject(receiver)) { | |
| return false; | |
| } | |
| const existingDesc = Reflect.getOwnPropertyDescriptor(receiver, property); | |
| if (existingDesc !== undefined) { | |
| if (isAccessorDescriptor(existingDesc)) { | |
| return false; | |
| } | |
| if (existingDesc.writable === false) { | |
| return false; | |
| } | |
| const valueDesc = { value }; | |
| return Reflect.defineProperty(receiver, property, valueDesc); | |
| } | |
| return Reflect.defineProperty( | |
| receiver, | |
| property, | |
| { value, writable: true, enumerable: true, configurable: true } | |
| ); | |
| } | |
| const setter = ownDesc.set; | |
| if (setter === undefined) { | |
| return false; | |
| } | |
| call(setter, receiver, value); | |
| return true; | |
| } | |
| function isDataDescriptor(desc) { | |
| return Object.hasOwn(desc, "value") || Object.hasOwn(desc, "writable"); | |
| } | |
| function isAccessorDescriptor(desc) { | |
| return Object.hasOwn(desc, "get") || Object.hasOwn(desc, "set"); | |
| } | |
| const supportsPropertyIndex = Symbol("supports property index"); | |
| const supportedPropertyIndices = Symbol("supported property indices"); | |
| const supportsPropertyName = Symbol("supports property name"); | |
| const supportedPropertyNames = Symbol("supported property names"); | |
| const indexedGet = Symbol("indexed property get"); | |
| const indexedSetNew = Symbol("indexed property set new"); | |
| const indexedSetExisting = Symbol("indexed property set existing"); | |
| const namedGet = Symbol("named property get"); | |
| const namedSetNew = Symbol("named property set new"); | |
| const namedSetExisting = Symbol("named property set existing"); | |
| const namedDelete = Symbol("named property delete"); | |
| const asyncIteratorNext = Symbol("async iterator get the next iteration result"); | |
| const asyncIteratorReturn = Symbol("async iterator return steps"); | |
| const asyncIteratorInit = Symbol("async iterator initialization steps"); | |
| const asyncIteratorEOI = Symbol("async iterator end of iteration"); | |
| module.exports = exports = { | |
| isObject, | |
| define, | |
| newObjectInRealm, | |
| wrapperSymbol, | |
| implSymbol, | |
| getSameObject, | |
| ctorRegistrySymbol, | |
| initCtorRegistry, | |
| wrapperForImpl, | |
| implForWrapper, | |
| tryWrapperForImpl, | |
| tryImplForWrapper, | |
| iterInternalSymbol, | |
| isArrayBuffer, | |
| isSharedArrayBuffer, | |
| isArrayIndexPropName, | |
| supportsPropertyIndex, | |
| supportedPropertyIndices, | |
| supportsPropertyName, | |
| supportedPropertyNames, | |
| indexedGet, | |
| indexedSetNew, | |
| indexedSetExisting, | |
| namedGet, | |
| namedSetNew, | |
| namedSetExisting, | |
| namedDelete, | |
| asyncIteratorNext, | |
| asyncIteratorReturn, | |
| asyncIteratorInit, | |
| asyncIteratorEOI, | |
| iteratorResult, | |
| ordinarySetWithOwnDescriptor | |
| }; | |