<html>
<head>
<title>ArrayBuffer External Memory test</title>
<script>

var log;
function print(message, color)
{
    var paragraph = document.createElement("div");
    paragraph.appendChild(document.createTextNode(message));
    paragraph.style.fontFamily = "monospace";
    if (color)
        paragraph.style.color = color;
    log.appendChild(paragraph);
}

function pass(msg)
{
    print("PASS: " + msg, "green");
}

function fail(msg)
{
    print("FAIL: " + msg, "red");
}

var KB = 1024;
var MB = KB * KB;
var noise = KB;

function externalMemory() {
    return getV8Statistics().amount_of_external_allocated_memory;
}

function collectGarbage() {
    for (var i = 0; i < 10; i++) gc();
}

function allocationsThatIncreaseExternalMemory() {
    function test(expression) {
        var before = externalMemory();
        (function () { eval(expression); }) ();
        var now = externalMemory();
        if (now < before + MB - noise) {
            fail(expression + " did not increase the amount of external memory (" +
                  before + ", " + now + ").");
        } else {
            pass(expression + " increased the amount of external memory.");
        }
        collectGarbage();
        var after = externalMemory();
        if (after > now + noise) {
            fail("Garbage collection after " + expression +
                 " did not return the amount of external memory to the initial value (" +
                 now + ", " + after + ").");
        } else {
            pass("Garbage collection after " + expression +
                 " returned the amount of external memory to the initial value.");
        }
    }

    test("(new ArrayBuffer(MB))");
    test("(new Float32Array(MB))");
    test("(new Float64Array(MB))");
    test("(new Int8Array(MB))");
    test("(new Int16Array(MB))");
    test("(new Int32Array(MB))");
    test("(new Uint8Array(MB))");
    test("(new Uint16Array(MB))");
    test("(new Uint32Array(MB))");
    var largeJSArray = [];
    for (var i = 0; i < MB; i++) largeJSArray.push(i);
    test("(new Float32Array(largeJSArray))");
    test("(new Float64Array(largeJSArray))");
    test("(new Int8Array(largeJSArray))");
    test("(new Int16Array(largeJSArray))");
    test("(new Int32Array(largeJSArray))");
    test("(new Uint8Array(largeJSArray))");
    test("(new Uint16Array(largeJSArray))");
    test("(new Uint32Array(largeJSArray))");
    var int8Array = new Int8Array(MB);
    test("(new  Float32Array(int8Array))");
    test("(new  Float64Array(int8Array))");
    test("(new  Int8Array(int8Array))");
    test("(new  Int16Array(int8Array))");
    test("(new  Int32Array(int8Array))");
    test("(new  Uint8Array(int8Array))");
    test("(new  Uint16Array(int8Array))");
    test("(new  Uint32Array(int8Array))");
}


function allocationsThatDoNotChangeExternalMemory() {
    function test(expression) {
        var before = externalMemory();
        (function () { eval(expression); }) ();
        var now = externalMemory();
        if (now > before + noise) {
            fail(expression + " increased the amount of external memory (" + before + ", " + now + ").");
        } else {
            pass(expression + " did not increase the amount of external memory.");
        }
        collectGarbage();
        var after = externalMemory();
        if (after < now - noise) {
            fail("Garbage collection after " + expression + " decreased the amount of external memory (" +
                 now + ", " + after + ").");
        } else {
            pass("Garbage collection after " + expression +
                 " did not decrease the amount of external memory.");
        }
    }
    var arrayBuffer = new ArrayBuffer(MB);
    test("(new  Float32Array(arrayBuffer))");
    test("(new  Float64Array(arrayBuffer))");
    test("(new  Int8Array(arrayBuffer))");
    test("(new  Int16Array(arrayBuffer))");
    test("(new  Int32Array(arrayBuffer))");
    test("(new  Uint8Array(arrayBuffer))");
    test("(new  Uint16Array(arrayBuffer))");
    test("(new  Uint32Array(arrayBuffer))");
    var int8Array = new Int8Array(MB);
    test("(new  Float32Array(int8Array.buffer))");
    test("(new  Float64Array(int8Array.buffer))");
    test("(new  Int8Array(int8Array.buffer))");
    test("(new  Int16Array(int8Array.buffer))");
    test("(new  Int32Array(int8Array.buffer))");
    test("(new  Uint8Array(int8Array.buffer))");
    test("(new  Uint16Array(int8Array.buffer))");
    test("(new  Uint32Array(int8Array.buffer))");
}


function transfersThatDecreaseExternalMemory() {
    var workerSource =
"function externalMemory() {\n" +
"    return getV8Statistics().amount_of_external_allocated_memory;\n" +
"}\n" +
"var KB = 1024;\n" +
"var MB = KB * KB;\n" +
"var noise = KB;\n" +
"self.onmessage = function(e) {\n" +
"    var before = externalMemory();\n" +
"    e.data;\n" +
"    var after = externalMemory();\n" +
"    if (after > before + MB - noise) {\n" +
"      self.postMessage('PASS: Amount of external memory increased.');\n" +
"    } else {\n" +
"      self.postMessage('FAIL: Amount of external memory did not increase.');\n" +
"    }\n" +
"}\n";

    var blob = new Blob([workerSource]);
    var worker = new Worker(window.webkitURL.createObjectURL(blob));
    worker.onmessage = function (e) {
        print("message from worker: " + e.data, "blue");
    }
    function test(expression)
    {
        var buffer = eval(expression);
        try {
            var before = externalMemory();
            worker.postMessage(buffer, [buffer]);
            var now = externalMemory();
            if (now > before - MB + noise) {
                fail("Transfer of " + expression + " did not decrease the amount of external memory (" +
                     before + ", " + now + ").");
            } else {
                pass("Transfer of " + expression + " decreased the amount of external memory.");
            }
            collectGarbage();
            var after = externalMemory();
            if (after < now - noise) {
                fail("Garbage collection after transfer of " + expression +
                     " decreased the amount of external memory (" + now + ", " + after + ").");
            } else {
                pass("Garbage collection after transfer of " + expression +
                     " did not decrease the amount of external memory.");
            }
        } catch (e) {
            fail("Transfer of " + name + ": could not webkitPostMessage: " + e);
            return false;
        }
        return true;
    }
    test("(new ArrayBuffer(MB))");
    test("(new Float32Array(MB)).buffer");
    test("(new Float64Array(MB)).buffer");
    test("(new Int8Array(MB)).buffer");
    test("(new Int16Array(MB)).buffer");
    test("(new Int32Array(MB)).buffer");
    test("(new Uint8Array(MB)).buffer");
    test("(new Uint16Array(MB)).buffer");
    test("(new Uint32Array(MB)).buffer");
}


function runAll() {
    log = document.getElementById("log1");
    if (typeof gc == "undefined" || typeof getV8Statistics == "undefined") {
        print("Run chrome browser with --js-flags='--expose_gc --track_gc_object_stats'", "red");
    } else {
         allocationsThatIncreaseExternalMemory();
         collectGarbage();
         allocationsThatDoNotChangeExternalMemory();
         collectGarbage();
         log = document.getElementById("log2");
         transfersThatDecreaseExternalMemory();
         collectGarbage();
    }
}

</script>
</head>
<body onload="runAll()">
<p>This test checks that allocation and deallocation of typed arrays correctly
adjusts the amount of external memory in V8.</p>
<div id='log1'></div>
<p>This test checks that transfer of an array buffer to worker decreases amount of
external memory in the main V8 isolate.</p>
<div id='log2'></div>
</body>
</html>
