diff --git a/test/built-ins/Promise/Symbol.species/prop-desc.js b/test/built-ins/Promise/Symbol.species/prop-desc.js
new file mode 100644
index 0000000000000000000000000000000000000000..3f0770773e0ebb19d0dd03839afb3f9566adc2af
--- /dev/null
+++ b/test/built-ins/Promise/Symbol.species/prop-desc.js
@@ -0,0 +1,25 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.4.6
+description: Promise `Symbol.species` property
+info: >
+    Promise[@@species] is an accessor property whose set accessor function is
+    undefined.
+
+    ES6 Section 17:
+
+    Every accessor property described in clauses 18 through 26 and in Annex B.2
+    has the attributes {[[Enumerable]]: false, [[Configurable]]: true } unless
+    otherwise specified.
+features: [Symbol.species]
+includes: [propertyHelper.js]
+---*/
+
+var desc = Object.getOwnPropertyDescriptor(Promise, Symbol.species);
+
+assert.sameValue(desc.set, undefined);
+assert.sameValue(typeof desc.get, 'function');
+
+verifyNotEnumerable(Promise, Symbol.species);
+verifyConfigurable(Promise, Symbol.species);
diff --git a/test/built-ins/Promise/Symbol.species/return-value.js b/test/built-ins/Promise/Symbol.species/return-value.js
new file mode 100644
index 0000000000000000000000000000000000000000..f2d8aaeb5a7c7cbcdea165a8bcd0b37337042b6e
--- /dev/null
+++ b/test/built-ins/Promise/Symbol.species/return-value.js
@@ -0,0 +1,14 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.4.6
+description: Promise `Symbol.species` accessor function return value
+info: >
+    1. Return the this value.
+features: [Symbol.species]
+---*/
+
+var desc = Object.getOwnPropertyDescriptor(Promise, Symbol.species);
+var thisValue = {};
+
+assert.sameValue(desc.get.call(thisValue), thisValue);
diff --git a/test/built-ins/Promise/all/ctx-ctor.js b/test/built-ins/Promise/all/ctx-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..83c0d53e99dc9fe6b55ba43a80c80f480c477dd4
--- /dev/null
+++ b/test/built-ins/Promise/all/ctx-ctor.js
@@ -0,0 +1,37 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.all` invoked on a constructor value
+es6id: 25.4.4.1
+info: >
+    1. Let C be the this value.
+    [...]
+    6. Let promiseCapability be NewPromiseCapability(C).
+    [...]
+    10. Let iteratorRecord be Record {[[iterator]]: iterator, [[done]]: false}.
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+    [...]
+    13. Return Completion(result).
+features: [class]
+---*/
+
+var executor = null;
+var callCount = 0;
+
+class SubPromise extends Promise {
+  constructor(a) {
+    super(a);
+    executor = a;
+    callCount += 1;
+  }
+}
+
+var instance = Promise.all.call(SubPromise);
+
+assert.sameValue(instance.constructor, SubPromise);
+assert.sameValue(instance instanceof SubPromise, true);
+
+assert.sameValue(callCount, 1);
+assert.sameValue(typeof executor, 'function');
diff --git a/test/built-ins/Promise/all/ctx-non-ctor.js b/test/built-ins/Promise/all/ctx-non-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..89c885b3ba58c175bc5b27b5d7b38f1efcd84b11
--- /dev/null
+++ b/test/built-ins/Promise/all/ctx-non-ctor.js
@@ -0,0 +1,20 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.all` invoked on a non-constructor value
+es6id: 25.4.4.1
+info: >
+    [...]
+    6. Let promiseCapability be NewPromiseCapability(C).
+    7. ReturnIfAbrupt(promiseCapability).
+
+    25.4.1.5 NewPromiseCapability ( C )
+
+    1. If IsConstructor(C) is false, throw a TypeError exception.
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.all.call(eval);
+});
diff --git a/test/built-ins/Promise/all/ctx-non-object.js b/test/built-ins/Promise/all/ctx-non-object.js
new file mode 100644
index 0000000000000000000000000000000000000000..d909bb7623ed4183b147e47922eff8b98d77ef97
--- /dev/null
+++ b/test/built-ins/Promise/all/ctx-non-object.js
@@ -0,0 +1,36 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.all` invoked on a non-object value
+es6id: 25.4.4.1
+info: >
+    1. Let C be the this value.
+    2. If Type(C) is not Object, throw a TypeError exception.
+features: [Symbol]
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.all.call(undefined, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.all.call(null, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.all.call(86, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.all.call('string', []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.all.call(true, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.all.call(Symbol(), []);
+});
diff --git a/test/built-ins/Promise/all/invoke-resolve-get-error.js b/test/built-ins/Promise/all/invoke-resolve-get-error.js
new file mode 100644
index 0000000000000000000000000000000000000000..d7b7a092ca3a31edcd5606eba3bce53a22161495
--- /dev/null
+++ b/test/built-ins/Promise/all/invoke-resolve-get-error.js
@@ -0,0 +1,37 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error retrieving the constructor's `resolve` method
+es6id: 25.4.4.1
+info: >
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.1.1 Runtime Semantics: PerformPromiseAll
+
+    [...]
+    6. Repeat
+        [...]
+        i. Let nextPromise be Invoke(constructor, "resolve", «nextValue»).
+        j. ReturnIfAbrupt(nextPromise ).
+---*/
+
+var error = new Test262Error();
+Object.defineProperty(Promise, 'resolve', {
+  get: function() { 
+    throw error;
+  }
+});
+
+Promise.all([new Promise(function() {})]).then(function() {
+  $ERROR('The promise should be rejected');
+}, function(reason) {
+  assert.sameValue(reason, error);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/all/invoke-resolve.js b/test/built-ins/Promise/all/invoke-resolve.js
new file mode 100644
index 0000000000000000000000000000000000000000..64ef8f2ca982ee27bd7e90923594f09f3b94df01
--- /dev/null
+++ b/test/built-ins/Promise/all/invoke-resolve.js
@@ -0,0 +1,52 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Invocation of the constructor's `resolve` method
+es6id: 25.4.4.1
+info: >
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+
+    [...]
+
+    25.4.4.1.1 Runtime Semantics: PerformPromiseAll
+
+    [...]
+    6. Repeat
+        [...]
+        i. Let nextPromise be Invoke(constructor, "resolve", «nextValue»).
+---*/
+
+var p1 = new Promise(function() {});
+var p2 = new Promise(function() {});
+var p3 = new Promise(function() {});
+var resolve = Promise.resolve;
+var callCount = 0;
+var current = p1;
+var next = p2;
+var afterNext = p3;
+
+Promise.resolve = function(nextValue) {
+  assert.sameValue(
+    nextValue, current, '`resolve` invoked with next iterated value'
+  );
+  assert.sameValue(
+    arguments.length, 1, '`resolve` invoked with a single argument'
+  );
+  assert.sameValue(this, Promise, '`this` value is the constructor');
+
+  current = next;
+  next = afterNext;
+  afterNext = null;
+
+  callCount += 1;
+
+  return resolve.apply(Promise, arguments);
+};
+
+Promise.all([p1, p2, p3]);
+
+assert.sameValue(
+  callCount, 3, '`resolve` invoked once for each iterated value'
+);
diff --git a/test/built-ins/Promise/all/invoke-then-error.js b/test/built-ins/Promise/all/invoke-then-error.js
new file mode 100644
index 0000000000000000000000000000000000000000..957093f2b5a7f529daf1b5515da1f1df03ad1545
--- /dev/null
+++ b/test/built-ins/Promise/all/invoke-then-error.js
@@ -0,0 +1,38 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error thrown when invoking the instance's `then` method
+es6id: 25.4.4.1
+info: >
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.1.1 Runtime Semantics: PerformPromiseAll
+
+    [...]
+    6. Repeat
+        [...]
+        r. Let result be Invoke(nextPromise, "then", «resolveElement,
+           resultCapability.[[Reject]]»).
+        s. ReturnIfAbrupt(result).
+---*/
+
+var promise = new Promise(function() {});
+var error = new Test262Error();
+
+promise.then = function() {
+  throw error;
+};
+
+Promise.all([promise]).then(function() {
+  $ERROR('The promise should be rejected');
+}, function(reason) {
+  assert.sameValue(reason, error);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/all/invoke-then.js b/test/built-ins/Promise/all/invoke-then.js
new file mode 100644
index 0000000000000000000000000000000000000000..e6418896426947152af6ff179fa7a4fd93c6fec9
--- /dev/null
+++ b/test/built-ins/Promise/all/invoke-then.js
@@ -0,0 +1,55 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Invocation of the instance's `then` method
+es6id: 25.4.4.1
+info: >
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+
+    [...]
+
+    25.4.4.1.1 Runtime Semantics: PerformPromiseAll
+
+    [...]
+    6. Repeat
+        [...]
+        r. Let result be Invoke(nextPromise, "then", «resolveElement,
+           resultCapability.[[Reject]]»).
+---*/
+
+var p1 = new Promise(function() {});
+var p2 = new Promise(function() {});
+var p3 = new Promise(function() {});
+var callCount = 0;
+var currentThis = p1;
+var nextThis = p2;
+var afterNextThis = p3;
+
+p1.then = p2.then = p3.then = function(a, b) {
+  assert.sameValue(typeof a, 'function', 'type of first argument');
+  assert.sameValue(
+    a.length,
+    1,
+    'ES6 25.4.1.3.2: The length property of a promise resolve function is 1.'
+  );
+  assert.sameValue(typeof b, 'function', 'type of second argument');
+  assert.sameValue(
+    b.length,
+    1,
+    'ES6 25.4.1.3.1: The length property of a promise reject function is 1.'
+  );
+  assert.sameValue(arguments.length, 2, '`then` invoked with two arguments');
+  assert.sameValue(this, currentThis, '`this` value');
+
+  currentThis = nextThis;
+  nextThis = afterNextThis;
+  afterNextThis = null;
+
+  callCount += 1;
+};
+
+Promise.all([p1, p2, p3]);
+
+assert.sameValue(callCount, 3, '`then` invoked once for every iterated value');
diff --git a/test/built-ins/Promise/all/iter-close.js b/test/built-ins/Promise/all/iter-close.js
new file mode 100644
index 0000000000000000000000000000000000000000..9496ca7de9f1b9b003179d9c5c13d08afcd90023
--- /dev/null
+++ b/test/built-ins/Promise/all/iter-close.js
@@ -0,0 +1,46 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Explicit iterator closing in response to error
+es6id: 25.4.4.1
+info: >
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.1.1 Runtime Semantics: PerformPromiseAll
+
+    [...]
+    6. Repeat
+        [...]
+        i. Let nextPromise be Invoke(constructor, "resolve", «nextValue»).
+        j. ReturnIfAbrupt(nextPromise ).
+features: [Symbol.iterator]
+---*/
+
+var iterDoneSpy = {};
+var callCount = 0;
+iterDoneSpy[Symbol.iterator] = function() {
+  return {
+    next: function() {
+      return { value: null, done: false };
+    },
+    return: function() {
+      callCount += 1;
+    }
+  };
+};
+
+Promise.resolve = function() {
+  throw new Error();
+};
+
+Promise.all(iterDoneSpy);
+
+assert.sameValue(callCount, 1);
diff --git a/test/built-ins/Promise/all/iter-next-val-err.js b/test/built-ins/Promise/all/iter-next-val-err.js
new file mode 100644
index 0000000000000000000000000000000000000000..902e7823e89df160cef36b8deb40291278ac4231
--- /dev/null
+++ b/test/built-ins/Promise/all/iter-next-val-err.js
@@ -0,0 +1,51 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error when accessing an iterator result's `value` property
+es6id: 25.4.4.1
+info: >
+    11. Let result be PerformPromiseAll(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.1.1 Runtime Semantics: PerformPromiseAll
+
+    [...]
+    6. Repeat
+        [...]
+        e. Let nextValue be IteratorValue(next).
+        f. If nextValue is an abrupt completion, set iteratorRecord.[[done]] to
+           true.
+        g. ReturnIfAbrupt(nextValue).
+features: [Symbol.iterator]
+---*/
+
+var iterNextValThrows = {};
+var poisonedVal = {
+  done: false
+};
+var error = new Test262Error();
+Object.defineProperty(poisonedVal, 'value', {
+  get: function() {
+    throw error;
+  }
+});
+iterNextValThrows[Symbol.iterator] = function() {
+  return {
+    next: function() {
+      return poisonedVal;
+    }
+  };
+};
+
+Promise.all(iterNextValThrows).then(function() {
+  $ERROR('The promise should be rejected.');
+}, function(reason) {
+  assert.sameValue(reason, error);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/all/species-get-error.js b/test/built-ins/Promise/all/species-get-error.js
new file mode 100644
index 0000000000000000000000000000000000000000..2deb108382a68d3a9f43cf5f2a1dbe22a5e2b293
--- /dev/null
+++ b/test/built-ins/Promise/all/species-get-error.js
@@ -0,0 +1,25 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error thrown when retrieving `Symbol.species` property of the `this` value
+es6id: 25.4.4.1
+info: >
+    1. Let C be the this value.
+    2. If Type(C) is not Object, throw a TypeError exception.
+    3. Let S be Get(C, @@species).
+    4. ReturnIfAbrupt(S).
+features: [Symbol.species]
+---*/
+
+var C = {};
+Object.defineProperty(C, Symbol.species, {
+  get: function() {
+    throw new Test262Error();
+  }
+});
+
+assert.throws(Test262Error, function() {
+  Promise.all.call(C);
+});
diff --git a/test/built-ins/Promise/exec-args.js b/test/built-ins/Promise/exec-args.js
new file mode 100644
index 0000000000000000000000000000000000000000..524c1edaa232f6c714f0ff83ac75b312eeae7b27
--- /dev/null
+++ b/test/built-ins/Promise/exec-args.js
@@ -0,0 +1,33 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+es6id: 25.4.3.1
+description: Promise executor is invoked synchronously
+info: >
+    9. Let completion be Call(executor, undefined,
+       «resolvingFunctions.[[Resolve]], resolvingFunctions.[[Reject]]»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    The length property of a promise resolve function is 1.
+
+    25.4.1.3.1 Promise Reject Functions
+
+    The length property of a promise reject function is 1.
+---*/
+
+var callCount = 0;
+var resolve, reject, argCount;
+
+new Promise(function(a, b) {
+  resolve = a;
+  reject = b;
+  argCount = arguments.length;
+});
+
+assert.sameValue(typeof resolve, 'function', 'type of first argument');
+assert.sameValue(resolve.length, 1, 'length of first argument');
+assert.sameValue(typeof reject, 'function', 'type of second argument');
+assert.sameValue(reject.length, 1, 'length of second argument');
+assert.sameValue(argCount, 2);
diff --git a/test/built-ins/Promise/prototype/catch/invokes-then.js b/test/built-ins/Promise/prototype/catch/invokes-then.js
new file mode 100644
index 0000000000000000000000000000000000000000..8c05f64578b920f260593a3f4c611837c458a24f
--- /dev/null
+++ b/test/built-ins/Promise/prototype/catch/invokes-then.js
@@ -0,0 +1,52 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.1
+description: Promise.prototype.catch invokes `then` method
+info: >
+    1. Let promise be the this value.
+    2. Return Invoke(promise, "then", «undefined, onRejected»).
+---*/
+
+var target = {};
+var returnValue = {};
+var callCount = 0;
+var thisValue = null;
+var argCount = null;
+var firstArg = null;
+var secondArg = null;
+var result = null;
+
+target.then = function(a, b) {
+  callCount += 1;
+
+  thisValue = this;
+  argCount = arguments.length;
+  firstArg = a;
+  secondArg = b;
+
+  return returnValue;
+};
+
+result = Promise.prototype.catch.call(target, 1, 2, 3);
+
+assert.sameValue(callCount, 1, 'Invokes `then` method exactly once');
+assert.sameValue(
+  thisValue,
+  target,
+  'Invokes `then` method with the instance as the `this` value'
+);
+assert.sameValue(
+  argCount, 2, 'Invokes `then` method with exactly two single arguments'
+);
+assert.sameValue(
+  firstArg,
+  undefined,
+  'Invokes `then` method with `undefined` as the first argument'
+);
+assert.sameValue(
+  secondArg, 1, 'Invokes `then` method with the provided argument'
+);
+assert.sameValue(
+  result, returnValue, 'Returns the result of the invocation of `then`'
+);
diff --git a/test/built-ins/Promise/prototype/then/ctor-custom.js b/test/built-ins/Promise/prototype/then/ctor-custom.js
new file mode 100644
index 0000000000000000000000000000000000000000..246d7914abd7b01b31db8faa8023684b5eda3faa
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/ctor-custom.js
@@ -0,0 +1,49 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The constructor defined by Symbol.species takes precedence
+info: >
+    1. Let promise be the this value.
+    2. If IsPromise(promise) is false, throw a TypeError exception.
+    3. Let C be SpeciesConstructor(promise, %Promise%).
+    4. ReturnIfAbrupt(C).
+    5. Let resultCapability be NewPromiseCapability(C).
+features: [Symbol.species, class]
+---*/
+
+var callCount = 0;
+var thisValue, firstArg, argLength, getCapabilitiesExecutor;
+var executor = function() {};
+var p1 = new Promise(function() {});
+var SpeciesConstructor = class extends Promise {
+  constructor(a) {
+    super(a);
+    callCount += 1;
+    thisValue = this;
+    getCapabilitiesExecutor = a;
+    argLength = arguments.length;
+  }
+};
+var p2;
+
+p1.constructor = function() {};
+p1.constructor[Symbol.species] = SpeciesConstructor;
+
+p2 = p1.then();
+
+assert.sameValue(callCount, 1, 'The constructor is invoked exactly once');
+assert(thisValue instanceof SpeciesConstructor);
+assert.sameValue(
+  argLength, 1, 'The constructor is invoked with a single argument'
+);
+assert.sameValue(typeof getCapabilitiesExecutor, 'function');
+assert.sameValue(
+  getCapabilitiesExecutor.length,
+  2,
+  'ES6 25.4.1.5.1: The length property of a GetCapabilitiesExecutor function is 2.'
+);
+assert(
+  p2 instanceof SpeciesConstructor,
+  'The returned object is an instance of the constructor'
+);
diff --git a/test/built-ins/Promise/prototype/then/ctor-null.js b/test/built-ins/Promise/prototype/then/ctor-null.js
new file mode 100644
index 0000000000000000000000000000000000000000..11f4eca54579e2987feb431d749c7fda2658f332
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/ctor-null.js
@@ -0,0 +1,20 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: >
+    A TypeError is thrown when the `this` value has a non-object `constructor` property
+info: >
+    1. Let promise be the this value.
+    2. If IsPromise(promise) is false, throw a TypeError exception.
+    3. Let C be SpeciesConstructor(promise, %Promise%).
+    4. ReturnIfAbrupt(C).
+    5. Let resultCapability be NewPromiseCapability(C).
+---*/
+
+var p = new Promise(function() {});
+p.constructor = null;
+
+assert.throws(TypeError, function() {
+  p.then();
+});
diff --git a/test/built-ins/Promise/prototype/then/S25.4.5.3_A3.1_T1.js b/test/built-ins/Promise/prototype/then/ctor-poisoned.js
similarity index 100%
rename from test/built-ins/Promise/prototype/then/S25.4.5.3_A3.1_T1.js
rename to test/built-ins/Promise/prototype/then/ctor-poisoned.js
diff --git a/test/built-ins/Promise/prototype/then/ctor-undef.js b/test/built-ins/Promise/prototype/then/ctor-undef.js
new file mode 100644
index 0000000000000000000000000000000000000000..eae1c4c1d1ea2584576093375bd195a87727d8ed
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/ctor-undef.js
@@ -0,0 +1,20 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: >
+    The Promise built-in is used when the `this` value has no `constructor` property
+info: >
+    1. Let promise be the this value.
+    2. If IsPromise(promise) is false, throw a TypeError exception.
+    3. Let C be SpeciesConstructor(promise, %Promise%).
+    4. ReturnIfAbrupt(C).
+    5. Let resultCapability be NewPromiseCapability(C).
+---*/
+
+var p1 = new Promise(function() {});
+delete p1.constructor;
+
+var p2 = p1.then();
+
+assert(p2 instanceof Promise);
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-poisoned-then.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-poisoned-then.js
new file mode 100644
index 0000000000000000000000000000000000000000..1b6fcb0c633decd34e395c2cc6ea55451dd36fe1
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-poisoned-then.js
@@ -0,0 +1,46 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: >
+    Access error for the `then` property of the object returned from the "on fulfilled" handler
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+---*/
+
+var poisonedThen = {};
+var error = new Test262Error();
+Object.defineProperty(poisonedThen, 'then', {
+  get: function() {
+    throw error;
+  }
+});
+
+var p = new Promise(function(r) { r(); });
+
+p.then(function() {
+  return poisonedThen;
+}).then(function() {
+  $DONE('The promise should not be fulfilled');
+}, function(reason) {
+  assert.sameValue(reason, error);
+
+  $DONE();
+});
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-fulfilled.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-fulfilled.js
new file mode 100644
index 0000000000000000000000000000000000000000..4e63f8502de6d88c96cdd9031891641a35ae2e8f
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-fulfilled.js
@@ -0,0 +1,70 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onFulfilled` method is a fulfilled promise
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+    10. Let thenAction be then.[[value]].
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob, «promise,
+        resolution, thenAction»)
+    13. Return undefined.
+---*/
+
+var executor1Counter = 0;
+var thenCounter = 0;
+var executor2Counter = 0;
+var promise = new Promise(function(resolve) {
+    resolve();
+
+    assert.sameValue(executor1Counter, 0);
+    assert.sameValue(thenCounter, 0);
+    assert.sameValue(executor2Counter, 0);
+
+    executor1Counter += 1;
+  });
+
+promise.then(function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(thenCounter, 0);
+    assert.sameValue(executor2Counter, 0);
+
+    thenCounter += 1;
+
+    return new Promise(function(resolve) {
+      resolve();
+
+      assert.sameValue(executor1Counter, 1);
+      assert.sameValue(thenCounter, 1);
+      assert.sameValue(executor2Counter, 0);
+
+      executor2Counter += 1;
+    });
+  }).then(function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(thenCounter, 1);
+    assert.sameValue(executor2Counter, 1);
+
+    $DONE();
+  }, function() {
+    $DONE('The promise should not be rejected');
+  });
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-pending-to-fulfilled.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-pending-to-fulfilled.js
new file mode 100644
index 0000000000000000000000000000000000000000..ff0791c5e3df54f746dd53ceb48dd07cf4ecd6b5
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-pending-to-fulfilled.js
@@ -0,0 +1,84 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onFulfilled` method is a pending promise
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+    10. Let thenAction be then.[[value]].
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob, «promise,
+        resolution, thenAction»)
+    13. Return undefined.
+---*/
+
+var executor1Counter = 0;
+var then1Counter = 0;
+var executor2Counter = 0;
+var then2Counter = 0;
+var promise = new Promise(function(resolve) {
+    resolve();
+
+    assert.sameValue(executor1Counter, 0);
+    assert.sameValue(then1Counter, 0);
+    assert.sameValue(executor2Counter, 0);
+    assert.sameValue(then2Counter, 0);
+
+    executor1Counter += 1;
+  });
+
+promise.then(function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(then1Counter, 0);
+    assert.sameValue(executor2Counter, 0);
+    assert.sameValue(then2Counter, 0);
+
+    then1Counter += 1;
+
+    return new Promise(function(resolve) {
+      promise.then(function() {
+        resolve();
+
+        assert.sameValue(executor1Counter, 1);
+        assert.sameValue(then1Counter, 1);
+        assert.sameValue(executor2Counter, 1);
+        assert.sameValue(then2Counter, 0);
+
+        then2Counter += 1;
+      });
+
+      assert.sameValue(executor1Counter, 1);
+      assert.sameValue(then1Counter, 1);
+      assert.sameValue(executor2Counter, 0);
+      assert.sameValue(then2Counter, 0);
+
+      executor2Counter += 1;
+    });
+  }).then(function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(then1Counter, 1);
+    assert.sameValue(executor2Counter, 1);
+    assert.sameValue(then2Counter, 1);
+
+    $DONE();
+  }, function() {
+    $DONE('The promise should not be rejected');
+  });
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-pending-to-rejected.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-pending-to-rejected.js
new file mode 100644
index 0000000000000000000000000000000000000000..2b3613c7befdfe63e9e41a3a95a44b67f7e54922
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-pending-to-rejected.js
@@ -0,0 +1,84 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onFulfilled` method is a pending promise
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+    10. Let thenAction be then.[[value]].
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob, «promise,
+        resolution, thenAction»)
+    13. Return undefined.
+---*/
+
+var executor1Counter = 0;
+var then1Counter = 0;
+var executor2Counter = 0;
+var then2Counter = 0;
+var promise = new Promise(function(resolve) {
+    resolve();
+
+    assert.sameValue(executor1Counter, 0);
+    assert.sameValue(then1Counter, 0);
+    assert.sameValue(executor2Counter, 0);
+    assert.sameValue(then2Counter, 0);
+
+    executor1Counter += 1;
+  });
+
+promise.then(function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(then1Counter, 0);
+    assert.sameValue(executor2Counter, 0);
+    assert.sameValue(then2Counter, 0);
+
+    then1Counter += 1;
+
+    return new Promise(function(_, reject) {
+      promise.then(function() {
+        reject();
+
+        assert.sameValue(executor1Counter, 1);
+        assert.sameValue(then1Counter, 1);
+        assert.sameValue(executor2Counter, 1);
+        assert.sameValue(then2Counter, 0);
+
+        then2Counter += 1;
+      });
+
+      assert.sameValue(executor1Counter, 1);
+      assert.sameValue(then1Counter, 1);
+      assert.sameValue(executor2Counter, 0);
+      assert.sameValue(then2Counter, 0);
+
+      executor2Counter += 1;
+    });
+  }).then(function() {
+    $DONE('The promise should not be fulfilled');
+  }, function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(then1Counter, 1);
+    assert.sameValue(executor2Counter, 1);
+    assert.sameValue(then2Counter, 1);
+
+    $DONE();
+  });
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-rejected.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-rejected.js
new file mode 100644
index 0000000000000000000000000000000000000000..47948dc48013e68defbe008b6b1cca87f2ad2139
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-prms-rejected.js
@@ -0,0 +1,70 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onFulfilled` method is a rejected promise
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+    10. Let thenAction be then.[[value]].
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob, «promise,
+        resolution, thenAction»)
+    13. Return undefined.
+---*/
+
+var executor1Counter = 0;
+var thenCounter = 0;
+var executor2Counter = 0;
+var promise = new Promise(function(resolve) {
+    resolve();
+
+    assert.sameValue(executor1Counter, 0);
+    assert.sameValue(thenCounter, 0);
+    assert.sameValue(executor2Counter, 0);
+
+    executor1Counter += 1;
+  });
+
+promise.then(function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(thenCounter, 0);
+    assert.sameValue(executor2Counter, 0);
+
+    thenCounter += 1;
+
+    return new Promise(function(_, reject) {
+      reject();
+
+      assert.sameValue(executor1Counter, 1);
+      assert.sameValue(thenCounter, 1);
+      assert.sameValue(executor2Counter, 0);
+
+      executor2Counter += 1;
+    });
+  }).then(function() {
+    $DONE('The promise should not be fulfilled');
+  }, function() {
+    assert.sameValue(executor1Counter, 1);
+    assert.sameValue(thenCounter, 1);
+    assert.sameValue(executor2Counter, 1);
+
+    $DONE();
+  });
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-self.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-self.js
new file mode 100644
index 0000000000000000000000000000000000000000..42e2588ef4a66ca9436c0a145df5293f873388fb
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-self.js
@@ -0,0 +1,41 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onFulfilled` method is a "thenable" object
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    6. If SameValue(resolution, promise) is true, then
+       a. Let selfResolutionError be a newly created TypeError object.
+       b. Return RejectPromise(promise, selfResolutionError).
+---*/
+
+var promise1 = new Promise(function(resolve) {
+  resolve();
+});
+
+var promise2 = promise1.then(function() {
+  return promise2;
+});
+
+promise2.then(function() {
+  $DONE('This promise should not be resolved');
+}, function(reason) {
+  assert.sameValue(reason.constructor, TypeError);
+
+  $DONE();
+});
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-return-thenable.js b/test/built-ins/Promise/prototype/then/on-fulfilled-return-thenable.js
new file mode 100644
index 0000000000000000000000000000000000000000..1a7974b718bab736514b5329627869b493956f2a
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-return-thenable.js
@@ -0,0 +1,70 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onFulfilled` method is a "thenable" object
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+    10. Let thenAction be then.[[value]].
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob, «promise,
+        resolution, thenAction»)
+    13. Return undefined.
+---*/
+
+var callCount = 0;
+var promise = new Promise(function(resolve) {
+  resolve();
+});
+
+var thenable = {
+  then: function(resolve, reject) {
+    assert.sameValue(
+      this, thenable, 'method invoked with correct `this` value'
+    );
+    assert.sameValue(typeof resolve, 'function', 'type of first argument');
+    assert.sameValue(
+      resolve.length,
+      1,
+      'ES6 25.4.1.3.2: The length property of a promise resolve function is 1.'
+    );
+    assert.sameValue(typeof reject, 'function', 'type of second argument');
+    assert.sameValue(
+      reject.length,
+      1,
+      'ES6 25.4.1.3.1: The length property of a promise reject function is 1.'
+    );
+    assert.sameValue(arguments.length, 2, 'total number of arguments');
+    resolve();
+
+    callCount += 1;
+  }
+};
+
+promise.then(function() {
+  return thenable;
+}).then(function() {
+  assert.sameValue(callCount, 1);
+
+  $DONE();
+}, function() {
+  $DONE('This promise should not be rejected');
+});
diff --git a/test/built-ins/Promise/prototype/then/on-fulfilled-throw.js b/test/built-ins/Promise/prototype/then/on-fulfilled-throw.js
new file mode 100644
index 0000000000000000000000000000000000000000..434cd57953c0202401e60210dc58f8e628a74ae3
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-fulfilled-throw.js
@@ -0,0 +1,57 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The `onFulfilled` method throws an error
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    8. Else if the value of promise's [[PromiseState]] internal slot is
+       "fulfilled",
+       a. Let value be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «fulfillReaction, value»).
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    [...]
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+    10. Let thenAction be then.[[value]].
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob, «promise,
+        resolution, thenAction»)
+    13. Return undefined.
+
+    25.4.2.2 PromiseResolveThenableJob
+
+    2. Let thenCallResult be Call(then, thenable,
+       «resolvingFunctions.[[Resolve]], resolvingFunctions.[[Reject]]»).
+    3. If thenCallResult is an abrupt completion,
+       a. Let status be Call(resolvingFunctions.[[Reject]], undefined,
+          «thenCallResult.[[value]]»).
+       b. NextJob Completion(status).
+---*/
+
+var error = new Test262Error();
+var promiseFulfilled = false;
+var promiseRejected = false;
+var promise = new Promise(function(resolve) {
+    resolve();
+  });
+
+promise.then(function() {
+    throw error;
+  }).then(function() {
+    $DONE('This promise should not be fulfilled');
+  }, function(reason) {
+    assert.sameValue(reason, error);
+
+    $DONE();
+  });
diff --git a/test/built-ins/Promise/prototype/then/on-rejected-return-value.js b/test/built-ins/Promise/prototype/then/on-rejected-return-value.js
new file mode 100644
index 0000000000000000000000000000000000000000..14f7c2df910f917ffbe5901f822e69b21dac0b59
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-rejected-return-value.js
@@ -0,0 +1,33 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The return value of the `onRejected` method
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    9. Else if the value of promise's [[PromiseState]] internal slot is
+       "rejected",
+       a. Let reason be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «rejectReaction, reason»).
+---*/
+
+var returnVal = {};
+var promise = new Promise(function(_, reject) {
+  reject();
+});
+
+promise.then(null, function() {
+  return returnVal;
+}).then(function(result) {
+  assert.sameValue(result, returnVal);
+
+  $DONE();
+}, function() {
+  $DONE('The promise should not be rejected');
+});
diff --git a/test/built-ins/Promise/prototype/then/on-rejected-throw.js b/test/built-ins/Promise/prototype/then/on-rejected-throw.js
new file mode 100644
index 0000000000000000000000000000000000000000..b218329cff5a0c7826a80d2d295544444b7bce7b
--- /dev/null
+++ b/test/built-ins/Promise/prototype/then/on-rejected-throw.js
@@ -0,0 +1,33 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+/*---
+es6id: 25.4.5.3
+description: The `onRejected` method throws an error
+info: >
+    7. Return PerformPromiseThen(promise, onFulfilled, onRejected,
+       resultCapability).
+
+    25.4.5.3.1 PerformPromiseThen
+
+    [...]
+    9. Else if the value of promise's [[PromiseState]] internal slot is
+       "rejected",
+       a. Let reason be the value of promise's [[PromiseResult]] internal slot.
+       b. Perform EnqueueJob("PromiseJobs", PromiseReactionJob,
+          «rejectReaction, reason»).
+---*/
+
+var error = new Test262Error();
+var promise = new Promise(function(_, reject) {
+  reject();
+});
+
+promise.then(null, function() {
+  throw error;
+  }).then(function(result) {
+    $DONE('This promise should not be fulfilled');
+  }, function(reason) {
+    assert.sameValue(reason, error);
+
+    $DONE();
+  });
diff --git a/test/built-ins/Promise/race/ctx-ctor.js b/test/built-ins/Promise/race/ctx-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..4f8c161772cc2032e702aa9bffd14cbb9ffe6056
--- /dev/null
+++ b/test/built-ins/Promise/race/ctx-ctor.js
@@ -0,0 +1,37 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.race` invoked on a constructor value
+es6id: 25.4.4.3
+info: >
+    1. Let C be the this value.
+    [...]
+    6. Let promiseCapability be NewPromiseCapability(C).
+    [...]
+    10. Let iteratorRecord be Record {[[iterator]]: iterator, [[done]]: false}.
+    11. Let result be PerformPromiseRace(iteratorRecord, promiseCapability, C).
+    [...]
+    13. Return Completion(result).
+features: [class]
+---*/
+
+var executor = null;
+var callCount = 0;
+
+class SubPromise extends Promise {
+  constructor(a) {
+    super(a);
+    executor = a;
+    callCount += 1;
+  }
+}
+
+var instance = Promise.race.call(SubPromise);
+
+assert.sameValue(instance.constructor, SubPromise);
+assert.sameValue(instance instanceof SubPromise, true);
+
+assert.sameValue(callCount, 1);
+assert.sameValue(typeof executor, 'function');
diff --git a/test/built-ins/Promise/race/ctx-non-ctor.js b/test/built-ins/Promise/race/ctx-non-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..542c07674a9aa8f5af5247ef10a8d104e01d40ac
--- /dev/null
+++ b/test/built-ins/Promise/race/ctx-non-ctor.js
@@ -0,0 +1,20 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.race` invoked on a non-constructor value
+es6id: 25.4.4.3
+info: >
+    [...]
+    6. Let promiseCapability be NewPromiseCapability(C).
+    7. ReturnIfAbrupt(promiseCapability).
+
+    25.4.1.5 NewPromiseCapability ( C )
+
+    1. If IsConstructor(C) is false, throw a TypeError exception.
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.race.call(eval);
+});
diff --git a/test/built-ins/Promise/race/ctx-non-object.js b/test/built-ins/Promise/race/ctx-non-object.js
new file mode 100644
index 0000000000000000000000000000000000000000..b21f9564135952bc9576b473e716314e1942fa79
--- /dev/null
+++ b/test/built-ins/Promise/race/ctx-non-object.js
@@ -0,0 +1,36 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.race` invoked on a non-object value
+es6id: 25.4.4.3
+info: >
+    1. Let C be the this value.
+    2. If Type(C) is not Object, throw a TypeError exception.
+features: [Symbol]
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.race.call(undefined, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.race.call(null, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.race.call(86, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.race.call('string', []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.race.call(true, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.race.call(Symbol(), []);
+});
diff --git a/test/built-ins/Promise/race/invoke-resolve-get-error.js b/test/built-ins/Promise/race/invoke-resolve-get-error.js
new file mode 100644
index 0000000000000000000000000000000000000000..2ed029d5e90fa9d324cc51b1c4cbb2b16411b4ed
--- /dev/null
+++ b/test/built-ins/Promise/race/invoke-resolve-get-error.js
@@ -0,0 +1,36 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error retrieving the constructor's `resolve` method
+es6id: 25.4.4.3
+info: >
+    11. Let result be PerformPromiseRace(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.3.1 Runtime Semantics: PerformPromiseRace
+
+    1. Repeat
+        [...]
+        h. Let nextPromise be Invoke(C, "resolve", «nextValue»).
+        i. ReturnIfAbrupt(nextPromise).
+---*/
+
+var error = new Test262Error();
+Object.defineProperty(Promise, 'resolve', {
+  get: function() { 
+    throw error;
+  }
+});
+
+Promise.race([new Promise(function() {})]).then(function() {
+  $ERROR('The promise should be rejected');
+}, function(reason) {
+  assert.sameValue(reason, error);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/race/invoke-resolve.js b/test/built-ins/Promise/race/invoke-resolve.js
new file mode 100644
index 0000000000000000000000000000000000000000..b7107f03e9c6ca3b2da1fbc4362615f5e0bf2d62
--- /dev/null
+++ b/test/built-ins/Promise/race/invoke-resolve.js
@@ -0,0 +1,51 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Invocation of the constructor's `resolve` method
+es6id: 25.4.4.3
+info: >
+    11. Let result be PerformPromiseRace(iteratorRecord, C, promiseCapability).
+
+    [...]
+
+    25.4.4.3.1 Runtime Semantics: PerformPromiseRace
+
+    1. Repeat
+        [...]
+        h. Let nextPromise be Invoke(C, "resolve", «nextValue»).
+---*/
+
+var p1 = new Promise(function() {});
+var p2 = new Promise(function() {});
+var p3 = new Promise(function() {});
+var resolve = Promise.resolve;
+var callCount = 0;
+var current = p1;
+var next = p2;
+var afterNext = p3;
+
+Promise.resolve = function(nextValue) {
+  assert.sameValue(
+    nextValue, current, '`resolve` invoked with next iterated value'
+  );
+  assert.sameValue(
+    arguments.length, 1, '`resolve` invoked with a single argument'
+  );
+  assert.sameValue(this, Promise, '`this` value set to the constructor');
+
+  current = next;
+  next = afterNext;
+  afterNext = null;
+
+  callCount += 1;
+
+  return resolve.apply(Promise, arguments);
+};
+
+Promise.race([p1, p2, p3]);
+
+assert.sameValue(
+  callCount, 3, '`resolve` invoked once for each iterated value'
+);
diff --git a/test/built-ins/Promise/race/invoke-then-error.js b/test/built-ins/Promise/race/invoke-then-error.js
new file mode 100644
index 0000000000000000000000000000000000000000..b2f79f53439774e81d5118f0f9bda835e3f71d6f
--- /dev/null
+++ b/test/built-ins/Promise/race/invoke-then-error.js
@@ -0,0 +1,37 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error thrown when invoking the instance's `then` method
+es6id: 25.4.4.3
+info: >
+    11. Let result be PerformPromiseRace(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.3.1 Runtime Semantics: PerformPromiseRace
+
+    1. Repeat
+        [...]
+        j. Let result be Invoke(nextPromise, "then",
+           «promiseCapability.[[Resolve]], promiseCapability.[[Reject]]»).
+        k. ReturnIfAbrupt(result).
+---*/
+
+var promise = new Promise(function() {});
+var error = new Test262Error();
+
+promise.then = function() {
+  throw error;
+};
+
+Promise.race([promise]).then(function() {
+  $ERROR('The promise should be rejected');
+}, function(reason) {
+  assert.sameValue(reason, error);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/race/invoke-then.js b/test/built-ins/Promise/race/invoke-then.js
new file mode 100644
index 0000000000000000000000000000000000000000..4d1db6d56e8517d44591c5a16de6472255e2ff7b
--- /dev/null
+++ b/test/built-ins/Promise/race/invoke-then.js
@@ -0,0 +1,55 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Invocation of the instance's `then` method
+es6id: 25.4.4.3
+info: >
+    11. Let result be PerformPromiseRace(iteratorRecord, C, promiseCapability).
+
+    [...]
+
+    25.4.4.3.1 Runtime Semantics: PerformPromiseRace
+
+    1. Repeat
+        [...]
+        j. Let result be Invoke(nextPromise, "then",
+           «promiseCapability.[[Resolve]], promiseCapability.[[Reject]]»).
+        k. ReturnIfAbrupt(result).
+---*/
+
+var p1 = new Promise(function() {});
+var p2 = new Promise(function() {});
+var p3 = new Promise(function() {});
+var callCount = 0;
+var currentThis = p1;
+var nextThis = p2;
+var afterNextThis = p3;
+
+p1.then = p2.then = p3.then = function(a, b) {
+  assert.sameValue(typeof a, 'function', 'type of first argument');
+  assert.sameValue(
+    a.length,
+    1,
+    'ES6 25.4.1.3.2: The length property of a promise resolve function is 1.'
+  );
+  assert.sameValue(typeof b, 'function', 'type of second argument');
+  assert.sameValue(
+    b.length,
+    1,
+    'ES6 25.4.1.3.1: The length property of a promise reject function is 1.'
+  );
+  assert.sameValue(arguments.length, 2, '`then` invoked with two arguments');
+  assert.sameValue(this, currentThis, '`this` value');
+
+  currentThis = nextThis;
+  nextThis = afterNextThis;
+  afterNextThis = null;
+
+  callCount += 1;
+};
+
+Promise.race([p1, p2, p3]);
+
+assert.sameValue(callCount, 3, '`then` invoked once for every iterated value');
diff --git a/test/built-ins/Promise/race/iter-next-val-err.js b/test/built-ins/Promise/race/iter-next-val-err.js
new file mode 100644
index 0000000000000000000000000000000000000000..eca773a9e64a437191d689be7b0f6665e447ed15
--- /dev/null
+++ b/test/built-ins/Promise/race/iter-next-val-err.js
@@ -0,0 +1,50 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error when accessing an iterator result's `value` property
+es6id: 25.4.4.3
+info: >
+    11. Let result be PerformPromiseRace(iteratorRecord, C, promiseCapability).
+    12. If result is an abrupt completion,
+        a. If iteratorRecord.[[done]] is false, let result be
+           IteratorClose(iterator, result).
+        b. IfAbruptRejectPromise(result, promiseCapability).
+
+    [...]
+
+    25.4.4.3.1 Runtime Semantics: PerformPromiseRace
+
+    1. Repeat
+        [...]
+        e. Let nextValue be IteratorValue(next).
+        f. If nextValue is an abrupt completion, set iteratorRecord.[[done]] to
+           true.
+        g. ReturnIfAbrupt(nextValue).
+features: [Symbol.iterator]
+---*/
+
+var iterNextValThrows = {};
+var poisonedVal = {
+  done: false
+};
+var error = new Test262Error();
+Object.defineProperty(poisonedVal, 'value', {
+  get: function() {
+    throw error;
+  }
+});
+iterNextValThrows[Symbol.iterator] = function() {
+  return {
+    next: function() {
+      return poisonedVal;
+    }
+  };
+};
+
+Promise.race(iterNextValThrows).then(function() {
+  $ERROR('The promise should be rejected.');
+}, function(reason) {
+  assert.sameValue(reason, error);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/race/species-get-error.js b/test/built-ins/Promise/race/species-get-error.js
new file mode 100644
index 0000000000000000000000000000000000000000..78b01acf1579a74c50e9ebf14819bd354b30d750
--- /dev/null
+++ b/test/built-ins/Promise/race/species-get-error.js
@@ -0,0 +1,25 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    Error thrown when retrieving `Symbol.species` property of the `this` value
+es6id: 25.4.4.3
+info: >
+    1. Let C be the this value.
+    2. If Type(C) is not Object, throw a TypeError exception.
+    3. Let S be Get(C, @@species).
+    4. ReturnIfAbrupt(S).
+features: [Symbol.species]
+---*/
+
+var C = {};
+Object.defineProperty(C, Symbol.species, {
+  get: function() {
+    throw new Test262Error();
+  }
+});
+
+assert.throws(Test262Error, function() {
+  Promise.race.call(C);
+});
diff --git a/test/built-ins/Promise/reject/ctx-ctor.js b/test/built-ins/Promise/reject/ctx-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..a270a2fa549583bd16cb0fdcfd89cfdcee8b380a
--- /dev/null
+++ b/test/built-ins/Promise/reject/ctx-ctor.js
@@ -0,0 +1,34 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.reject` invoked on a constructor value
+es6id: 25.4.4.5
+info: >
+    1. Let C be the this value.
+    [...]
+    3. Let promiseCapability be NewPromiseCapability(C).
+    [...]
+    7. Return promiseCapability.[[Promise]].
+features: [class]
+---*/
+
+var executor = null;
+var callCount = 0;
+
+class SubPromise extends Promise {
+  constructor(a) {
+    super(a);
+    executor = a;
+    callCount += 1;
+  }
+}
+
+var instance = Promise.reject.call(SubPromise);
+
+assert.sameValue(instance.constructor, SubPromise);
+assert.sameValue(instance instanceof SubPromise, true);
+
+assert.sameValue(callCount, 1);
+assert.sameValue(typeof executor, 'function');
diff --git a/test/built-ins/Promise/reject/ctx-non-ctor.js b/test/built-ins/Promise/reject/ctx-non-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..a01eb4da20527bbb4cc1d0d218a0143f8a700e9a
--- /dev/null
+++ b/test/built-ins/Promise/reject/ctx-non-ctor.js
@@ -0,0 +1,16 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.reject` invoked on a non-constructor value
+es6id: 25.4.4.4
+info: >
+    [...]
+    3. Let promiseCapability be NewPromiseCapability(C).
+    4. ReturnIfAbrupt(promiseCapability).
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.reject.call(eval);
+});
diff --git a/test/built-ins/Promise/reject/ctx-non-object.js b/test/built-ins/Promise/reject/ctx-non-object.js
new file mode 100644
index 0000000000000000000000000000000000000000..0f37e09b98ea0b40589e0a8ddbc9b4e0042a1240
--- /dev/null
+++ b/test/built-ins/Promise/reject/ctx-non-object.js
@@ -0,0 +1,36 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked on a non-object value
+es6id: 25.4.4.4
+info: >
+    1. Let C be the this value.
+    2. If Type(C) is not Object, throw a TypeError exception.
+features: [Symbol]
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.reject.call(undefined, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.reject.call(null, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.reject.call(86, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.reject.call('string', []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.reject.call(true, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.reject.call(Symbol(), []);
+});
diff --git a/test/built-ins/Promise/resolve/arg-non-thenable.js b/test/built-ins/Promise/resolve/arg-non-thenable.js
new file mode 100644
index 0000000000000000000000000000000000000000..2aa032efac4624c541ccc712ac2a942d6af50407
--- /dev/null
+++ b/test/built-ins/Promise/resolve/arg-non-thenable.js
@@ -0,0 +1,29 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked with an object whose `then` property is not callable
+es6id: 25.4.4.5
+info: >
+    6. Let resolveResult be Call(promiseCapability.[[Resolve]], undefined,
+       «x»).
+
+    [...]
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    11. If IsCallable(thenAction) is false, then
+        a. Return FulfillPromise(promise, resolution).
+    12. Perform EnqueueJob ("PromiseJobs", PromiseResolveThenableJob,
+        «promise, resolution, thenAction»)
+    13. Return undefined.
+---*/
+
+var nonThenable = {
+  then: null
+};
+
+Promise.resolve(nonThenable).then(function(value) {
+  assert.sameValue(value, nonThenable);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/resolve/arg-poisoned-then.js b/test/built-ins/Promise/resolve/arg-poisoned-then.js
new file mode 100644
index 0000000000000000000000000000000000000000..085e1455a767de649e6ff0fa82e2c32b4830ff52
--- /dev/null
+++ b/test/built-ins/Promise/resolve/arg-poisoned-then.js
@@ -0,0 +1,35 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked with an object with a "poisoned" `then` property
+es6id: 25.4.4.5
+info: >
+    6. Let resolveResult be Call(promiseCapability.[[Resolve]], undefined,
+       «x»).
+
+    [...]
+
+    25.4.1.3.2 Promise Resolve Functions
+
+    8. Let then be Get(resolution, "then").
+    9. If then is an abrupt completion, then
+       a. Return RejectPromise(promise, then.[[value]]).
+---*/
+
+var poisonedThen = {};
+var err = new Test262Error();
+Object.defineProperty(poisonedThen, 'then', {
+  get: function() {
+    throw err;
+  }
+});
+
+Promise.resolve(poisonedThen).then(function() {
+  $ERROR(
+    'Promise should be rejected when retrieving `then` property throws an error'
+  );
+}, function(reason) {
+  assert.sameValue(reason, err);
+}).then($DONE, $DONE);
diff --git a/test/built-ins/Promise/resolve/arg-uniq-ctor.js b/test/built-ins/Promise/resolve/arg-uniq-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..dcab56e1d791e545358abbd53d598efd1eb0ac74
--- /dev/null
+++ b/test/built-ins/Promise/resolve/arg-uniq-ctor.js
@@ -0,0 +1,27 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked with a Promise with a unique constructor
+es6id: 25.4.4.5
+info: >
+    1. Let C be the this value.
+    [...]
+    3. If IsPromise(x) is true,
+       a. Let xConstructor be Get(x, "constructor").
+       b. ReturnIfAbrupt(xConstructor).
+       c. If SameValue(xConstructor, C) is true, return x.
+    4. Let promiseCapability be NewPromiseCapability(C).
+    [...]
+    8. Return promiseCapability.[[Promise]].
+---*/
+
+var promise1 = new Promise(function() {});
+var promise2;
+
+promise1.constructor = null;
+
+promise2 = Promise.resolve(promise1);
+
+assert.sameValue(promise1 === promise2, false);
diff --git a/test/built-ins/Promise/resolve/ctx-ctor.js b/test/built-ins/Promise/resolve/ctx-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..f1772d8119321c1784a23b03a29a0ab79372b784
--- /dev/null
+++ b/test/built-ins/Promise/resolve/ctx-ctor.js
@@ -0,0 +1,34 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked on a constructor value
+es6id: 25.4.4.5
+info: >
+    1. Let C be the this value.
+    [...]
+    4. Let promiseCapability be NewPromiseCapability(C).
+    [...]
+    8. Return promiseCapability.[[Promise]].
+features: [class]
+---*/
+
+var executor = null;
+var callCount = 0;
+
+class SubPromise extends Promise {
+  constructor(a) {
+    super(a);
+    executor = a;
+    callCount += 1;
+  }
+}
+
+var instance = Promise.resolve.call(SubPromise);
+
+assert.sameValue(instance.constructor, SubPromise);
+assert.sameValue(instance instanceof SubPromise, true);
+
+assert.sameValue(callCount, 1);
+assert.sameValue(typeof executor, 'function');
diff --git a/test/built-ins/Promise/resolve/ctx-non-ctor.js b/test/built-ins/Promise/resolve/ctx-non-ctor.js
new file mode 100644
index 0000000000000000000000000000000000000000..84cde055d49e8ca1e645061e850a818d021cff84
--- /dev/null
+++ b/test/built-ins/Promise/resolve/ctx-non-ctor.js
@@ -0,0 +1,16 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked on a non-constructor value
+es6id: 25.4.4.5
+info: >
+    [...]
+    4. Let promiseCapability be NewPromiseCapability(C).
+    5. ReturnIfAbrupt(promiseCapability).
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call(eval);
+});
diff --git a/test/built-ins/Promise/resolve/ctx-non-object.js b/test/built-ins/Promise/resolve/ctx-non-object.js
new file mode 100644
index 0000000000000000000000000000000000000000..439cb34e92b648aaddffef11c0a21933b6509897
--- /dev/null
+++ b/test/built-ins/Promise/resolve/ctx-non-object.js
@@ -0,0 +1,36 @@
+// Copyright (C) 2015 the V8 project authors. All rights reserved.
+// This code is governed by the BSD license found in the LICENSE file.
+
+/*---
+description: >
+    `Promise.resolve` invoked on a non-object value
+es6id: 25.4.4.5
+info: >
+    1. Let C be the this value.
+    2. If Type(C) is not Object, throw a TypeError exception.
+features: [Symbol]
+---*/
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call(undefined, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call(null, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call(86, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call('string', []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call(true, []);
+});
+
+assert.throws(TypeError, function() {
+  Promise.resolve.call(Symbol(), []);
+});