text: // Copyright (C) 2017 André Bargull. All rights reserved.
  // This code is governed by the BSD license found in the LICENSE file.
  
  /*---
  esid: sec-array.prototype.reverse
  description: >
    Ensure correct MOP operations are called when length exceeds 2^53-1.
  includes: [compareArray.js, proxyTrapsHelper.js]
  ---*/
  
  function StopReverse() { }
  
  var arrayLike = {
    0: "zero",
    /* 1: hole, */
    2: "two",
    /* 3: hole, */
  
    get 4() {
      throw new StopReverse();
    },
  
    9007199254740987: "2**53-5",
    /* 9007199254740988: hole, */
    /* 9007199254740989: hole, */
    9007199254740990: "2**53-2",
  
    length: 2**53 + 2,
  };
  
  var traps = [];
  
  var proxy = new Proxy(arrayLike, allowProxyTraps({
    getOwnPropertyDescriptor(t, pk) {
      traps.push(`GetOwnPropertyDescriptor:${String(pk)}`);
      return Reflect.getOwnPropertyDescriptor(t, pk);
    },
    defineProperty(t, pk, desc) {
      traps.push(`DefineProperty:${String(pk)}`);
      return Reflect.defineProperty(t, pk, desc);
    },
    has(t, pk) {
      traps.push(`Has:${String(pk)}`);
      return Reflect.has(t, pk);
    },
    get(t, pk, r) {
      traps.push(`Get:${String(pk)}`);
      return Reflect.get(t, pk, r);
    },
    set(t, pk, v, r) {
      traps.push(`Set:${String(pk)}`);
      return Reflect.set(t, pk, v, r);
    },
    deleteProperty(t, pk) {
      traps.push(`Delete:${String(pk)}`);
      return Reflect.deleteProperty(t, pk);
    },
  }))
  
  // Uses a separate exception than Test262Error, so that errors from allowProxyTraps
  // are properly propagated.
  assert.throws(StopReverse, function() {
    Array.prototype.reverse.call(proxy);
  });
  
  assert.compareArray(traps, [
    // Initial get length operation.
    "Get:length",
  
    // Lower and upper index are both present.
    "Has:0",
    "Get:0",
    "Has:9007199254740990",
    "Get:9007199254740990",
    "Set:0",
    "GetOwnPropertyDescriptor:0",
    "DefineProperty:0",
    "Set:9007199254740990",
    "GetOwnPropertyDescriptor:9007199254740990",
    "DefineProperty:9007199254740990",
  
    // Lower and upper index are both absent.
    "Has:1",
    "Has:9007199254740989",
  
    // Lower index is present, upper index is absent.
    "Has:2",
    "Get:2",
    "Has:9007199254740988",
    "Delete:2",
    "Set:9007199254740988",
    "GetOwnPropertyDescriptor:9007199254740988",
    "DefineProperty:9007199254740988",
  
    // Lower index is absent, upper index is present.
    "Has:3",
    "Has:9007199254740987",
    "Get:9007199254740987",
    "Set:3",
    "GetOwnPropertyDescriptor:3",
    "DefineProperty:3",
    "Delete:9007199254740987",
  
    // Stop exception.
    "Has:4",
    "Get:4",
  ]);
  
  assert.sameValue(arrayLike.length, 2**53 + 2, "Length property is not modified");
  
  assert.sameValue(arrayLike[0], "2**53-2", "Property at index 0");
  assert.sameValue(1 in arrayLike, false, "Property at index 1");
  assert.sameValue(2 in arrayLike, false, "Property at index 2");
  assert.sameValue(arrayLike[3], "2**53-5", "Property at index 3");
  
  assert.sameValue(9007199254740987 in arrayLike, false, "Property at index 2**53-5");
  assert.sameValue(arrayLike[9007199254740988], "two", "Property at index 2**53-4");
  assert.sameValue(9007199254740989 in arrayLike, false, "Property at index 2**53-3");
  assert.sameValue(arrayLike[9007199254740990], "zero", "Property at index 2**53-2");
  