/*
 * Copyright (C) 2015-2016 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 that the argument passed is a typed array
// and throws if it is not.


// Typed Arrays have their own species constructor function since they need
// to look up their default constructor, which is expensive. If we used the
// normal speciesConstructor helper we would need to look up the default
// constructor every time.
@globalPrivate
function typedArraySpeciesConstructor(value)
{
    "use strict";
    let constructor = value.constructor;
    if (constructor === @undefined)
        return @typedArrayGetOriginalConstructor(value);

    if (!@isObject(constructor))
        @throwTypeError("|this|.constructor is not an Object or undefined");

    constructor = constructor.@speciesSymbol;
    if (@isUndefinedOrNull(constructor))
        return @typedArrayGetOriginalConstructor(value);
    // The lack of an @isConstructor(constructor) check here is not observable because
    // the first thing we will do with the value is attempt to construct the result with it.
    // If any user of this function does not immediately construct the result they need to
    // verify that the result is a constructor.
    return constructor;
}

@globalPrivate
function typedArrayClampArgumentToStartOrEnd(value, length, undefinedValue)
{
    "use strict";

    if (value === @undefined)
        return undefinedValue;

    let int = @toInteger(value);
    if (int < 0) {
        int += length;
        return int < 0 ? 0 : int;
    }
    return int > length ? length : int;
}

function values()
{
    "use strict";
    @typedArrayLength(this);
    return new @ArrayIterator(this, "value", @arrayIteratorValueNext);
}

function keys()
{
    "use strict";
    @typedArrayLength(this);
    return new @ArrayIterator(this, "key", @arrayIteratorKeyNext);
}

function entries()
{
    "use strict";
    @typedArrayLength(this);
    return new @ArrayIterator(this, "key+value", @arrayIteratorKeyValueNext);
}

function every(callback /*, thisArg */)
{
    "use strict";
    var length = @typedArrayLength(this);
    var thisArg = @argument(1);

    if (typeof callback !== "function")
        @throwTypeError("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 fill(value /* [, start [, end]] */)
{
    "use strict";

    let length = @typedArrayLength(this);

    let start = @argument(1);
    let end = @argument(2);

    start = @typedArrayClampArgumentToStartOrEnd(start, length, 0);
    end = @typedArrayClampArgumentToStartOrEnd(end, length, length);

    for (let i = start; i < end; i++)
        this[i] = value;
    return this;
}

function find(callback /* [, thisArg] */)
{
    "use strict";
    var length = @typedArrayLength(this);
    var thisArg = @argument(1);

    if (typeof callback !== "function")
        @throwTypeError("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 = @argument(1);

    if (typeof callback !== "function")
        @throwTypeError("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 = @argument(1);

    if (typeof callback !== "function")
        @throwTypeError("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 = @argument(1);

    if (typeof callback !== "function")
        @throwTypeError("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 subarray(begin, end)
{
    "use strict";

    if (!@isTypedArrayView(this))
        @throwTypeError("|this| should be a typed array view");

    let start = @toInteger(begin);
    let finish;
    if (end !== @undefined)
        finish = @toInteger(end);

    let constructor = @typedArraySpeciesConstructor(this);

    return @typedArraySubarrayCreate.@call(this, start, finish, constructor);
}

function reduce(callback /* [, initialValue] */)
{
    // 22.2.3.19
    "use strict";

    var length = @typedArrayLength(this);

    if (typeof callback !== "function")
        @throwTypeError("TypedArray.prototype.reduce callback must be a function");

    var argumentCount = @argumentCount();
    if (length === 0 && argumentCount < 2)
        @throwTypeError("TypedArray.prototype.reduce of empty array with no initial value");

    var accumulator, k = 0;
    if (argumentCount > 1)
        accumulator = @argument(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")
        @throwTypeError("TypedArray.prototype.reduceRight callback must be a function");

    var argumentCount = @argumentCount();
    if (length === 0 && argumentCount < 2)
        @throwTypeError("TypedArray.prototype.reduceRight of empty array with no initial value");

    var accumulator, k = length - 1;
    if (argumentCount > 1)
        accumulator = @argument(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")
        @throwTypeError("TypedArray.prototype.map callback must be a function");

    var thisArg = @argument(1);

    // Do species construction
    var constructor = this.constructor;
    var result;
    if (constructor === @undefined)
        result = new (@typedArrayGetOriginalConstructor(this))(length);
    else {
        var speciesConstructor = constructor.@speciesSymbol;
        if (@isUndefinedOrNull(speciesConstructor))
            result = new (@typedArrayGetOriginalConstructor(this))(length);
        else {
            result = new speciesConstructor(length);
            // typedArrayLength throws if it doesn't get a view.
            @typedArrayLength(result);
        }
    }

    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")
        @throwTypeError("TypedArray.prototype.filter callback must be a function");

    var thisArg = @argument(1);
    var kept = [];

    for (var i = 0; i < length; i++) {
        var value = this[i];
        if (callback.@call(thisArg, value, i, this))
            kept.@push(value);
    }

    var constructor = this.constructor;
    var result;
    var resultLength = kept.length;
    if (constructor === @undefined)
        result = new (@typedArrayGetOriginalConstructor(this))(resultLength);
    else {
        var speciesConstructor = constructor.@speciesSymbol;
        if (@isUndefinedOrNull(speciesConstructor))
            result = new (@typedArrayGetOriginalConstructor(this))(resultLength);
        else {
            result = new speciesConstructor(resultLength);
            // typedArrayLength throws if it doesn't get a view.
            @typedArrayLength(result);
        }
    }

    for (var i = 0; i < kept.length; i++)
        result[i] = kept[i];

    return result;
}

function toLocaleString(/* locale, options */)
{
    "use strict";

    var length = @typedArrayLength(this);

    if (length == 0)
        return "";

    var string = this[0].toLocaleString(@argument(0), @argument(1));
    for (var i = 1; i < length; i++)
        string += "," + this[i].toLocaleString(@argument(0), @argument(1));

    return string;
}
