summaryrefslogtreecommitdiff
path: root/Source/JavaScriptCore/builtins
diff options
context:
space:
mode:
Diffstat (limited to 'Source/JavaScriptCore/builtins')
-rw-r--r--Source/JavaScriptCore/builtins/ArrayConstructor.js110
-rw-r--r--Source/JavaScriptCore/builtins/ArrayIteratorPrototype.js60
-rw-r--r--Source/JavaScriptCore/builtins/ArrayPrototype.js663
-rw-r--r--Source/JavaScriptCore/builtins/BuiltinExecutables.cpp131
-rw-r--r--Source/JavaScriptCore/builtins/BuiltinExecutables.h71
-rw-r--r--Source/JavaScriptCore/builtins/BuiltinNames.h124
-rw-r--r--Source/JavaScriptCore/builtins/BuiltinUtils.h54
-rw-r--r--Source/JavaScriptCore/builtins/DatePrototype.js182
-rw-r--r--Source/JavaScriptCore/builtins/FunctionPrototype.js53
-rw-r--r--Source/JavaScriptCore/builtins/GeneratorPrototype.js93
-rw-r--r--Source/JavaScriptCore/builtins/GlobalObject.js66
-rw-r--r--Source/JavaScriptCore/builtins/InspectorInstrumentationObject.js40
-rw-r--r--Source/JavaScriptCore/builtins/InternalPromiseConstructor.js86
-rw-r--r--Source/JavaScriptCore/builtins/IteratorPrototype.js31
-rw-r--r--Source/JavaScriptCore/builtins/MapPrototype.js46
-rw-r--r--Source/JavaScriptCore/builtins/ModuleLoaderObject.js562
-rw-r--r--Source/JavaScriptCore/builtins/NumberPrototype.js47
-rw-r--r--Source/JavaScriptCore/builtins/ObjectConstructor.js46
-rw-r--r--Source/JavaScriptCore/builtins/PromiseConstructor.js139
-rw-r--r--Source/JavaScriptCore/builtins/PromiseOperations.js215
-rw-r--r--Source/JavaScriptCore/builtins/PromisePrototype.js66
-rw-r--r--Source/JavaScriptCore/builtins/ReflectObject.js61
-rw-r--r--Source/JavaScriptCore/builtins/SetPrototype.js46
-rw-r--r--Source/JavaScriptCore/builtins/StringConstructor.js60
-rw-r--r--Source/JavaScriptCore/builtins/StringIteratorPrototype.js64
-rw-r--r--Source/JavaScriptCore/builtins/StringPrototype.js82
-rw-r--r--Source/JavaScriptCore/builtins/TypedArrayConstructor.js181
-rw-r--r--Source/JavaScriptCore/builtins/TypedArrayPrototype.js287
28 files changed, 3666 insertions, 0 deletions
diff --git a/Source/JavaScriptCore/builtins/ArrayConstructor.js b/Source/JavaScriptCore/builtins/ArrayConstructor.js
new file mode 100644
index 000000000..27efc1d95
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/ArrayConstructor.js
@@ -0,0 +1,110 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function of(/* items... */)
+{
+ "use strict";
+
+ var length = arguments.length;
+ // TODO: Need isConstructor(this) instead of typeof "function" check.
+ var array = typeof this === 'function' ? new this(length) : new @Array(length);
+ for (var k = 0; k < length; ++k)
+ @putByValDirect(array, k, arguments[k]);
+ array.length = length;
+ return array;
+}
+
+function from(items /*, mapFn, thisArg */)
+{
+ "use strict";
+
+ var thisObj = this;
+
+ var mapFn = arguments.length > 1 ? arguments[1] : @undefined;
+
+ var thisArg;
+
+ if (mapFn !== @undefined) {
+ if (typeof mapFn !== "function")
+ throw new @TypeError("Array.from requires that the second argument, when provided, be a function");
+
+ if (arguments.length > 2)
+ thisArg = arguments[2];
+ }
+
+ if (items == null)
+ throw new @TypeError("Array.from requires an array-like object - not null or undefined");
+
+ var iteratorMethod = items[@symbolIterator];
+ if (iteratorMethod != null) {
+ if (typeof iteratorMethod !== "function")
+ throw new @TypeError("Array.from requires that the property of the first argument, items[Symbol.iterator], when exists, be a function");
+
+ // TODO: Need isConstructor(thisObj) instead of typeof "function" check.
+ var result = (typeof thisObj === "function") ? @Object(new thisObj()) : [];
+
+ var k = 0;
+ var iterator = iteratorMethod.@call(items);
+
+ // Since for-of loop once more looks up the @@iterator property of a given iterable,
+ // it could be observable if the user defines a getter for @@iterator.
+ // To avoid this situation, we define a wrapper object that @@iterator just returns a given iterator.
+ var wrapper = {
+ [@symbolIterator]() {
+ return iterator;
+ }
+ };
+
+ for (var value of wrapper) {
+ if (mapFn)
+ @putByValDirect(result, k, thisArg === @undefined ? mapFn(value, k) : mapFn.@call(thisArg, value, k));
+ else
+ @putByValDirect(result, k, value);
+ k += 1;
+ }
+
+ result.length = k;
+ return result;
+ }
+
+ var arrayLike = @Object(items);
+ var arrayLikeLength = @toLength(arrayLike.length);
+
+ // TODO: Need isConstructor(thisObj) instead of typeof "function" check.
+ var result = (typeof thisObj === "function") ? @Object(new thisObj(arrayLikeLength)) : new @Array(arrayLikeLength);
+
+ var k = 0;
+ while (k < arrayLikeLength) {
+ var value = arrayLike[k];
+ if (mapFn)
+ @putByValDirect(result, k, thisArg === @undefined ? mapFn(value, k) : mapFn.@call(thisArg, value, k));
+ else
+ @putByValDirect(result, k, value);
+ k += 1;
+ }
+
+ result.length = arrayLikeLength;
+ return result;
+}
diff --git a/Source/JavaScriptCore/builtins/ArrayIteratorPrototype.js b/Source/JavaScriptCore/builtins/ArrayIteratorPrototype.js
new file mode 100644
index 000000000..aa7886c6f
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/ArrayIteratorPrototype.js
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function next()
+{
+ "use strict";
+
+ if (this == null)
+ throw new @TypeError("%ArrayIteratorPrototype%.next requires that |this| not be null or undefined");
+
+ var itemKind = this.@arrayIterationKind;
+ if (itemKind === @undefined)
+ throw new @TypeError("%ArrayIteratorPrototype%.next requires that |this| be an Array Iterator instance");
+
+ var done = true;
+ var value = @undefined;
+
+ var array = this.@iteratedObject;
+ if (array !== @undefined) {
+ var index = this.@arrayIteratorNextIndex;
+ var length = array.length >>> 0;
+ if (index >= length) {
+ this.@iteratedObject = @undefined;
+ } else {
+ this.@arrayIteratorNextIndex = index + 1;
+ done = false;
+ if (itemKind === @arrayIterationKindKey) {
+ value = index;
+ } else if (itemKind === @arrayIterationKindValue) {
+ value = array[index];
+ } else {
+ value = [ index, array[index] ];
+ }
+ }
+ }
+
+ return {done, value};
+}
diff --git a/Source/JavaScriptCore/builtins/ArrayPrototype.js b/Source/JavaScriptCore/builtins/ArrayPrototype.js
new file mode 100644
index 000000000..57c81d7c7
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/ArrayPrototype.js
@@ -0,0 +1,663 @@
+/*
+ * Copyright (C) 2014, 2015 Apple Inc. All rights reserved.
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function reduce(callback /*, initialValue */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.reduce requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.reduce requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.reduce callback must be a function");
+
+ if (length === 0 && arguments.length < 2)
+ throw new @TypeError("reduce of empty array with no initial value");
+
+ var accumulator, k = 0;
+ if (arguments.length > 1)
+ accumulator = arguments[1];
+ else {
+ while (k < length && !(k in array))
+ k += 1;
+ if (k >= length)
+ throw new @TypeError("reduce of empty array with no initial value");
+ accumulator = array[k++];
+ }
+
+ while (k < length) {
+ if (k in array)
+ accumulator = callback.@call(@undefined, accumulator, array[k], k, array);
+ k += 1;
+ }
+ return accumulator;
+}
+
+function reduceRight(callback /*, initialValue */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.reduceRight requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.reduceRight requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.reduceRight callback must be a function");
+
+ if (length === 0 && arguments.length < 2)
+ throw new @TypeError("reduceRight of empty array with no initial value");
+
+ var accumulator, k = length - 1;
+ if (arguments.length > 1)
+ accumulator = arguments[1];
+ else {
+ while (k >= 0 && !(k in array))
+ k -= 1;
+ if (k < 0)
+ throw new @TypeError("reduceRight of empty array with no initial value");
+ accumulator = array[k--];
+ }
+
+ while (k >= 0) {
+ if (k in array)
+ accumulator = callback.@call(@undefined, accumulator, array[k], k, array);
+ k -= 1;
+ }
+ return accumulator;
+}
+
+function every(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.every requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.every requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.every callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ for (var i = 0; i < length; i++) {
+ if (!(i in array))
+ continue;
+ if (!callback.@call(thisArg, array[i], i, array))
+ return false;
+ }
+
+ return true;
+}
+
+function forEach(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.forEach requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.forEach requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.forEach callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ for (var i = 0; i < length; i++) {
+ if (i in array)
+ callback.@call(thisArg, array[i], i, array);
+ }
+}
+
+function filter(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.filter requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.filter requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.filter callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ var result = [];
+ var nextIndex = 0;
+ for (var i = 0; i < length; i++) {
+ if (!(i in array))
+ continue;
+ var current = array[i]
+ if (callback.@call(thisArg, current, i, array)) {
+ @putByValDirect(result, nextIndex, current);
+ ++nextIndex;
+ }
+ }
+ return result;
+}
+
+function map(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.map requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.map requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.map callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ var result = [];
+ result.length = length;
+ var nextIndex = 0;
+ for (var i = 0; i < length; i++) {
+ if (!(i in array))
+ continue;
+ var mappedValue = callback.@call(thisArg, array[i], i, array);
+ @putByValDirect(result, i, mappedValue);
+ }
+ return result;
+}
+
+function some(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.some requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.some requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.some callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ for (var i = 0; i < length; i++) {
+ if (!(i in array))
+ continue;
+ if (callback.@call(thisArg, array[i], i, array))
+ return true;
+ }
+ return false;
+}
+
+function fill(value /* [, start [, end]] */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.fill requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.fill requires that |this| not be undefined");
+ var O = @Object(this);
+ var len = @toLength(O.length);
+ var relativeStart = 0;
+ if (arguments.length > 1 && arguments[1] !== @undefined)
+ relativeStart = arguments[1] | 0;
+ var k = 0;
+ if (relativeStart < 0) {
+ k = len + relativeStart;
+ if (k < 0)
+ k = 0;
+ } else {
+ k = relativeStart;
+ if (k > len)
+ k = len;
+ }
+ var relativeEnd = len;
+ if (arguments.length > 2 && arguments[2] !== @undefined)
+ relativeEnd = arguments[2] | 0;
+ var final = 0;
+ if (relativeEnd < 0) {
+ final = len + relativeEnd;
+ if (final < 0)
+ final = 0;
+ } else {
+ final = relativeEnd;
+ if (final > len)
+ final = len;
+ }
+ for (; k < final; k++)
+ O[k] = value;
+ return O;
+}
+
+function find(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.find requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.find requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.find callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ for (var i = 0; i < length; i++) {
+ var kValue = array[i];
+ if (callback.@call(thisArg, kValue, i, array))
+ return kValue;
+ }
+ return @undefined;
+}
+
+function findIndex(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.findIndex requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.findIndex requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("Array.prototype.findIndex callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ for (var i = 0; i < length; i++) {
+ if (callback.@call(thisArg, array[i], i, array))
+ return i;
+ }
+ return -1;
+}
+
+function includes(searchElement /*, fromIndex*/)
+{
+ "use strict";
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.includes requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.includes requires that |this| not be undefined");
+
+ var array = @Object(this);
+ var length = @toLength(array.length);
+
+ if (length === 0)
+ return false;
+
+ var fromIndex = 0;
+ if (arguments.length > 1 && arguments[1] !== @undefined)
+ fromIndex = arguments[1] | 0;
+
+ var index;
+ if (fromIndex >= 0)
+ index = fromIndex;
+ else
+ index = length + fromIndex;
+
+ if (index < 0)
+ index = 0;
+
+ var currentElement;
+ for (; index < length; ++index) {
+ currentElement = array[index];
+ // Use SameValueZero comparison, rather than just StrictEquals.
+ if (searchElement === currentElement || (searchElement !== searchElement && currentElement !== currentElement))
+ return true;
+ }
+ return false;
+}
+
+function sort(comparator)
+{
+ "use strict";
+
+ function min(a, b)
+ {
+ return a < b ? a : b;
+ }
+
+ function stringComparator(a, b)
+ {
+ var aString = a.string;
+ var bString = b.string;
+
+ var aLength = aString.length;
+ var bLength = bString.length;
+ var length = min(aLength, bLength);
+
+ for (var i = 0; i < length; ++i) {
+ var aCharCode = aString.@charCodeAt(i);
+ var bCharCode = bString.@charCodeAt(i);
+
+ if (aCharCode == bCharCode)
+ continue;
+
+ return aCharCode - bCharCode;
+ }
+
+ return aLength - bLength;
+ }
+
+ // Move undefineds and holes to the end of a sparse array. Result is [values..., undefineds..., holes...].
+ function compactSparse(array, dst, src, length)
+ {
+ var values = [ ];
+ var seen = { };
+ var valueCount = 0;
+ var undefinedCount = 0;
+
+ // Clean up after the in-progress non-sparse compaction that failed.
+ for (var i = dst; i < src; ++i)
+ delete array[i];
+
+ for (var object = array; object; object = @Object.@getPrototypeOf(object)) {
+ var propertyNames = @Object.@getOwnPropertyNames(object);
+ for (var i = 0; i < propertyNames.length; ++i) {
+ var index = propertyNames[i];
+ if (index < length) { // Exclude non-numeric properties and properties past length.
+ if (seen[index]) // Exclude duplicates.
+ continue;
+ seen[index] = 1;
+
+ var value = array[index];
+ delete array[index];
+
+ if (value === @undefined) {
+ ++undefinedCount;
+ continue;
+ }
+
+ array[valueCount++] = value;
+ }
+ }
+ }
+
+ for (var i = valueCount; i < valueCount + undefinedCount; ++i)
+ array[i] = @undefined;
+
+ return valueCount;
+ }
+
+ function compactSlow(array, length)
+ {
+ var holeCount = 0;
+
+ for (var dst = 0, src = 0; src < length; ++src) {
+ if (!(src in array)) {
+ ++holeCount;
+ if (holeCount < 256)
+ continue;
+ return compactSparse(array, dst, src, length);
+ }
+
+ var value = array[src];
+ if (value === @undefined)
+ continue;
+
+ array[dst++] = value;
+ }
+
+ var valueCount = dst;
+ var undefinedCount = length - valueCount - holeCount;
+
+ for (var i = valueCount; i < valueCount + undefinedCount; ++i)
+ array[i] = @undefined;
+
+ for (var i = valueCount + undefinedCount; i < length; ++i)
+ delete array[i];
+
+ return valueCount;
+ }
+
+ // Move undefineds and holes to the end of an array. Result is [values..., undefineds..., holes...].
+ function compact(array, length)
+ {
+ for (var i = 0; i < array.length; ++i) {
+ if (array[i] === @undefined)
+ return compactSlow(array, length);
+ }
+
+ return length;
+ }
+
+ function merge(dst, src, srcIndex, srcEnd, width, comparator)
+ {
+ var left = srcIndex;
+ var leftEnd = min(left + width, srcEnd);
+ var right = leftEnd;
+ var rightEnd = min(right + width, srcEnd);
+
+ for (var dstIndex = left; dstIndex < rightEnd; ++dstIndex) {
+ if (right < rightEnd) {
+ if (left >= leftEnd || comparator(src[right], src[left]) < 0) {
+ dst[dstIndex] = src[right++];
+ continue;
+ }
+ }
+
+ dst[dstIndex] = src[left++];
+ }
+ }
+
+ function mergeSort(array, valueCount, comparator)
+ {
+ var buffer = [ ];
+ buffer.length = valueCount;
+
+ var dst = buffer;
+ var src = array;
+ for (var width = 1; width < valueCount; width *= 2) {
+ for (var srcIndex = 0; srcIndex < valueCount; srcIndex += 2 * width)
+ merge(dst, src, srcIndex, valueCount, width, comparator);
+
+ var tmp = src;
+ src = dst;
+ dst = tmp;
+ }
+
+ if (src != array) {
+ for(var i = 0; i < valueCount; i++)
+ array[i] = src[i];
+ }
+ }
+
+ function bucketSort(array, dst, bucket, depth)
+ {
+ if (bucket.length < 32 || depth > 32) {
+ mergeSort(bucket, bucket.length, stringComparator);
+ for (var i = 0; i < bucket.length; ++i)
+ array[dst++] = bucket[i].value;
+ return dst;
+ }
+
+ var buckets = [ ];
+ for (var i = 0; i < bucket.length; ++i) {
+ var entry = bucket[i];
+ var string = entry.string;
+ if (string.length == depth) {
+ array[dst++] = entry.value;
+ continue;
+ }
+
+ var c = string.@charCodeAt(depth);
+ if (!buckets[c])
+ buckets[c] = [ ];
+ buckets[c][buckets[c].length] = entry;
+ }
+
+ for (var i = 0; i < buckets.length; ++i) {
+ if (!buckets[i])
+ continue;
+ dst = bucketSort(array, dst, buckets[i], depth + 1);
+ }
+
+ return dst;
+ }
+
+ function comparatorSort(array, comparator)
+ {
+ var length = array.length >>> 0;
+
+ // For compatibility with Firefox and Chrome, do nothing observable
+ // to the target array if it has 0 or 1 sortable properties.
+ if (length < 2)
+ return;
+
+ var valueCount = compact(array, length);
+ mergeSort(array, valueCount, comparator);
+ }
+
+ function stringSort(array)
+ {
+ var length = array.length >>> 0;
+
+ // For compatibility with Firefox and Chrome, do nothing observable
+ // to the target array if it has 0 or 1 sortable properties.
+ if (length < 2)
+ return;
+
+ var valueCount = compact(array, length);
+
+ var strings = new @Array(valueCount);
+ for (var i = 0; i < valueCount; ++i)
+ strings[i] = { string: @toString(array[i]), value: array[i] };
+
+ bucketSort(array, 0, strings, 0);
+ }
+
+ if (this === null)
+ throw new @TypeError("Array.prototype.sort requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("Array.prototype.sort requires that |this| not be undefined");
+
+ if (typeof this == "string")
+ throw new @TypeError("Attempted to assign to readonly property.");
+
+ var array = @Object(this);
+
+ if (typeof comparator == "function")
+ comparatorSort(array, comparator);
+ else
+ stringSort(array);
+
+ return array;
+}
+
+function copyWithin(target, start /*, end */)
+{
+ "use strict";
+
+ function maxWithPositives(a, b)
+ {
+ return (a < b) ? b : a;
+ }
+
+ function minWithMaybeNegativeZeroAndPositive(maybeNegativeZero, positive)
+ {
+ return (maybeNegativeZero < positive) ? maybeNegativeZero : positive;
+ }
+
+ if (this === null || this === @undefined)
+ throw new @TypeError("Array.copyWithin requires that |this| not be null or undefined");
+ var thisObject = @Object(this);
+
+ var length = @toLength(thisObject.length);
+
+ var relativeTarget = @toInteger(target);
+ var to = (relativeTarget < 0) ? maxWithPositives(length + relativeTarget, 0) : minWithMaybeNegativeZeroAndPositive(relativeTarget, length);
+
+ var relativeStart = @toInteger(start);
+ var from = (relativeStart < 0) ? maxWithPositives(length + relativeStart, 0) : minWithMaybeNegativeZeroAndPositive(relativeStart, length);
+
+ var relativeEnd;
+ if (arguments.length >= 3) {
+ var end = arguments[2];
+ if (end === @undefined)
+ relativeEnd = length;
+ else
+ relativeEnd = @toInteger(end);
+ } else
+ relativeEnd = length;
+
+ var finalValue = (relativeEnd < 0) ? maxWithPositives(length + relativeEnd, 0) : minWithMaybeNegativeZeroAndPositive(relativeEnd, length);
+
+ var count = minWithMaybeNegativeZeroAndPositive(finalValue - from, length - to);
+
+ var direction = 1;
+ if (from < to && to < from + count) {
+ direction = -1;
+ from = from + count - 1;
+ to = to + count - 1;
+ }
+
+ for (var i = 0; i < count; ++i, from += direction, to += direction) {
+ if (from in thisObject)
+ thisObject[to] = thisObject[from];
+ else
+ delete thisObject[to];
+ }
+
+ return thisObject;
+}
diff --git a/Source/JavaScriptCore/builtins/BuiltinExecutables.cpp b/Source/JavaScriptCore/builtins/BuiltinExecutables.cpp
new file mode 100644
index 000000000..0d59afccc
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/BuiltinExecutables.cpp
@@ -0,0 +1,131 @@
+/*
+ * Copyright (C) 2014 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+
+#include "config.h"
+#include "BuiltinExecutables.h"
+
+#include "BuiltinNames.h"
+#include "Executable.h"
+#include "JSCInlines.h"
+#include "Parser.h"
+#include <wtf/NeverDestroyed.h>
+
+namespace JSC {
+
+static UnlinkedFunctionExecutable* createExecutableInternal(VM&, const SourceCode&, const Identifier&, ConstructorKind, ConstructAbility);
+
+BuiltinExecutables::BuiltinExecutables(VM& vm)
+ : m_vm(vm)
+#define INITIALIZE_BUILTIN_SOURCE_MEMBERS(name, functionName, length) , m_##name##Source(makeSource(StringImpl::createFromLiteral(s_##name, length)))
+ JSC_FOREACH_BUILTIN_CODE(INITIALIZE_BUILTIN_SOURCE_MEMBERS)
+#undef EXPOSE_BUILTIN_STRINGS
+{
+}
+
+UnlinkedFunctionExecutable* BuiltinExecutables::createDefaultConstructor(ConstructorKind constructorKind, const Identifier& name)
+{
+ static NeverDestroyed<const String> baseConstructorCode(ASCIILiteral("(function () { })"));
+ static NeverDestroyed<const String> derivedConstructorCode(ASCIILiteral("(function () { super(...arguments); })"));
+
+ switch (constructorKind) {
+ case ConstructorKind::None:
+ break;
+ case ConstructorKind::Base:
+ return createExecutableInternal(m_vm, makeSource(baseConstructorCode), name, constructorKind, ConstructAbility::CanConstruct);
+ case ConstructorKind::Derived:
+ return createExecutableInternal(m_vm, makeSource(derivedConstructorCode), name, constructorKind, ConstructAbility::CanConstruct);
+ }
+ ASSERT_NOT_REACHED();
+ return nullptr;
+}
+
+UnlinkedFunctionExecutable* BuiltinExecutables::createBuiltinExecutable(const SourceCode& code, const Identifier& name, ConstructAbility constructAbility)
+{
+ return createExecutableInternal(m_vm, code, name, ConstructorKind::None, constructAbility);
+}
+
+UnlinkedFunctionExecutable* createBuiltinExecutable(VM& vm, const SourceCode& code, const Identifier& name, ConstructAbility constructAbility)
+{
+ return createExecutableInternal(vm, code, name, ConstructorKind::None, constructAbility);
+}
+
+UnlinkedFunctionExecutable* createExecutableInternal(VM& vm, const SourceCode& source, const Identifier& name, ConstructorKind constructorKind, ConstructAbility constructAbility)
+{
+ JSTextPosition positionBeforeLastNewline;
+ ParserError error;
+ bool isParsingDefaultConstructor = constructorKind != ConstructorKind::None;
+ JSParserBuiltinMode builtinMode = isParsingDefaultConstructor ? JSParserBuiltinMode::NotBuiltin : JSParserBuiltinMode::Builtin;
+ UnlinkedFunctionKind kind = isParsingDefaultConstructor ? UnlinkedNormalFunction : UnlinkedBuiltinFunction;
+ RefPtr<SourceProvider> sourceOverride = isParsingDefaultConstructor ? source.provider() : nullptr;
+ std::unique_ptr<ProgramNode> program = parse<ProgramNode>(
+ &vm, source, Identifier(), builtinMode,
+ JSParserStrictMode::NotStrict, SourceParseMode::ProgramMode, SuperBinding::NotNeeded, error,
+ &positionBeforeLastNewline, constructorKind);
+
+ if (!program) {
+ dataLog("Fatal error compiling builtin function '", name.string(), "': ", error.message());
+ CRASH();
+ }
+
+ StatementNode* exprStatement = program->singleStatement();
+ RELEASE_ASSERT(exprStatement);
+ RELEASE_ASSERT(exprStatement->isExprStatement());
+ ExpressionNode* funcExpr = static_cast<ExprStatementNode*>(exprStatement)->expr();
+ RELEASE_ASSERT(funcExpr);
+ RELEASE_ASSERT(funcExpr->isFuncExprNode());
+ FunctionMetadataNode* metadata = static_cast<FuncExprNode*>(funcExpr)->metadata();
+ RELEASE_ASSERT(!program->hasCapturedVariables());
+
+ metadata->setEndPosition(positionBeforeLastNewline);
+ RELEASE_ASSERT(metadata);
+ RELEASE_ASSERT(metadata->ident().isNull());
+
+ // This function assumes an input string that would result in a single anonymous function expression.
+ metadata->setEndPosition(positionBeforeLastNewline);
+ RELEASE_ASSERT(metadata);
+ metadata->overrideName(name);
+ VariableEnvironment dummyTDZVariables;
+ UnlinkedFunctionExecutable* functionExecutable = UnlinkedFunctionExecutable::create(&vm, source, metadata, kind, constructAbility, dummyTDZVariables, DerivedContextType::None, WTFMove(sourceOverride));
+ functionExecutable->setNameValue(vm, jsString(&vm, name.string()));
+ return functionExecutable;
+}
+
+void BuiltinExecutables::finalize(Handle<Unknown>, void* context)
+{
+ static_cast<Weak<UnlinkedFunctionExecutable>*>(context)->clear();
+}
+
+#define DEFINE_BUILTIN_EXECUTABLES(name, functionName, length) \
+UnlinkedFunctionExecutable* BuiltinExecutables::name##Executable() \
+{\
+ if (!m_##name##Executable)\
+ m_##name##Executable = Weak<UnlinkedFunctionExecutable>(createBuiltinExecutable(m_##name##Source, m_vm.propertyNames->builtinNames().functionName##PublicName(), s_##name##ConstructAbility), this, &m_##name##Executable);\
+ return m_##name##Executable.get();\
+}
+JSC_FOREACH_BUILTIN_CODE(DEFINE_BUILTIN_EXECUTABLES)
+#undef EXPOSE_BUILTIN_SOURCES
+
+}
diff --git a/Source/JavaScriptCore/builtins/BuiltinExecutables.h b/Source/JavaScriptCore/builtins/BuiltinExecutables.h
new file mode 100644
index 000000000..ec8d57704
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/BuiltinExecutables.h
@@ -0,0 +1,71 @@
+/*
+ * Copyright (C) 2014 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef BuiltinExecutables_h
+#define BuiltinExecutables_h
+
+#include "JSCBuiltins.h"
+#include "ParserModes.h"
+#include "SourceCode.h"
+#include "Weak.h"
+#include "WeakHandleOwner.h"
+
+namespace JSC {
+
+class UnlinkedFunctionExecutable;
+class Identifier;
+class VM;
+
+class BuiltinExecutables final: private WeakHandleOwner {
+ WTF_MAKE_FAST_ALLOCATED;
+public:
+ explicit BuiltinExecutables(VM&);
+
+#define EXPOSE_BUILTIN_EXECUTABLES(name, functionName, length) \
+UnlinkedFunctionExecutable* name##Executable(); \
+const SourceCode& name##Source() { return m_##name##Source; }
+
+ JSC_FOREACH_BUILTIN_CODE(EXPOSE_BUILTIN_EXECUTABLES)
+#undef EXPOSE_BUILTIN_SOURCES
+
+ UnlinkedFunctionExecutable* createDefaultConstructor(ConstructorKind, const Identifier& name);
+
+private:
+ void finalize(Handle<Unknown>, void* context) override;
+
+ VM& m_vm;
+
+ UnlinkedFunctionExecutable* createBuiltinExecutable(const SourceCode&, const Identifier&, ConstructAbility);
+
+#define DECLARE_BUILTIN_SOURCE_MEMBERS(name, functionName, length)\
+ SourceCode m_##name##Source; \
+ Weak<UnlinkedFunctionExecutable> m_##name##Executable;
+ JSC_FOREACH_BUILTIN_CODE(DECLARE_BUILTIN_SOURCE_MEMBERS)
+#undef DECLARE_BUILTIN_SOURCE_MEMBERS
+};
+
+}
+
+#endif
diff --git a/Source/JavaScriptCore/builtins/BuiltinNames.h b/Source/JavaScriptCore/builtins/BuiltinNames.h
new file mode 100644
index 000000000..75fc848e2
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/BuiltinNames.h
@@ -0,0 +1,124 @@
+/*
+ * Copyright (C) 2014 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef BuiltinNames_h
+#define BuiltinNames_h
+
+#include "BuiltinUtils.h"
+#include "CommonIdentifiers.h"
+#include "JSCBuiltins.h"
+
+namespace JSC {
+
+#define INITIALIZE_PRIVATE_TO_PUBLIC_ENTRY(name) m_privateToPublicMap.add(m_##name##PrivateName.impl(), &m_##name);
+#define INITIALIZE_PUBLIC_TO_PRIVATE_ENTRY(name) m_publicToPrivateMap.add(m_##name.impl(), &m_##name##PrivateName);
+
+class BuiltinNames {
+ WTF_MAKE_NONCOPYABLE(BuiltinNames); WTF_MAKE_FAST_ALLOCATED;
+
+public:
+ BuiltinNames(VM* vm, CommonIdentifiers* commonIdentifiers)
+ : m_emptyIdentifier(commonIdentifiers->emptyIdentifier)
+ JSC_FOREACH_BUILTIN_FUNCTION_NAME(INITIALIZE_BUILTIN_NAMES)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_PROPERTY_NAME(INITIALIZE_BUILTIN_NAMES)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_WELL_KNOWN_SYMBOL(INITIALIZE_BUILTIN_SYMBOLS)
+ {
+ JSC_FOREACH_BUILTIN_FUNCTION_NAME(INITIALIZE_PRIVATE_TO_PUBLIC_ENTRY)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_PROPERTY_NAME(INITIALIZE_PRIVATE_TO_PUBLIC_ENTRY)
+ JSC_FOREACH_BUILTIN_FUNCTION_NAME(INITIALIZE_PUBLIC_TO_PRIVATE_ENTRY)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_PROPERTY_NAME(INITIALIZE_PUBLIC_TO_PRIVATE_ENTRY)
+ }
+
+ bool isPrivateName(SymbolImpl& uid) const;
+ bool isPrivateName(UniquedStringImpl& uid) const;
+ bool isPrivateName(const Identifier&) const;
+ const Identifier* lookUpPrivateName(const Identifier&) const;
+ const Identifier& lookUpPublicName(const Identifier&) const;
+
+ void appendExternalName(const Identifier& publicName, const Identifier& privateName);
+
+ JSC_FOREACH_BUILTIN_FUNCTION_NAME(DECLARE_BUILTIN_IDENTIFIER_ACCESSOR)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_PROPERTY_NAME(DECLARE_BUILTIN_IDENTIFIER_ACCESSOR)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_WELL_KNOWN_SYMBOL(DECLARE_BUILTIN_SYMBOL_ACCESSOR)
+
+private:
+ Identifier m_emptyIdentifier;
+ JSC_FOREACH_BUILTIN_FUNCTION_NAME(DECLARE_BUILTIN_NAMES)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_PROPERTY_NAME(DECLARE_BUILTIN_NAMES)
+ JSC_COMMON_PRIVATE_IDENTIFIERS_EACH_WELL_KNOWN_SYMBOL(DECLARE_BUILTIN_SYMBOLS)
+ typedef HashMap<RefPtr<UniquedStringImpl>, const Identifier*, IdentifierRepHash> BuiltinNamesMap;
+ BuiltinNamesMap m_publicToPrivateMap;
+ BuiltinNamesMap m_privateToPublicMap;
+};
+
+inline bool BuiltinNames::isPrivateName(SymbolImpl& uid) const
+{
+ return m_privateToPublicMap.contains(&uid);
+}
+
+inline bool BuiltinNames::isPrivateName(UniquedStringImpl& uid) const
+{
+ if (!uid.isSymbol())
+ return false;
+ return m_privateToPublicMap.contains(&uid);
+}
+
+inline bool BuiltinNames::isPrivateName(const Identifier& ident) const
+{
+ if (ident.isNull())
+ return false;
+ return isPrivateName(*ident.impl());
+}
+
+inline const Identifier* BuiltinNames::lookUpPrivateName(const Identifier& ident) const
+{
+ auto iter = m_publicToPrivateMap.find(ident.impl());
+ if (iter != m_publicToPrivateMap.end())
+ return iter->value;
+ return 0;
+}
+
+inline const Identifier& BuiltinNames::lookUpPublicName(const Identifier& ident) const
+{
+ auto iter = m_privateToPublicMap.find(ident.impl());
+ if (iter != m_privateToPublicMap.end())
+ return *iter->value;
+ return m_emptyIdentifier;
+}
+
+inline void BuiltinNames::appendExternalName(const Identifier& publicName, const Identifier& privateName)
+{
+#ifndef NDEBUG
+ for (const auto& key : m_publicToPrivateMap.keys())
+ ASSERT(publicName.string() != *key);
+#endif
+
+ m_privateToPublicMap.add(privateName.impl(), &publicName);
+ m_publicToPrivateMap.add(publicName.impl(), &privateName);
+}
+
+}
+
+#endif
diff --git a/Source/JavaScriptCore/builtins/BuiltinUtils.h b/Source/JavaScriptCore/builtins/BuiltinUtils.h
new file mode 100644
index 000000000..45c3e6a85
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/BuiltinUtils.h
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2014 Apple Inc. All rights reserved.
+ * Copyright (C) 2015 Canon Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef BuiltinUtils_h
+#define BuiltinUtils_h
+
+#include "ConstructAbility.h"
+
+namespace JSC {
+
+#define INITIALIZE_BUILTIN_NAMES(name) , m_##name(JSC::Identifier::fromString(vm, #name)), m_##name##PrivateName(JSC::Identifier::fromUid(JSC::PrivateName(JSC::PrivateName::Description, ASCIILiteral("PrivateSymbol." #name))))
+#define DECLARE_BUILTIN_NAMES(name) const JSC::Identifier m_##name; const JSC::Identifier m_##name##PrivateName;
+#define DECLARE_BUILTIN_IDENTIFIER_ACCESSOR(name) \
+ const JSC::Identifier& name##PublicName() const { return m_##name; } \
+ const JSC::Identifier& name##PrivateName() const { return m_##name##PrivateName; }
+
+#define INITIALIZE_BUILTIN_SYMBOLS(name) , m_##name##Symbol(JSC::Identifier::fromUid(JSC::PrivateName(JSC::PrivateName::Description, ASCIILiteral("Symbol." #name))))
+#define DECLARE_BUILTIN_SYMBOLS(name) const JSC::Identifier m_##name##Symbol;
+#define DECLARE_BUILTIN_SYMBOL_ACCESSOR(name) \
+ const JSC::Identifier& name##Symbol() const { return m_##name##Symbol; }
+
+class Identifier;
+class SourceCode;
+class UnlinkedFunctionExecutable;
+class VM;
+
+JS_EXPORT_PRIVATE UnlinkedFunctionExecutable* createBuiltinExecutable(VM&, const SourceCode&, const Identifier&, ConstructAbility);
+
+}
+
+#endif
diff --git a/Source/JavaScriptCore/builtins/DatePrototype.js b/Source/JavaScriptCore/builtins/DatePrototype.js
new file mode 100644
index 000000000..2c82508f9
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/DatePrototype.js
@@ -0,0 +1,182 @@
+/*
+ * Copyright (C) 2015 Andy VanWagoner <thetalecrafter@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// @conditional=ENABLE(INTL)
+
+function toLocaleString(/* locales, options */)
+{
+ "use strict";
+
+ function toDateTimeOptionsAnyAll(opts)
+ {
+ // ToDateTimeOptions(options, "any", "all")
+ // http://www.ecma-international.org/ecma-402/2.0/#sec-InitializeDateTimeFormat
+
+ var options;
+ if (opts === @undefined)
+ options = null;
+ else if (opts === null)
+ throw new @TypeError("null is not an object");
+ else
+ options = @Object(opts);
+
+ // Check original instead of descendant to reduce lookups up the prototype chain.
+ var needsDefaults = !options || (
+ options.weekday === @undefined &&
+ options.year === @undefined &&
+ options.month === @undefined &&
+ options.day === @undefined &&
+ options.hour === @undefined &&
+ options.minute === @undefined &&
+ options.second === @undefined
+ );
+
+ // Only create descendant if it will have own properties.
+ if (needsDefaults) {
+ options = @Object.create(options)
+ options.year = "numeric";
+ options.month = "numeric";
+ options.day = "numeric";
+ options.hour = "numeric";
+ options.minute = "numeric";
+ options.second = "numeric";
+ }
+
+ // 9. Return options.
+ return options;
+ }
+
+ // 13.3.1 Date.prototype.toLocaleString ([locales [, options ]]) (ECMA-402 2.0)
+ // http://www.ecma-international.org/ecma-402/2.0/#sec-Date.prototype.toLocaleString
+
+ var value = @thisTimeValue.@call(this);
+ if (@isNaN(value))
+ return "Invalid Date";
+
+ var options = toDateTimeOptionsAnyAll(arguments[1]);
+ var locales = arguments[0];
+
+ var dateFormat = new @DateTimeFormat(locales, options);
+ return dateFormat.format(value);
+}
+
+function toLocaleDateString(/* locales, options */)
+{
+ "use strict";
+
+ function toDateTimeOptionsDateDate(opts)
+ {
+ // ToDateTimeOptions(options, "date", "date")
+ // http://www.ecma-international.org/ecma-402/2.0/#sec-InitializeDateTimeFormat
+
+ var options;
+ if (opts === @undefined)
+ options = null;
+ else if (opts === null)
+ throw new @TypeError("null is not an object");
+ else
+ options = @Object(opts);
+
+ // Check original instead of descendant to reduce lookups up the prototype chain.
+ var needsDefaults = !options || (
+ options.weekday === @undefined &&
+ options.year === @undefined &&
+ options.month === @undefined &&
+ options.day === @undefined
+ );
+
+ // Only create descendant if it will have own properties.
+ if (needsDefaults) {
+ options = @Object.create(options)
+ options.year = "numeric";
+ options.month = "numeric";
+ options.day = "numeric";
+ }
+
+ return options;
+ }
+
+ // 13.3.2 Date.prototype.toLocaleDateString ([locales [, options ]]) (ECMA-402 2.0)
+ // http://www.ecma-international.org/ecma-402/2.0/#sec-Date.prototype.toLocaleDateString
+
+ var value = @thisTimeValue.@call(this);
+ if (@isNaN(value))
+ return "Invalid Date";
+
+ var options = toDateTimeOptionsDateDate(arguments[1]);
+ var locales = arguments[0];
+
+ var dateFormat = new @DateTimeFormat(locales, options);
+ return dateFormat.format(value);
+}
+
+function toLocaleTimeString(/* locales, options */)
+{
+ "use strict";
+
+ function toDateTimeOptionsTimeTime(opts)
+ {
+ // ToDateTimeOptions(options, "time", "time")
+ // http://www.ecma-international.org/ecma-402/2.0/#sec-InitializeDateTimeFormat
+
+ var options;
+ if (opts === @undefined)
+ options = null;
+ else if (opts === null)
+ throw new @TypeError("null is not an object");
+ else
+ options = @Object(opts);
+
+ // Check original instead of descendant to reduce lookups up the prototype chain.
+ var needsDefaults = !options || (
+ options.hour === @undefined &&
+ options.minute === @undefined &&
+ options.second === @undefined
+ );
+
+ // Only create descendant if it will have own properties.
+ if (needsDefaults) {
+ options = @Object.create(options)
+ options.hour = "numeric";
+ options.minute = "numeric";
+ options.second = "numeric";
+ }
+
+ return options;
+ }
+
+ // 13.3.3 Date.prototype.toLocaleTimeString ([locales [, options ]]) (ECMA-402 2.0)
+ // http://www.ecma-international.org/ecma-402/2.0/#sec-Date.prototype.toLocaleTimeString
+
+ var value = @thisTimeValue.@call(this);
+ if (@isNaN(value))
+ return "Invalid Date";
+
+ var options = toDateTimeOptionsTimeTime(arguments[1]);
+ var locales = arguments[0];
+
+ var dateFormat = new @DateTimeFormat(locales, options);
+ return dateFormat.format(value);
+}
diff --git a/Source/JavaScriptCore/builtins/FunctionPrototype.js b/Source/JavaScriptCore/builtins/FunctionPrototype.js
new file mode 100644
index 000000000..364bc4328
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/FunctionPrototype.js
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2014 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function call(thisArgument)
+{
+ "use strict";
+
+ return this.@call(...arguments);
+}
+
+function apply(thisValue, argumentValues)
+{
+ "use strict";
+
+ return this.@apply(thisValue, argumentValues);
+}
+
+// FIXME: this should have a different name: https://bugs.webkit.org/show_bug.cgi?id=151363
+function symbolHasInstance(value)
+{
+ "use strict";
+
+ if (typeof this !== "function")
+ return false;
+
+ if (@isBoundFunction(this))
+ return @hasInstanceBoundFunction(this, value);
+
+ let target = this.prototype;
+ return @instanceOf(value, target);
+}
diff --git a/Source/JavaScriptCore/builtins/GeneratorPrototype.js b/Source/JavaScriptCore/builtins/GeneratorPrototype.js
new file mode 100644
index 000000000..597a8821d
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/GeneratorPrototype.js
@@ -0,0 +1,93 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// 25.3.3.3 GeneratorResume ( generator, value )
+// 25.3.3.4 GeneratorResumeAbrupt(generator, abruptCompletion)
+function generatorResume(generator, sentValue, resumeMode)
+{
+ "use strict";
+
+ // GeneratorState.
+ const Completed = -1;
+ const Executing = -2;
+
+ // ResumeMode.
+ const NormalMode = 0;
+ const ReturnMode = 1;
+ const ThrowMode = 2;
+
+ let state = generator.@generatorState;
+ let done = false;
+ let value = @undefined;
+
+ if (typeof state !== 'number')
+ throw new @TypeError("|this| should be a generator");
+
+ if (state === Executing)
+ throw new @TypeError("Generator is executing");
+
+ if (state === Completed) {
+ if (resumeMode === ThrowMode)
+ throw sentValue;
+
+ done = true;
+ if (resumeMode === ReturnMode)
+ value = sentValue;
+ } else {
+ try {
+ generator.@generatorState = Executing;
+ value = generator.@generatorNext.@call(generator.@generatorThis, generator, state, sentValue, resumeMode);
+ if (generator.@generatorState === Executing) {
+ generator.@generatorState = Completed;
+ done = true;
+ }
+ } catch (error) {
+ generator.@generatorState = Completed;
+ throw error;
+ }
+ }
+ return { done, value };
+}
+
+function next(value)
+{
+ "use strict";
+
+ return @generatorResume(this, value, /* NormalMode */ 0);
+}
+
+function return(value)
+{
+ "use strict";
+
+ return @generatorResume(this, value, /* ReturnMode */ 1);
+}
+
+function throw(exception)
+{
+ "use strict";
+
+ return @generatorResume(this, exception, /* ThrowMode */ 2);
+}
diff --git a/Source/JavaScriptCore/builtins/GlobalObject.js b/Source/JavaScriptCore/builtins/GlobalObject.js
new file mode 100644
index 000000000..db53c397b
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/GlobalObject.js
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// @internal
+
+function toInteger(target)
+{
+ "use strict";
+
+ var numberValue = @Number(target);
+
+ // isNaN(numberValue)
+ if (numberValue !== numberValue)
+ return 0;
+
+ if (numberValue === 0 || !@isFinite(numberValue))
+ return numberValue;
+
+ return (numberValue > 0 ? 1 : -1) * @floor(@abs(numberValue));
+}
+
+function toLength(target)
+{
+ "use strict";
+
+ var maxSafeInteger = 0x1FFFFFFFFFFFFF;
+ var length = @toInteger(target);
+ // originally Math.min(Math.max(length, 0), maxSafeInteger));
+ return length > 0 ? (length < maxSafeInteger ? length : maxSafeInteger) : 0;
+}
+
+function isDictionary(object)
+{
+ "use strict";
+
+ return object === @undefined || object == null || typeof object === "object";
+}
+
+// FIXME: this needs to have it's name changed to "get [Symbol.species]".
+// see: https://bugs.webkit.org/show_bug.cgi?id=151363
+function speciesGetter()
+{
+ return this;
+}
diff --git a/Source/JavaScriptCore/builtins/InspectorInstrumentationObject.js b/Source/JavaScriptCore/builtins/InspectorInstrumentationObject.js
new file mode 100644
index 000000000..fb7d9eae6
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/InspectorInstrumentationObject.js
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function promiseFulfilled(promise, value, reactions)
+{
+ "use strict";
+
+ if (!this.isEnabled)
+ return;
+}
+
+function promiseRejected(promise, reason, reactions)
+{
+ "use strict";
+
+ if (!this.isEnabled)
+ return;
+}
diff --git a/Source/JavaScriptCore/builtins/InternalPromiseConstructor.js b/Source/JavaScriptCore/builtins/InternalPromiseConstructor.js
new file mode 100644
index 000000000..d01f5f7e5
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/InternalPromiseConstructor.js
@@ -0,0 +1,86 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function internalAll(array)
+{
+ // This function is intended to be used in the JSC internals.
+ // The implementation should take care not to perform the user
+ // observable / trappable operations.
+ //
+ // 1. Don't use for-of and iterables. This function only accepts
+ // the dense array of the promises.
+ // 2. Don't look up this.constructor / @@species. Always construct
+ // the plain Promise object.
+
+ "use strict";
+
+ var promiseCapability = @newPromiseCapability(@InternalPromise);
+
+ var values = [];
+ var index = 0;
+ var remainingElementsCount = 0;
+
+ function newResolveElement(index)
+ {
+ var alreadyCalled = false;
+ return function (argument)
+ {
+ if (alreadyCalled)
+ return @undefined;
+ alreadyCalled = true;
+
+ @putByValDirect(values, index, argument);
+
+ --remainingElementsCount;
+ if (remainingElementsCount === 0)
+ return promiseCapability.@resolve.@call(@undefined, values);
+
+ return @undefined;
+ }
+ }
+
+ try {
+ if (array.length === 0)
+ promiseCapability.@resolve.@call(@undefined, values);
+ else {
+ for (var index = 0, length = array.length; index < length; ++index) {
+ var value = array[index];
+ @putByValDirect(values, index, @undefined);
+
+ var nextPromiseCapability = @newPromiseCapability(@InternalPromise);
+ nextPromiseCapability.@resolve.@call(@undefined, value);
+ var nextPromise = nextPromiseCapability.@promise;
+
+ var resolveElement = newResolveElement(index);
+ ++remainingElementsCount;
+ nextPromise.then(resolveElement, promiseCapability.@reject);
+ }
+ }
+ } catch (error) {
+ promiseCapability.@reject.@call(@undefined, error);
+ }
+
+ return promiseCapability.@promise;
+}
diff --git a/Source/JavaScriptCore/builtins/IteratorPrototype.js b/Source/JavaScriptCore/builtins/IteratorPrototype.js
new file mode 100644
index 000000000..5c1691a3d
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/IteratorPrototype.js
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function symbolIteratorGetter()
+{
+ "use strict";
+
+ return this;
+}
diff --git a/Source/JavaScriptCore/builtins/MapPrototype.js b/Source/JavaScriptCore/builtins/MapPrototype.js
new file mode 100644
index 000000000..620a015d3
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/MapPrototype.js
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2016 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function forEach(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (!@isMap(this))
+ throw new @TypeError("Map operation called on non-Map object");
+
+ if (typeof callback !== 'function')
+ throw new @TypeError("Map.prototype.forEach callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ var iterator = @MapIterator(this);
+
+ // To avoid object allocations for iterator result objects, we pass the placeholder to the special "next" function in order to fill the results.
+ var value = [ @undefined, @undefined ];
+ for (;;) {
+ if (@mapIteratorNext.@call(iterator, value))
+ break;
+ callback.@call(thisArg, value[1], value[0], this);
+ }
+}
diff --git a/Source/JavaScriptCore/builtins/ModuleLoaderObject.js b/Source/JavaScriptCore/builtins/ModuleLoaderObject.js
new file mode 100644
index 000000000..568a307b7
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/ModuleLoaderObject.js
@@ -0,0 +1,562 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// https://whatwg.github.io/loader/#loader-object
+// Module Loader has several hooks that can be customized by the platform.
+// For example, the [[Fetch]] hook can be provided by the JavaScriptCore shell
+// as fetching the payload from the local file system.
+// Currently, there are 4 hooks.
+// 1. Loader.resolve
+// 2. Loader.fetch
+// 3. Loader.translate
+// 4. Loader.instantiate
+
+function setStateToMax(entry, newState)
+{
+ // https://whatwg.github.io/loader/#set-state-to-max
+
+ "use strict";
+
+ if (entry.state < newState)
+ entry.state = newState;
+}
+
+function newRegistryEntry(key)
+{
+ // https://whatwg.github.io/loader/#registry
+ //
+ // Each registry entry becomes one of the 5 states.
+ // 1. Fetch
+ // Ready to fetch (or now fetching) the resource of this module.
+ // Typically, we fetch the source code over the network or from the file system.
+ // a. If the status is Fetch and there is no entry.fetch promise, the entry is ready to fetch.
+ // b. If the status is Fetch and there is the entry.fetch promise, the entry is just fetching the resource.
+ //
+ // 2. Translate
+ // Ready to translate (or now translating) the raw fetched resource to the ECMAScript source code.
+ // We can insert the hook that translates the resources e.g. transpilers.
+ // a. If the status is Translate and there is no entry.translate promise, the entry is ready to translate.
+ // b. If the status is Translate and there is the entry.translate promise, the entry is just translating
+ // the payload to the source code.
+ //
+ // 3. Instantiate (AnalyzeModule)
+ // Ready to instantiate (or now instantiating) the module record from the fetched (and translated)
+ // source code.
+ // Typically, we parse the module code, extract the dependencies and binding information.
+ // a. If the status is Instantiate and there is no entry.instantiate promise, the entry is ready to instantiate.
+ // b. If the status is Instantiate and there is the entry.translate promise, the entry is just instantiating
+ // the module record.
+ //
+ // 4. ResolveDependencies (not in the draft) https://github.com/whatwg/loader/issues/68
+ // Ready to request the dependent modules (or now requesting & resolving).
+ // Without this state, the current draft causes infinite recursion when there is circular dependency.
+ // a. If the status is ResolveDependencies and there is no entry.resolveDependencies promise, the entry is ready to resolve the dependencies.
+ // b. If the status is ResolveDependencies and there is the entry.resolveDependencies promise, the entry is just resolving
+ // the dependencies.
+ //
+ // 5. Link
+ // Ready to link the module with the other modules.
+ // Linking means that the module imports and exports the bindings from/to the other modules.
+ //
+ // 6. Ready
+ // The module is linked, so the module is ready to be executed.
+ //
+ // Each registry entry has the 4 promises; "fetch", "translate", "instantiate" and "resolveDependencies".
+ // They are assigned when starting the each phase. And they are fulfilled when the each phase is completed.
+ //
+ // In the current module draft, linking will be performed after the whole modules are instantiated and the dependencies are resolved.
+ // And execution is also done after the all modules are linked.
+ //
+ // TODO: We need to exploit the way to execute the module while fetching non-related modules.
+ // One solution; introducing the ready promise chain to execute the modules concurrently while keeping
+ // the execution order.
+
+ "use strict";
+
+ return {
+ key: key,
+ state: this.Fetch,
+ metadata: @undefined,
+ fetch: @undefined,
+ translate: @undefined,
+ instantiate: @undefined,
+ resolveDependencies: @undefined,
+ dependencies: [], // To keep the module order, we store the module keys in the array.
+ dependenciesMap: @undefined,
+ module: @undefined, // JSModuleRecord
+ error: @undefined,
+ };
+}
+
+function ensureRegistered(key)
+{
+ // https://whatwg.github.io/loader/#ensure-registered
+
+ "use strict";
+
+ var entry = this.registry.@get(key);
+ if (entry)
+ return entry;
+
+ entry = this.newRegistryEntry(key);
+ this.registry.@set(key, entry);
+
+ return entry;
+}
+
+function forceFulfillPromise(promise, value)
+{
+ "use strict";
+
+ if (promise.@promiseState === @promiseStatePending)
+ @fulfillPromise(promise, value);
+}
+
+function fulfillFetch(entry, payload)
+{
+ // https://whatwg.github.io/loader/#fulfill-fetch
+
+ "use strict";
+
+ if (!entry.fetch)
+ entry.fetch = @newPromiseCapability(@InternalPromise).@promise;
+ this.forceFulfillPromise(entry.fetch, payload);
+ this.setStateToMax(entry, this.Translate);
+}
+
+function fulfillTranslate(entry, source)
+{
+ // https://whatwg.github.io/loader/#fulfill-translate
+
+ "use strict";
+
+ if (!entry.translate)
+ entry.translate = @newPromiseCapability(@InternalPromise).@promise;
+ this.forceFulfillPromise(entry.translate, source);
+ this.setStateToMax(entry, this.Instantiate);
+}
+
+function fulfillInstantiate(entry, optionalInstance, source)
+{
+ // https://whatwg.github.io/loader/#fulfill-instantiate
+
+ "use strict";
+
+ if (!entry.instantiate)
+ entry.instantiate = @newPromiseCapability(@InternalPromise).@promise;
+ this.commitInstantiated(entry, optionalInstance, source);
+
+ // FIXME: The draft fulfills the promise in the CommitInstantiated operation.
+ // But it CommitInstantiated is also used in the requestInstantiate and
+ // we should not "force fulfill" there.
+ // So we separate "force fulfill" operation from the CommitInstantiated operation.
+ // https://github.com/whatwg/loader/pull/67
+ this.forceFulfillPromise(entry.instantiate, entry);
+}
+
+function commitInstantiated(entry, optionalInstance, source)
+{
+ // https://whatwg.github.io/loader/#commit-instantiated
+
+ "use strict";
+
+ var moduleRecord = this.instantiation(optionalInstance, source, entry);
+
+ // FIXME: Described in the draft,
+ // 4. Fulfill entry.[[Instantiate]] with instance.
+ // But, instantiate promise should be fulfilled with the entry.
+ // We remove this statement because instantiate promise will be
+ // fulfilled without this "force fulfill" operation.
+ // https://github.com/whatwg/loader/pull/67
+
+ var dependencies = [];
+ var dependenciesMap = moduleRecord.dependenciesMap;
+ moduleRecord.registryEntry = entry;
+ var requestedModules = this.requestedModules(moduleRecord);
+ for (var i = 0, length = requestedModules.length; i < length; ++i) {
+ var depKey = requestedModules[i];
+ var pair = {
+ key: depKey,
+ value: @undefined
+ };
+ @putByValDirect(dependencies, i, pair);
+ dependenciesMap.@set(depKey, pair);
+ }
+ entry.dependencies = dependencies;
+ entry.dependenciesMap = dependenciesMap;
+ entry.module = moduleRecord;
+ this.setStateToMax(entry, this.ResolveDependencies);
+}
+
+function instantiation(result, source, entry)
+{
+ // https://whatwg.github.io/loader/#instantiation
+ // FIXME: Current implementation does not support optionalInstance.
+ // https://bugs.webkit.org/show_bug.cgi?id=148171
+
+ "use strict";
+
+ return this.parseModule(entry.key, source);
+}
+
+// Loader.
+
+function requestFetch(key)
+{
+ // https://whatwg.github.io/loader/#request-fetch
+
+ "use strict";
+
+ var entry = this.ensureRegistered(key);
+ if (entry.state > this.Link) {
+ var deferred = @newPromiseCapability(@InternalPromise);
+ deferred.@reject.@call(@undefined, new @TypeError("Requested module is already ready to be executed."));
+ return deferred.@promise;
+ }
+
+ if (entry.fetch)
+ return entry.fetch;
+
+ var loader = this;
+
+ // Hook point.
+ // 2. Loader.fetch
+ // https://whatwg.github.io/loader/#browser-fetch
+ // Take the key and fetch the resource actually.
+ // For example, JavaScriptCore shell can provide the hook fetching the resource
+ // from the local file system.
+ var fetchPromise = this.fetch(key).then(function (payload) {
+ loader.setStateToMax(entry, loader.Translate);
+ return payload;
+ });
+ entry.fetch = fetchPromise;
+ return fetchPromise;
+}
+
+function requestTranslate(key)
+{
+ // https://whatwg.github.io/loader/#request-translate
+
+ "use strict";
+
+ var entry = this.ensureRegistered(key);
+ if (entry.state > this.Link) {
+ var deferred = @newPromiseCapability(@InternalPromise);
+ deferred.@reject.@call(@undefined, new @TypeError("Requested module is already ready to be executed."));
+ return deferred.@promise;
+ }
+
+ if (entry.translate)
+ return entry.translate;
+
+ var loader = this;
+ var translatePromise = this.requestFetch(key).then(function (payload) {
+ // Hook point.
+ // 3. Loader.translate
+ // https://whatwg.github.io/loader/#browser-translate
+ // Take the key and the fetched source code and translate it to the ES6 source code.
+ // Typically it is used by the transpilers.
+ return loader.translate(key, payload).then(function (source) {
+ loader.setStateToMax(entry, loader.Instantiate);
+ return source;
+ });
+ });
+ entry.translate = translatePromise;
+ return translatePromise;
+}
+
+function requestInstantiate(key)
+{
+ // https://whatwg.github.io/loader/#request-instantiate
+
+ "use strict";
+
+ var entry = this.ensureRegistered(key);
+ if (entry.state > this.Link) {
+ var deferred = @newPromiseCapability(@InternalPromise);
+ deferred.@reject.@call(@undefined, new @TypeError("Requested module is already ready to be executed."));
+ return deferred.@promise;
+ }
+
+ if (entry.instantiate)
+ return entry.instantiate;
+
+ var loader = this;
+ var instantiatePromise = this.requestTranslate(key).then(function (source) {
+ // Hook point.
+ // 4. Loader.instantiate
+ // https://whatwg.github.io/loader/#browser-instantiate
+ // Take the key and the translated source code, and instantiate the module record
+ // by parsing the module source code.
+ // It has the chance to provide the optional module instance that is different from
+ // the ordinary one.
+ return loader.instantiate(key, source).then(function (optionalInstance) {
+ loader.commitInstantiated(entry, optionalInstance, source);
+ return entry;
+ });
+ });
+ entry.instantiate = instantiatePromise;
+ return instantiatePromise;
+}
+
+function requestResolveDependencies(key)
+{
+ // FIXME: In the spec, after requesting instantiation, we will resolve
+ // the dependencies without any status change. As a result, when there
+ // is circular dependencies, instantiation is done only once, but
+ // repeatedly resolving the dependencies. This means that infinite
+ // recursion occur when the given modules have circular dependency. To
+ // avoid this situation, we introduce new state, "ResolveDependencies". This means
+ // "Now the module is instantiated, so ready to resolve the dependencies
+ // or now resolving them".
+ // https://github.com/whatwg/loader/issues/68
+
+ "use strict";
+
+ var entry = this.ensureRegistered(key);
+ if (entry.state > this.Link) {
+ var deferred = @newPromiseCapability(@InternalPromise);
+ deferred.@reject.@call(@undefined, new @TypeError("Requested module is already ready to be executed."));
+ return deferred.@promise;
+ }
+
+ if (entry.resolveDependencies)
+ return entry.resolveDependencies;
+
+ var loader = this;
+ var resolveDependenciesPromise = this.requestInstantiate(key).then(function (entry) {
+ var depLoads = [];
+ for (var i = 0, length = entry.dependencies.length; i < length; ++i) {
+ let pair = entry.dependencies[i];
+
+ // Hook point.
+ // 1. Loader.resolve.
+ // https://whatwg.github.io/loader/#browser-resolve
+ // Take the name and resolve it to the unique identifier for the resource location.
+ // For example, take the "jquery" and return the URL for the resource.
+ var promise = loader.resolve(pair.key, key).then(function (depKey) {
+ var depEntry = loader.ensureRegistered(depKey);
+
+ // Recursive resolving. The dependencies of this entry is being resolved or already resolved.
+ // Stop tracing the circular dependencies.
+ // But to retrieve the instantiated module record correctly,
+ // we need to wait for the instantiation for the dependent module.
+ // For example, reaching here, the module is starting resolving the dependencies.
+ // But the module may or may not reach the instantiation phase in the loader's pipeline.
+ // If we wait for the ResolveDependencies for this module, it construct the circular promise chain and
+ // rejected by the Promises runtime. Since only we need is the instantiated module, instead of waiting
+ // the ResolveDependencies for this module, we just wait Instantiate for this.
+ if (depEntry.resolveDependencies) {
+ return depEntry.instantiate.then(function (entry) {
+ pair.value = entry.module;
+ return entry;
+ });
+ }
+
+ return loader.requestResolveDependencies(depKey).then(function (entry) {
+ pair.value = entry.module;
+ return entry;
+ });
+ });
+ @putByValDirect(depLoads, i, promise);
+ }
+
+ return @InternalPromise.internalAll(depLoads).then(function (modules) {
+ loader.setStateToMax(entry, loader.Link);
+ return entry;
+ });
+ });
+
+ entry.resolveDependencies = resolveDependenciesPromise;
+ return resolveDependenciesPromise;
+}
+
+function requestInstantiateAll(key)
+{
+ // https://whatwg.github.io/loader/#request-instantiate-all
+
+ "use strict";
+
+ return this.requestResolveDependencies(key);
+}
+
+function requestLink(key)
+{
+ // https://whatwg.github.io/loader/#request-link
+
+ "use strict";
+
+ var entry = this.ensureRegistered(key);
+ if (entry.state > this.Link) {
+ var deferred = @newPromiseCapability(@InternalPromise);
+ deferred.@resolve.@call(@undefined, entry.module);
+ return deferred.@promise;
+ }
+
+ var loader = this;
+ return this.requestInstantiateAll(key).then(function (entry) {
+ loader.link(entry);
+ return entry;
+ });
+}
+
+function requestReady(key)
+{
+ // https://whatwg.github.io/loader/#request-ready
+
+ "use strict";
+
+ var loader = this;
+ return this.requestLink(key).then(function (entry) {
+ loader.moduleEvaluation(entry.module);
+ });
+}
+
+// Linking semantics.
+
+function link(entry)
+{
+ // https://whatwg.github.io/loader/#link
+
+ "use strict";
+
+ // FIXME: Current implementation does not support optionalInstance.
+ // So Link's step 3 is skipped.
+ // https://bugs.webkit.org/show_bug.cgi?id=148171
+
+ if (entry.state === this.Ready)
+ return;
+ this.setStateToMax(entry, this.Ready);
+
+ // Since we already have the "dependencies" field,
+ // we can call moduleDeclarationInstantiation with the correct order
+ // without constructing the dependency graph by calling dependencyGraph.
+ var dependencies = entry.dependencies;
+ for (var i = 0, length = dependencies.length; i < length; ++i) {
+ var pair = dependencies[i];
+ this.link(pair.value.registryEntry);
+ }
+
+ this.moduleDeclarationInstantiation(entry.module);
+}
+
+// Module semantics.
+
+function moduleEvaluation(moduleRecord)
+{
+ // http://www.ecma-international.org/ecma-262/6.0/#sec-moduleevaluation
+
+ "use strict";
+
+ if (moduleRecord.evaluated)
+ return;
+ moduleRecord.evaluated = true;
+
+ var entry = moduleRecord.registryEntry;
+
+ // The contents of the [[RequestedModules]] is cloned into entry.dependencies.
+ var dependencies = entry.dependencies;
+ for (var i = 0, length = dependencies.length; i < length; ++i) {
+ var pair = dependencies[i];
+ var requiredModuleRecord = pair.value;
+ this.moduleEvaluation(requiredModuleRecord);
+ }
+ this.evaluate(entry.key, moduleRecord);
+}
+
+// APIs to control the module loader.
+
+function provide(key, stage, value)
+{
+ "use strict";
+
+ var entry = this.ensureRegistered(key);
+
+ if (stage === this.Fetch) {
+ if (entry.status > this.Fetch)
+ throw new @TypeError("Requested module is already fetched.");
+ this.fulfillFetch(entry, value);
+ return;
+ }
+
+ if (stage === this.Translate) {
+ if (entry.status > this.Translate)
+ throw new @TypeError("Requested module is already translated.");
+ this.fulfillFetch(entry, @undefined);
+ this.fulfillTranslate(entry, value);
+ return;
+ }
+
+ if (stage === this.Instantiate) {
+ if (entry.status > this.Instantiate)
+ throw new @TypeError("Requested module is already instantiated.");
+ this.fulfillFetch(entry, @undefined);
+ this.fulfillTranslate(entry, value);
+ var loader = this;
+ entry.translate.then(function (source) {
+ loader.fulfillInstantiate(entry, value, source);
+ });
+ return;
+ }
+
+ throw new @TypeError("Requested module is already ready to be executed.");
+}
+
+function loadAndEvaluateModule(moduleName, referrer)
+{
+ "use strict";
+
+ var loader = this;
+ // Loader.resolve hook point.
+ // resolve: moduleName => Promise(moduleKey)
+ // Take the name and resolve it to the unique identifier for the resource location.
+ // For example, take the "jquery" and return the URL for the resource.
+ return this.resolve(moduleName, referrer).then(function (key) {
+ return loader.requestReady(key);
+ });
+}
+
+function loadModule(moduleName, referrer)
+{
+ "use strict";
+
+ var loader = this;
+ // Loader.resolve hook point.
+ // resolve: moduleName => Promise(moduleKey)
+ // Take the name and resolve it to the unique identifier for the resource location.
+ // For example, take the "jquery" and return the URL for the resource.
+ return this.resolve(moduleName, referrer).then(function (key) {
+ return loader.requestInstantiateAll(key);
+ }).then(function (entry) {
+ return entry.key;
+ });
+}
+
+function linkAndEvaluateModule(key)
+{
+ "use strict";
+
+ return this.requestReady(key);
+}
diff --git a/Source/JavaScriptCore/builtins/NumberPrototype.js b/Source/JavaScriptCore/builtins/NumberPrototype.js
new file mode 100644
index 000000000..49a1a8b8a
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/NumberPrototype.js
@@ -0,0 +1,47 @@
+/*
+ * Copyright (C) 2015 Andy VanWagoner <thetalecrafter@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// @conditional=ENABLE(INTL)
+
+function toLocaleString(/* locales, options */)
+{
+ "use strict";
+
+ // 13.2.1 Number.prototype.toLocaleString ([locales [, options ]]) (ECMA-402 2.0)
+ // http://ecma-international.org/publications/standards/Ecma-402.htm
+
+ // 1. Let x be thisNumberValue(this value).
+ // 2. ReturnIfAbrupt(x).
+ var number = this;
+ if (!(typeof number === "number" || number instanceof @Number))
+ throw new @TypeError("Number.prototype.toLocaleString called on incompatible " + typeof number);
+
+ // 3. Let numberFormat be Construct(%NumberFormat%, «locales, options»).
+ // 4. ReturnIfAbrupt(numberFormat).
+ var numberFormat = new @NumberFormat(arguments[0], arguments[1]);
+
+ // 5. Return FormatNumber(numberFormat, x).
+ return numberFormat.format(number);
+}
diff --git a/Source/JavaScriptCore/builtins/ObjectConstructor.js b/Source/JavaScriptCore/builtins/ObjectConstructor.js
new file mode 100644
index 000000000..4fa7ddf18
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/ObjectConstructor.js
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2015 Jordan Harband. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function assign(target/*[*/, /*...*/sources/*] */)
+{
+ "use strict";
+
+ if (target == null)
+ throw new @TypeError("can't convert " + target + " to object");
+
+ var objTarget = @Object(target);
+ for (var s = 1, argumentsLength = arguments.length; s < argumentsLength; ++s) {
+ var nextSource = arguments[s];
+ if (nextSource != null) {
+ var from = @Object(nextSource);
+ var keys = @ownEnumerablePropertyKeys(from);
+ for (var i = 0, keysLength = keys.length; i < keysLength; ++i) {
+ var nextKey = keys[i];
+ objTarget[nextKey] = from[nextKey];
+ }
+ }
+ }
+ return objTarget;
+}
diff --git a/Source/JavaScriptCore/builtins/PromiseConstructor.js b/Source/JavaScriptCore/builtins/PromiseConstructor.js
new file mode 100644
index 000000000..77ce57c83
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/PromiseConstructor.js
@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function all(iterable)
+{
+ "use strict";
+
+ if (!@isObject(this))
+ throw new @TypeError("|this| is not a object");
+
+ // FIXME: Fix this code when @@species well-known symbol is landed.
+ // https://bugs.webkit.org/show_bug.cgi?id=146624
+ var constructor = this;
+
+ var promiseCapability = @newPromiseCapability(constructor);
+
+ var values = [];
+ var index = 0;
+ var remainingElementsCount = 1;
+
+ function newResolveElement(index)
+ {
+ var alreadyCalled = false;
+ return function (argument)
+ {
+ if (alreadyCalled)
+ return @undefined;
+ alreadyCalled = true;
+
+ @putByValDirect(values, index, argument);
+
+ --remainingElementsCount;
+ if (remainingElementsCount === 0)
+ return promiseCapability.@resolve.@call(@undefined, values);
+
+ return @undefined;
+ }
+ }
+
+ try {
+ for (var value of iterable) {
+ @putByValDirect(values, index, @undefined);
+ var nextPromise = constructor.resolve(value);
+ var resolveElement = newResolveElement(index);
+ ++remainingElementsCount;
+ nextPromise.then(resolveElement, promiseCapability.@reject);
+ ++index;
+ }
+
+ --remainingElementsCount;
+ if (remainingElementsCount === 0)
+ promiseCapability.@resolve.@call(@undefined, values);
+ } catch (error) {
+ promiseCapability.@reject.@call(@undefined, error);
+ }
+
+ return promiseCapability.@promise;
+}
+
+function race(iterable)
+{
+ "use strict";
+
+ if (!@isObject(this))
+ throw new @TypeError("|this| is not a object");
+
+ // FIXME: Fix this code when @@species well-known symbol is landed.
+ // https://bugs.webkit.org/show_bug.cgi?id=146624
+ var constructor = this;
+
+ var promiseCapability = @newPromiseCapability(constructor);
+
+ try {
+ for (var value of iterable) {
+ var nextPromise = constructor.resolve(value);
+ nextPromise.then(promiseCapability.@resolve, promiseCapability.@reject);
+ }
+ } catch (error) {
+ promiseCapability.@reject.@call(@undefined, error);
+ }
+
+ return promiseCapability.@promise;
+}
+
+function reject(reason)
+{
+ "use strict";
+
+ if (!@isObject(this))
+ throw new @TypeError("|this| is not a object");
+
+ var promiseCapability = @newPromiseCapability(this);
+
+ promiseCapability.@reject.@call(@undefined, reason);
+
+ return promiseCapability.@promise;
+}
+
+function resolve(value)
+{
+ "use strict";
+
+ if (!@isObject(this))
+ throw new @TypeError("|this| is not a object");
+
+ if (@isPromise(value)) {
+ var valueConstructor = value.constructor;
+ if (valueConstructor === this)
+ return value;
+ }
+
+ var promiseCapability = @newPromiseCapability(this);
+
+ promiseCapability.@resolve.@call(@undefined, value);
+
+ return promiseCapability.@promise;
+}
diff --git a/Source/JavaScriptCore/builtins/PromiseOperations.js b/Source/JavaScriptCore/builtins/PromiseOperations.js
new file mode 100644
index 000000000..c4e59bb07
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/PromiseOperations.js
@@ -0,0 +1,215 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// @internal
+
+function isPromise(promise)
+{
+ "use strict";
+
+ return @isObject(promise) && !!promise.@promiseState;
+}
+
+function newPromiseReaction(capability, handler)
+{
+ "use strict";
+
+ return {
+ @capabilities: capability,
+ @handler: handler
+ };
+}
+
+function newPromiseCapability(constructor)
+{
+ "use strict";
+
+ // FIXME: Check isConstructor(constructor).
+ if (typeof constructor !== "function")
+ throw new @TypeError("promise capability requires a constructor function");
+
+ var promiseCapability = {
+ @promise: @undefined,
+ @resolve: @undefined,
+ @reject: @undefined
+ };
+
+ function executor(resolve, reject)
+ {
+ if (promiseCapability.@resolve !== @undefined)
+ throw new @TypeError("resolve function is already set");
+ if (promiseCapability.@reject !== @undefined)
+ throw new @TypeError("reject function is already set");
+
+ promiseCapability.@resolve = resolve;
+ promiseCapability.@reject = reject;
+ }
+
+ var promise = new constructor(executor);
+
+ if (typeof promiseCapability.@resolve !== "function")
+ throw new @TypeError("executor did not take a resolve function");
+
+ if (typeof promiseCapability.@reject !== "function")
+ throw new @TypeError("executor did not take a reject function");
+
+ promiseCapability.@promise = promise;
+
+ return promiseCapability;
+}
+
+function triggerPromiseReactions(reactions, argument)
+{
+ "use strict";
+
+ for (var index = 0, length = reactions.length; index < length; ++index)
+ @enqueueJob(@promiseReactionJob, [reactions[index], argument]);
+}
+
+function rejectPromise(promise, reason)
+{
+ "use strict";
+
+ var reactions = promise.@promiseRejectReactions;
+ promise.@promiseResult = reason;
+ promise.@promiseFulfillReactions = @undefined;
+ promise.@promiseRejectReactions = @undefined;
+ promise.@promiseState = @promiseStateRejected;
+
+ @InspectorInstrumentation.promiseRejected(promise, reason, reactions);
+
+ @triggerPromiseReactions(reactions, reason);
+}
+
+function fulfillPromise(promise, value)
+{
+ "use strict";
+
+ var reactions = promise.@promiseFulfillReactions;
+ promise.@promiseResult = value;
+ promise.@promiseFulfillReactions = @undefined;
+ promise.@promiseRejectReactions = @undefined;
+ promise.@promiseState = @promiseStateFulfilled;
+
+ @InspectorInstrumentation.promiseFulfilled(promise, value, reactions);
+
+ @triggerPromiseReactions(reactions, value);
+}
+
+function createResolvingFunctions(promise)
+{
+ "use strict";
+
+ var alreadyResolved = false;
+
+ var resolve = function (resolution) {
+ if (alreadyResolved)
+ return @undefined;
+ alreadyResolved = true;
+
+ if (resolution === promise)
+ return @rejectPromise(promise, new @TypeError("Resolve a promise with itself"));
+
+ if (!@isObject(resolution))
+ return @fulfillPromise(promise, resolution);
+
+ var then;
+ try {
+ then = resolution.then;
+ } catch (error) {
+ return @rejectPromise(promise, error);
+ }
+
+ if (typeof then !== 'function')
+ return @fulfillPromise(promise, resolution);
+
+ @enqueueJob(@promiseResolveThenableJob, [promise, resolution, then]);
+
+ return @undefined;
+ };
+
+ var reject = function (reason) {
+ if (alreadyResolved)
+ return @undefined;
+ alreadyResolved = true;
+
+ return @rejectPromise(promise, reason);
+ };
+
+ return {
+ @resolve: resolve,
+ @reject: reject
+ };
+}
+
+function promiseReactionJob(reaction, argument)
+{
+ "use strict";
+
+ var promiseCapability = reaction.@capabilities;
+
+ var result;
+ try {
+ result = reaction.@handler.@call(@undefined, argument);
+ } catch (error) {
+ return promiseCapability.@reject.@call(@undefined, error);
+ }
+
+ return promiseCapability.@resolve.@call(@undefined, result);
+}
+
+function promiseResolveThenableJob(promiseToResolve, thenable, then)
+{
+ "use strict";
+
+ var resolvingFunctions = @createResolvingFunctions(promiseToResolve);
+
+ try {
+ return then.@call(thenable, resolvingFunctions.@resolve, resolvingFunctions.@reject);
+ } catch (error) {
+ return resolvingFunctions.@reject.@call(@undefined, error);
+ }
+}
+
+function initializePromise(executor)
+{
+ "use strict";
+
+ if (typeof executor !== 'function')
+ throw new @TypeError("Promise constructor takes a function argument");
+
+ this.@promiseState = @promiseStatePending;
+ this.@promiseFulfillReactions = [];
+ this.@promiseRejectReactions = [];
+
+ var resolvingFunctions = @createResolvingFunctions(this);
+ try {
+ executor(resolvingFunctions.@resolve, resolvingFunctions.@reject);
+ } catch (error) {
+ return resolvingFunctions.@reject.@call(@undefined, error);
+ }
+
+ return this;
+}
diff --git a/Source/JavaScriptCore/builtins/PromisePrototype.js b/Source/JavaScriptCore/builtins/PromisePrototype.js
new file mode 100644
index 000000000..ec604b828
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/PromisePrototype.js
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2014 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function catch(onRejected)
+{
+ "use strict";
+
+ return this.then(@undefined, onRejected);
+}
+
+function then(onFulfilled, onRejected)
+{
+ "use strict";
+
+ if (!@isPromise(this))
+ throw new @TypeError("|this| is not a object");
+
+ // FIXME: Fix this code when @@species well-known symbol is landed.
+ // https://bugs.webkit.org/show_bug.cgi?id=146624
+ var constructor = this.constructor;
+
+ var resultCapability = @newPromiseCapability(constructor);
+
+ if (typeof onFulfilled !== "function")
+ onFulfilled = function (argument) { return argument; };
+
+ if (typeof onRejected !== "function")
+ onRejected = function (argument) { throw argument; };
+
+ var fulfillReaction = @newPromiseReaction(resultCapability, onFulfilled);
+ var rejectReaction = @newPromiseReaction(resultCapability, onRejected);
+
+ var state = this.@promiseState;
+
+ if (state === @promiseStatePending) {
+ @putByValDirect(this.@promiseFulfillReactions, this.@promiseFulfillReactions.length, fulfillReaction)
+ @putByValDirect(this.@promiseRejectReactions, this.@promiseRejectReactions.length, rejectReaction)
+ } else if (state === @promiseStateFulfilled)
+ @enqueueJob(@promiseReactionJob, [fulfillReaction, this.@promiseResult]);
+ else if (state === @promiseStateRejected)
+ @enqueueJob(@promiseReactionJob, [rejectReaction, this.@promiseResult]);
+
+ return resultCapability.@promise;
+}
diff --git a/Source/JavaScriptCore/builtins/ReflectObject.js b/Source/JavaScriptCore/builtins/ReflectObject.js
new file mode 100644
index 000000000..69c982850
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/ReflectObject.js
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// http://www.ecma-international.org/ecma-262/6.0/#sec-reflect.apply
+function apply(target, thisArgument, argumentsList)
+{
+ "use strict";
+
+ if (typeof target !== "function")
+ throw new @TypeError("Reflect.apply requires the first argument be a function");
+
+ if (!@isObject(argumentsList))
+ throw new @TypeError("Reflect.apply requires the third argument be an object");
+
+ return target.@apply(thisArgument, argumentsList);
+}
+
+// http://www.ecma-international.org/ecma-262/6.0/#sec-reflect.deleteproperty
+function deleteProperty(target, propertyKey)
+{
+ // Intentionally keep the code the sloppy mode to suppress the TypeError
+ // raised by the delete operator under the strict mode.
+
+ if (!@isObject(target))
+ throw new @TypeError("Reflect.deleteProperty requires the first argument be an object");
+
+ return delete target[propertyKey];
+}
+
+// http://www.ecma-international.org/ecma-262/6.0/#sec-reflect.has
+function has(target, propertyKey)
+{
+ "use strict";
+
+ if (!@isObject(target))
+ throw new @TypeError("Reflect.has requires the first argument be an object");
+
+ return propertyKey in target;
+}
diff --git a/Source/JavaScriptCore/builtins/SetPrototype.js b/Source/JavaScriptCore/builtins/SetPrototype.js
new file mode 100644
index 000000000..55271b529
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/SetPrototype.js
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2016 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function forEach(callback /*, thisArg */)
+{
+ "use strict";
+
+ if (!@isSet(this))
+ throw new @TypeError("Set operation called on non-Set object");
+
+ if (typeof callback !== 'function')
+ throw new @TypeError("Set.prototype.forEach callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ var iterator = @SetIterator(this);
+
+ // To avoid object allocations for iterator result objects, we pass the placeholder to the special "next" function in order to fill the results.
+ var value = [ @undefined ];
+ for (;;) {
+ if (@setIteratorNext.@call(iterator, value))
+ break;
+ callback.@call(thisArg, value[0], value[0], this);
+ }
+}
diff --git a/Source/JavaScriptCore/builtins/StringConstructor.js b/Source/JavaScriptCore/builtins/StringConstructor.js
new file mode 100644
index 000000000..90b435fce
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/StringConstructor.js
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function raw(template)
+{
+ "use strict";
+
+ if (template === null || template === @undefined)
+ throw new @TypeError("String.raw requires template not be null or undefined");
+ var cookedSegments = @Object(template);
+
+ var rawValue = cookedSegments.raw;
+ if (rawValue === null || rawValue === @undefined)
+ throw new @TypeError("String.raw requires template.raw not be null or undefined");
+ var rawSegments = @Object(rawValue);
+
+ var numberOfSubstitutions = arguments.length - 1;
+
+ var segmentCount = @toLength(rawSegments.length);
+
+ if (segmentCount <= 0)
+ return '';
+
+ var stringElements = '';
+ for (var i = 0; ; ++i) {
+ var segment = @toString(rawSegments[i]);
+ stringElements += segment;
+
+ if ((i + 1) === segmentCount)
+ return stringElements;
+
+ if (i < numberOfSubstitutions) {
+ var substitutionIndexInArguments = i + 1;
+ var next = @toString(arguments[substitutionIndexInArguments]);
+ stringElements += next;
+ }
+ }
+}
diff --git a/Source/JavaScriptCore/builtins/StringIteratorPrototype.js b/Source/JavaScriptCore/builtins/StringIteratorPrototype.js
new file mode 100644
index 000000000..f774ec47a
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/StringIteratorPrototype.js
@@ -0,0 +1,64 @@
+/*
+ * Copyright (C) 2015 Yusuke Suzuki <utatane.tea@gmail.com>.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+function next()
+{
+ "use strict";
+
+ if (this == null)
+ throw new @TypeError("%StringIteratorPrototype%.next requires that |this| not be null or undefined");
+
+ var position = this.@stringIteratorNextIndex;
+ if (position === @undefined)
+ throw new @TypeError("%StringIteratorPrototype%.next requires that |this| be a String Iterator instance");
+
+ var done = true;
+ var value = @undefined;
+
+ var string = this.@iteratedString;
+ if (string !== @undefined) {
+ var length = string.length >>> 0;
+ if (position >= length) {
+ this.@iteratedString = @undefined;
+ } else {
+ done = false;
+
+ var first = string.@charCodeAt(position);
+ if (first < 0xD800 || first > 0xDBFF || position + 1 === length)
+ value = string[position];
+ else {
+ var second = string.@charCodeAt(position + 1);
+ if (second < 0xDC00 || second > 0xDFFF)
+ value = string[position];
+ else
+ value = string[position] + string[position + 1];
+ }
+
+ this.@stringIteratorNextIndex = position + value.length;
+ }
+ }
+
+ return {done, value};
+}
diff --git a/Source/JavaScriptCore/builtins/StringPrototype.js b/Source/JavaScriptCore/builtins/StringPrototype.js
new file mode 100644
index 000000000..9a3049ba1
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/StringPrototype.js
@@ -0,0 +1,82 @@
+/*
+ * Copyright (C) 2015 Andy VanWagoner <thetalecrafter@gmail.com>.
+ * Copyright (C) 2016 Yusuke Suzuki <utatane.tea@gmail.com>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// @conditional=ENABLE(INTL)
+
+function localeCompare(that/*, locales, options */)
+{
+ "use strict";
+
+ // 13.1.1 String.prototype.localeCompare (that [, locales [, options ]]) (ECMA-402 2.0)
+ // http://ecma-international.org/publications/standards/Ecma-402.htm
+
+ // 1. Let O be RequireObjectCoercible(this value).
+ if (this === null)
+ throw new @TypeError("String.prototype.localeCompare requires that |this| not be null");
+
+ if (this === @undefined)
+ throw new @TypeError("String.prototype.localeCompare requires that |this| not be undefined");
+
+ // 2. Let S be ToString(O).
+ // 3. ReturnIfAbrupt(S).
+ var thisString = @toString(this);
+
+ // 4. Let That be ToString(that).
+ // 5. ReturnIfAbrupt(That).
+ var thatString = @toString(that);
+
+ // Avoid creating a collator for defaults.
+ if (arguments[1] === @undefined && arguments[2] === @undefined)
+ return @Collator.prototype.compare(thisString, thatString);
+
+ // 6. Let collator be Construct(%Collator%, «locales, options»).
+ // 7. ReturnIfAbrupt(collator).
+ var collator = new @Collator(arguments[1], arguments[2]);
+
+ // 8. Return CompareStrings(collator, S, That).
+ return collator.compare(thisString, thatString);
+}
+
+function search(regexp)
+{
+ "use strict";
+
+ if (this == null) {
+ if (this === null)
+ throw new @TypeError("String.prototype.search requires that |this| not be null");
+ throw new @TypeError("String.prototype.search requires that |this| not be undefined");
+ }
+
+ if (regexp != null) {
+ var searcher = regexp[@symbolSearch];
+ if (searcher !== @undefined)
+ return searcher.@call(regexp, this);
+ }
+
+ var thisString = @toString(this);
+ var createdRegExp = new @RegExp(regexp, @undefined);
+ return createdRegExp[@symbolSearch](thisString);
+}
diff --git a/Source/JavaScriptCore/builtins/TypedArrayConstructor.js b/Source/JavaScriptCore/builtins/TypedArrayConstructor.js
new file mode 100644
index 000000000..a83d745fd
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/TypedArrayConstructor.js
@@ -0,0 +1,181 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// According to the spec we are supposed to crawl the prototype chain looking
+// for the a TypedArray constructor. The way we implement this is with a
+// private function, @alloctateTypedArray, on each of the prototypes.
+// This enables us to optimize this lookup in the inline cache.
+
+function of(/* items... */)
+{
+ "use strict";
+ let len = arguments.length;
+ let constructFunction = this.@allocateTypedArray;
+ if (constructFunction === @undefined)
+ throw new @TypeError("TypedArray.from requires its this argument to subclass a TypedArray constructor");
+
+ let result = constructFunction(len);
+
+ for (let i = 0; i < len; i++)
+ result[i] = arguments[i];
+
+ return result;
+}
+
+function from(items /* [ , mapfn [ , thisArg ] ] */)
+{
+ "use strict";
+
+ let mapFn = arguments[1];
+
+ let thisArg;
+
+ if (mapFn !== @undefined) {
+ if (typeof mapFn !== "function")
+ throw new @TypeError("TypedArray.from requires that the second argument, when provided, be a function");
+
+ if (arguments.length > 2)
+ thisArg = arguments[2];
+ }
+
+ if (items == null)
+ throw new @TypeError("TypedArray.from requires an array-like object - not null or undefined");
+
+ let iteratorMethod = items[@symbolIterator];
+ if (iteratorMethod != null) {
+ if (typeof iteratorMethod !== "function")
+ throw new @TypeError("TypedArray.from requires that the property of the first argument, items[Symbol.iterator], when exists, be a function");
+
+ let accumulator = [];
+
+ let k = 0;
+ let iterator = iteratorMethod.@call(items);
+
+ // Since for-of loop once more looks up the @@iterator property of a given iterable,
+ // it could be observable if the user defines a getter for @@iterator.
+ // To avoid this situation, we define a wrapper object that @@iterator just returns a given iterator.
+ let wrapper = {
+ [@symbolIterator]() {
+ return iterator;
+ }
+ };
+
+
+ for (let value of wrapper) {
+ if (mapFn)
+ @putByValDirect(accumulator, k, thisArg === @undefined ? mapFn(value, k) : mapFn.@call(thisArg, value, k));
+ else
+ @putByValDirect(accumulator, k, value);
+ k++;
+ }
+
+ let constructFunction = this.@allocateTypedArray;
+ if (constructFunction === @undefined)
+ throw new @TypeError("TypedArray.from requires its this argument subclass a TypedArray constructor");
+
+ let result = constructFunction(k);
+
+ for (let i = 0; i < k; i++)
+ result[i] = accumulator[i];
+
+
+ return result;
+ }
+
+ let arrayLike = @Object(items);
+ let arrayLikeLength = @toLength(arrayLike.length);
+
+ let constructFunction = this.@allocateTypedArray;
+ if (constructFunction === @undefined)
+ throw new @TypeError("this does not subclass a TypedArray constructor");
+
+ let result = constructFunction(arrayLikeLength);
+
+ let k = 0;
+ while (k < arrayLikeLength) {
+ let value = arrayLike[k];
+ if (mapFn)
+ result[k] = thisArg === @undefined ? mapFn(value, k) : mapFn.@call(thisArg, value, k);
+ else
+ result[k] = value;
+ k++;
+ }
+
+ return result;
+}
+
+function allocateInt8Array(length) {
+
+ return new @Int8Array(length);
+
+}
+
+function allocateInt16Array(length) {
+
+ return new @Int16Array(length);
+
+}
+
+function allocateInt32Array(length) {
+
+ return new @Int32Array(length);
+
+}
+
+function allocateUint32Array(length) {
+
+ return new @Uint32Array(length);
+
+}
+
+function allocateUint16Array(length) {
+
+ return new @Uint16Array(length);
+
+}
+
+function allocateUint8Array(length) {
+
+ return new @Uint8Array(length);
+
+}
+
+function allocateUint8ClampedArray(length) {
+
+ return new @Uint8ClampedArray(length);
+
+}
+
+function allocateFloat32Array(length) {
+
+ return new @Float32Array(length);
+
+}
+
+function allocateFloat64Array(length) {
+
+ return new @Float64Array(length);
+
+}
diff --git a/Source/JavaScriptCore/builtins/TypedArrayPrototype.js b/Source/JavaScriptCore/builtins/TypedArrayPrototype.js
new file mode 100644
index 000000000..f68bb43bd
--- /dev/null
+++ b/Source/JavaScriptCore/builtins/TypedArrayPrototype.js
@@ -0,0 +1,287 @@
+/*
+ * Copyright (C) 2015 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// Note that the intrisic @typedArrayLength checks the that the argument passed is a typed array
+// and throws if it is not.
+
+function every(callback /*, thisArg */)
+{
+ "use strict";
+ var length = @typedArrayLength(this);
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.every callback must be a function");
+
+ for (var i = 0; i < length; i++) {
+ if (!callback.@call(thisArg, this[i], i, this))
+ return false;
+ }
+
+ return true;
+}
+
+function find(callback /* [, thisArg] */)
+{
+ "use strict";
+ var length = @typedArrayLength(this);
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.find callback must be a function");
+
+ for (var i = 0; i < length; i++) {
+ let elem = this[i];
+ if (callback.@call(thisArg, elem, i, this))
+ return elem;
+ }
+ return @undefined;
+}
+
+function findIndex(callback /* [, thisArg] */)
+{
+ "use strict";
+ var length = @typedArrayLength(this);
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.findIndex callback must be a function");
+
+ for (var i = 0; i < length; i++) {
+ if (callback.@call(thisArg, this[i], i, this))
+ return i;
+ }
+ return -1;
+}
+
+function forEach(callback /* [, thisArg] */)
+{
+ "use strict";
+ var length = @typedArrayLength(this);
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.forEach callback must be a function");
+
+ for (var i = 0; i < length; i++)
+ callback.@call(thisArg, this[i], i, this);
+}
+
+function some(callback /* [, thisArg] */)
+{
+ // 22.2.3.24
+ "use strict";
+ var length = @typedArrayLength(this);
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.some callback must be a function");
+
+ for (var i = 0; i < length; i++) {
+ if (callback.@call(thisArg, this[i], i, this))
+ return true;
+ }
+
+ return false;
+}
+
+function sort(comparator)
+{
+ // 22.2.3.25
+ "use strict";
+
+ function min(a, b)
+ {
+ return a < b ? a : b;
+ }
+
+ function merge(dst, src, srcIndex, srcEnd, width, comparator)
+ {
+ var left = srcIndex;
+ var leftEnd = min(left + width, srcEnd);
+ var right = leftEnd;
+ var rightEnd = min(right + width, srcEnd);
+
+ for (var dstIndex = left; dstIndex < rightEnd; ++dstIndex) {
+ if (right < rightEnd) {
+ if (left >= leftEnd || comparator(src[right], src[left]) < 0) {
+ dst[dstIndex] = src[right++];
+ continue;
+ }
+ }
+
+ dst[dstIndex] = src[left++];
+ }
+ }
+
+ function mergeSort(array, valueCount, comparator)
+ {
+ var buffer = [ ];
+ buffer.length = valueCount;
+
+ var dst = buffer;
+ var src = array;
+
+ for (var width = 1; width < valueCount; width *= 2) {
+ for (var srcIndex = 0; srcIndex < valueCount; srcIndex += 2 * width)
+ merge(dst, src, srcIndex, valueCount, width, comparator);
+
+ var tmp = src;
+ src = dst;
+ dst = tmp;
+ }
+
+ if (src != array) {
+ for(var i = 0; i < valueCount; i++)
+ array[i] = src[i];
+ }
+ }
+
+ var length = @typedArrayLength(this);
+
+ if (length < 2)
+ return;
+
+ if (typeof comparator == "function")
+ mergeSort(this, length, comparator);
+ else
+ @typedArraySort(this);
+
+ return this;
+}
+
+function reduce(callback /* [, initialValue] */)
+{
+ // 22.2.3.19
+ "use strict";
+
+ var length = @typedArrayLength(this);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.reduce callback must be a function");
+
+ if (length === 0 && arguments.length < 2)
+ throw new @TypeError("TypedArray.prototype.reduce of empty array with no initial value");
+
+ var accumulator, k = 0;
+ if (arguments.length > 1)
+ accumulator = arguments[1];
+ else
+ accumulator = this[k++];
+
+ for (; k < length; k++)
+ accumulator = callback.@call(@undefined, accumulator, this[k], k, this);
+
+ return accumulator;
+}
+
+function reduceRight(callback /* [, initialValue] */)
+{
+ // 22.2.3.20
+ "use strict";
+
+ var length = @typedArrayLength(this);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.reduceRight callback must be a function");
+
+ if (length === 0 && arguments.length < 2)
+ throw new @TypeError("TypedArray.prototype.reduceRight of empty array with no initial value");
+
+ var accumulator, k = length - 1;
+ if (arguments.length > 1)
+ accumulator = arguments[1];
+ else
+ accumulator = this[k--];
+
+ for (; k >= 0; k--)
+ accumulator = callback.@call(@undefined, accumulator, this[k], k, this);
+
+ return accumulator;
+}
+
+function map(callback /*, thisArg */)
+{
+ // 22.2.3.18
+ "use strict";
+
+ var length = @typedArrayLength(this);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.map callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+ // FIXME: This should be a species constructor.
+ var result = new this.constructor(length);
+ for (var i = 0; i < length; i++) {
+ var mappedValue = callback.@call(thisArg, this[i], i, this);
+ result[i] = mappedValue;
+ }
+ return result;
+}
+
+function filter(callback /*, thisArg */)
+{
+ "use strict";
+
+ var length = @typedArrayLength(this);
+
+ if (typeof callback !== "function")
+ throw new @TypeError("TypedArray.prototype.filter callback must be a function");
+
+ var thisArg = arguments.length > 1 ? arguments[1] : @undefined;
+
+ var kept = [];
+
+ for (var i = 0; i < length; i++) {
+ var value = this[i];
+ if (callback.@call(thisArg, value, i, this))
+ kept.@push(value);
+ }
+
+ // FIXME: This should be a species constructor.
+ var result = new this.constructor(kept.length);
+
+ for (var i = 0; i < kept.length; i++)
+ result[i] = kept[i];
+
+ return result;
+}
+
+function toLocaleString()
+{
+ "use strict";
+
+ var length = @typedArrayLength(this);
+
+ if (length == 0)
+ return "";
+
+ var string = this[0].toLocaleString();
+ for (var i = 1; i < length; i++)
+ string += "," + this[i].toLocaleString();
+
+ return string;
+}