//-------------------------------------------------------------------------------------------------------
// Copyright (C) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
//-------------------------------------------------------------------------------------------------------

/// <reference path="protolib.js" />
if (this.WScript && this.WScript.LoadScriptFile) {
    WScript.LoadScriptFile("protolib.js");
}

var tests = [
    {
        name: "seal/freeze Object.prototype",
        body: function () {
            ["Object.seal(Object.prototype)", "Object.freeze(Object.prototype)"].forEach(function (expr) {
                verify_disable(expr, KEEP_ENABLED); // These no longer disables __proto__
            });
        }
    },

    {
        name: "delete Object.prototype.__proto__",
        body: function () {
            var eng = make_engine();

            var desc = eng.Object.getOwnPropertyDescriptor(eng.Object.prototype, "__proto__");
            eng.verify_disable("delete Object.prototype.__proto__");

            // redefine such a property brings __proto__ back
            eng.Object.defineProperty(eng.Object.prototype, "__proto__", desc);
            eng.verify__proto__enabled();
        }
    },

    {
        name: "DefineOwnProperty with missing/different attribute set",
        body: function () {
            function getDescString(desc) {
                var set = [];
                for (var name in desc) {
                    set.push(name + ": " + desc[name]);
                }
                return '{' + set.join(", ") + '}';
            }

            function testDesc(desc, keepEnabled) {
                var expr = 'Object.defineProperty(Object.prototype, "__proto__", ' + getDescString(desc) + ')';

                var eng = make_engine();
                eng.__verify_disable(expr, keepEnabled);

                // Verify we indeed have those attr set successfully
                var otherDesc = eng.Object.getOwnPropertyDescriptor(eng.Object.prototype, "__proto__");
                for (var name in desc) {
                    assert.areEqual("" + desc[name], "" + otherDesc[name], name);
                }
            }

            var ATTR_NAMES = ["enumerable", "configurable"];
            var DEF_DESC = { enumerable: false, configurable: true };

            // Test any attr missing
            for (var n = 0; n < 3; n++) {
                var desc = {};
                for (var i = 0; i < 2; i++) {
                    if (n & (1 << i)) {
                        var name = ATTR_NAMES[i];
                        desc[name] = DEF_DESC[name];
                    }
                }

                testDesc(desc, KEEP_ENABLED); // Now these don't disable __proto__
            }

            // Test any attr diff
            ATTR_NAMES.forEach(function (attr) {
                var desc = { enumerable: false, configurable: true };
                desc[attr] = !desc[attr];

                testDesc(desc, KEEP_ENABLED); // Now these don't disable __proto__
            });

            testDesc({ enumerable: false, configurable: true }, KEEP_ENABLED);

            // But will be disabled if we change to value, or change setter
            testDesc({ value: 234, writable: true, enumerable: false, configurable: true });
            testDesc({ set: function () { return "custom setter" }, enumerable: false, configurable: true });
        }
    },

    {
        name: "Change Object.prototype.__proto__ getter or setter",
        body: function () {
            make_engine().run(function () {
                var oldDesc = Object.getOwnPropertyDescriptor(Object.prototype, "__proto__");

                var p = { p: 12 };
                var p2 = { p2: 23 };
                var o = { o: 34 };

                assert.areEqual(Object.prototype, o.__proto__);
                o.__proto__ = p;
                assert.areEqual(p, Object.getPrototypeOf(o));

                // Replace the setter
                Object.defineProperty(Object.prototype, "__proto__", { set: function () { } });
                assert.areEqual(p, o.__proto__);
                o.__proto__ = p2; // This does not work
                assert.areEqual(p, o.__proto__);
                Object.setPrototypeOf(o, p2); // But this works
                assert.areEqual(p2, o.__proto__);

                // Replace the getter
                Object.defineProperty(Object.prototype, "__proto__", { get: function () { return 123; } });
                assert.areEqual(123, o.__proto__);
                assert.areEqual(p2, Object.getPrototypeOf(o));
                Object.setPrototypeOf(o, p);
                assert.areEqual(123, o.__proto__);
                assert.areEqual(p, Object.getPrototypeOf(o));

                // Restore
                Object.defineProperty(Object.prototype, "__proto__", { get: oldDesc.get, set: oldDesc.set });
                assert.areEqual(p, o.__proto__);

                verify__proto__enabled();
            });
        }
    },
];
testRunner.run(tests);
