proto_disable.js 5.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. //-------------------------------------------------------------------------------------------------------
  2. // Copyright (C) Microsoft. All rights reserved.
  3. // Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
  4. //-------------------------------------------------------------------------------------------------------
  5. /// <reference path="protolib.js" />
  6. if (this.WScript && this.WScript.LoadScriptFile) {
  7. WScript.LoadScriptFile("protolib.js");
  8. }
  9. var tests = [
  10. {
  11. name: "seal/freeze Object.prototype",
  12. body: function () {
  13. ["Object.seal(Object.prototype)", "Object.freeze(Object.prototype)"].forEach(function (expr) {
  14. verify_disable(expr, KEEP_ENABLED); // These no longer disables __proto__
  15. });
  16. }
  17. },
  18. {
  19. name: "delete Object.prototype.__proto__",
  20. body: function () {
  21. var eng = make_engine();
  22. var desc = eng.Object.getOwnPropertyDescriptor(eng.Object.prototype, "__proto__");
  23. eng.verify_disable("delete Object.prototype.__proto__");
  24. // redefine such a property brings __proto__ back
  25. eng.Object.defineProperty(eng.Object.prototype, "__proto__", desc);
  26. eng.verify__proto__enabled();
  27. }
  28. },
  29. {
  30. name: "DefineOwnProperty with missing/different attribute set",
  31. body: function () {
  32. function getDescString(desc) {
  33. var set = [];
  34. for (var name in desc) {
  35. set.push(name + ": " + desc[name]);
  36. }
  37. return '{' + set.join(", ") + '}';
  38. }
  39. function testDesc(desc, keepEnabled) {
  40. var expr = 'Object.defineProperty(Object.prototype, "__proto__", ' + getDescString(desc) + ')';
  41. var eng = make_engine();
  42. eng.__verify_disable(expr, keepEnabled);
  43. // Verify we indeed have those attr set successfully
  44. var otherDesc = eng.Object.getOwnPropertyDescriptor(eng.Object.prototype, "__proto__");
  45. for (var name in desc) {
  46. assert.areEqual("" + desc[name], "" + otherDesc[name], name);
  47. }
  48. }
  49. var ATTR_NAMES = ["enumerable", "configurable"];
  50. var DEF_DESC = { enumerable: false, configurable: true };
  51. // Test any attr missing
  52. for (var n = 0; n < 3; n++) {
  53. var desc = {};
  54. for (var i = 0; i < 2; i++) {
  55. if (n & (1 << i)) {
  56. var name = ATTR_NAMES[i];
  57. desc[name] = DEF_DESC[name];
  58. }
  59. }
  60. testDesc(desc, KEEP_ENABLED); // Now these don't disable __proto__
  61. }
  62. // Test any attr diff
  63. ATTR_NAMES.forEach(function (attr) {
  64. var desc = { enumerable: false, configurable: true };
  65. desc[attr] = !desc[attr];
  66. testDesc(desc, KEEP_ENABLED); // Now these don't disable __proto__
  67. });
  68. testDesc({ enumerable: false, configurable: true }, KEEP_ENABLED);
  69. // But will be disabled if we change to value, or change setter
  70. testDesc({ value: 234, writable: true, enumerable: false, configurable: true });
  71. testDesc({ set: function () { return "custom setter" }, enumerable: false, configurable: true });
  72. }
  73. },
  74. {
  75. name: "Change Object.prototype.__proto__ getter or setter",
  76. body: function () {
  77. make_engine().run(function () {
  78. var oldDesc = Object.getOwnPropertyDescriptor(Object.prototype, "__proto__");
  79. var p = { p: 12 };
  80. var p2 = { p2: 23 };
  81. var o = { o: 34 };
  82. assert.areEqual(Object.prototype, o.__proto__);
  83. o.__proto__ = p;
  84. assert.areEqual(p, Object.getPrototypeOf(o));
  85. // Replace the setter
  86. Object.defineProperty(Object.prototype, "__proto__", { set: function () { } });
  87. assert.areEqual(p, o.__proto__);
  88. o.__proto__ = p2; // This does not work
  89. assert.areEqual(p, o.__proto__);
  90. Object.setPrototypeOf(o, p2); // But this works
  91. assert.areEqual(p2, o.__proto__);
  92. // Replace the getter
  93. Object.defineProperty(Object.prototype, "__proto__", { get: function () { return 123; } });
  94. assert.areEqual(123, o.__proto__);
  95. assert.areEqual(p2, Object.getPrototypeOf(o));
  96. Object.setPrototypeOf(o, p);
  97. assert.areEqual(123, o.__proto__);
  98. assert.areEqual(p, Object.getPrototypeOf(o));
  99. // Restore
  100. Object.defineProperty(Object.prototype, "__proto__", { get: oldDesc.get, set: oldDesc.set });
  101. assert.areEqual(p, o.__proto__);
  102. verify__proto__enabled();
  103. });
  104. }
  105. },
  106. ];
  107. testRunner.run(tests);