/* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ function IteratorIdentity() { return this; } var LegacyIteratorWrapperMap = new std_WeakMap(); function LegacyIteratorNext(arg) { var iter = callFunction(std_WeakMap_get, LegacyIteratorWrapperMap, this); try { return { value: callContentFunction(iter.next, iter, arg), done: false }; } catch (e) { if (e instanceof std_StopIteration) return { value: undefined, done: true }; throw e; } } function LegacyIteratorThrow(exn) { var iter = callFunction(std_WeakMap_get, LegacyIteratorWrapperMap, this); try { return { value: callContentFunction(iter.throw, iter, exn), done: false }; } catch (e) { if (e instanceof std_StopIteration) return { value: undefined, done: true }; throw e; } } function LegacyIterator(iter) { callFunction(std_WeakMap_set, LegacyIteratorWrapperMap, this, iter); } function LegacyGeneratorIterator(iter) { callFunction(std_WeakMap_set, LegacyIteratorWrapperMap, this, iter); } var LegacyIteratorsInitialized = std_Object_create(null); function InitLegacyIterators() { var props = std_Object_create(null); props.next = std_Object_create(null); props.next.value = LegacyIteratorNext; props.next.enumerable = false; props.next.configurable = true; props.next.writable = true; props[std_iterator] = std_Object_create(null); props[std_iterator].value = IteratorIdentity; props[std_iterator].enumerable = false; props[std_iterator].configurable = true; props[std_iterator].writable = true; var LegacyIteratorProto = std_Object_create(GetIteratorPrototype(), props); MakeConstructible(LegacyIterator, LegacyIteratorProto); props.throw = std_Object_create(null); props.throw.value = LegacyIteratorThrow; props.throw.enumerable = false; props.throw.configurable = true; props.throw.writable = true; var LegacyGeneratorIteratorProto = std_Object_create(GetIteratorPrototype(), props); MakeConstructible(LegacyGeneratorIterator, LegacyGeneratorIteratorProto); LegacyIteratorsInitialized.initialized = true; } function NewLegacyIterator(iter, wrapper) { if (!LegacyIteratorsInitialized.initialized) InitLegacyIterators(); return new wrapper(iter); } function LegacyIteratorShim() { return NewLegacyIterator(ToObject(this), LegacyIterator); } function LegacyGeneratorIteratorShim() { return NewLegacyIterator(ToObject(this), LegacyGeneratorIterator); } // 7.4.8 CreateListIterator() function CreateListIterator(array) { let iterator = NewListIterator(); UnsafeSetReservedSlot(iterator, ITERATOR_SLOT_TARGET, array); UnsafeSetReservedSlot(iterator, ITERATOR_SLOT_NEXT_INDEX, 0); // 7.4.8.1 ListIterator next() // The spec requires that we use a new next function per iterator object. let next = function() { if (!IsObject(this) || !IsListIterator(this)) return callFunction(CallListIteratorMethodIfWrapped, this, "ListIteratorNext"); if (ActiveFunction() !== UnsafeGetReservedSlot(this, ITERATOR_SLOT_NEXT_METHOD)) ThrowTypeError(JSMSG_INCOMPATIBLE_METHOD, "next", "method", ToString(this)); let array = UnsafeGetObjectFromReservedSlot(this, ITERATOR_SLOT_TARGET); let index = UnsafeGetReservedSlot(this, ITERATOR_SLOT_NEXT_INDEX); if (index >= ToLength(array.length)) { UnsafeSetReservedSlot(this, ITERATOR_SLOT_NEXT_INDEX, 1/0); return { value: undefined, done: true }; } UnsafeSetReservedSlot(this, ITERATOR_SLOT_NEXT_INDEX, index + 1); return { value: array[index], done: false }; }; UnsafeSetReservedSlot(iterator, ITERATOR_SLOT_NEXT_METHOD, next); iterator.next = next; iterator[std_iterator] = ListIteratorIdentity; return iterator; } function ListIteratorIdentity() { if (!IsObject(this) || !IsListIterator(this)) return callFunction(CallListIteratorMethodIfWrapped, this, "ListIteratorIdentity"); return this; }