OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 (function(global, utils, extrasUtils) { | 5 (function(global, utils, extrasUtils) { |
6 | 6 |
7 "use strict"; | 7 "use strict"; |
8 | 8 |
9 %CheckIsBootstrapping(); | 9 %CheckIsBootstrapping(); |
10 | 10 |
(...skipping 372 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
383 // Shortcut Promise.reject and Promise.resolve() implementations, used by | 383 // Shortcut Promise.reject and Promise.resolve() implementations, used by |
384 // Async Functions implementation. | 384 // Async Functions implementation. |
385 function PromiseCreateRejected(r) { | 385 function PromiseCreateRejected(r) { |
386 return %_Call(PromiseReject, GlobalPromise, r); | 386 return %_Call(PromiseReject, GlobalPromise, r); |
387 } | 387 } |
388 | 388 |
389 function PromiseCreateResolved(x) { | 389 function PromiseCreateResolved(x) { |
390 return %_Call(PromiseResolve, GlobalPromise, x); | 390 return %_Call(PromiseResolve, GlobalPromise, x); |
391 } | 391 } |
392 | 392 |
| 393 function PerformPromiseThen(promise, onResolve, onReject, resultCapability) { |
| 394 if (!IS_CALLABLE(onResolve)) onResolve = PromiseIdResolveHandler; |
| 395 if (!IS_CALLABLE(onReject)) onReject = PromiseIdRejectHandler; |
| 396 |
| 397 var status = GET_PRIVATE(promise, promiseStateSymbol); |
| 398 switch (status) { |
| 399 case kPending: |
| 400 PromiseAttachCallbacks(promise, resultCapability, onResolve, onReject); |
| 401 break; |
| 402 case kFulfilled: |
| 403 PromiseEnqueue(GET_PRIVATE(promise, promiseResultSymbol), |
| 404 onResolve, resultCapability, kFulfilled); |
| 405 break; |
| 406 case kRejected: |
| 407 if (!HAS_DEFINED_PRIVATE(promise, promiseHasHandlerSymbol)) { |
| 408 // Promise has already been rejected, but had no handler. |
| 409 // Revoke previously triggered reject event. |
| 410 %PromiseRevokeReject(promise); |
| 411 } |
| 412 PromiseEnqueue(GET_PRIVATE(promise, promiseResultSymbol), |
| 413 onReject, resultCapability, kRejected); |
| 414 break; |
| 415 } |
| 416 |
| 417 // Mark this promise as having handler. |
| 418 SET_PRIVATE(promise, promiseHasHandlerSymbol, true); |
| 419 return resultCapability.promise; |
| 420 } |
| 421 |
393 // ES#sec-promise.prototype.then | 422 // ES#sec-promise.prototype.then |
394 // Promise.prototype.then ( onFulfilled, onRejected ) | 423 // Promise.prototype.then ( onFulfilled, onRejected ) |
395 // Multi-unwrapped chaining with thenable coercion. | 424 // Multi-unwrapped chaining with thenable coercion. |
396 function PromiseThen(onResolve, onReject) { | 425 function PromiseThen(onResolve, onReject) { |
397 var status = GET_PRIVATE(this, promiseStateSymbol); | 426 var status = GET_PRIVATE(this, promiseStateSymbol); |
398 if (IS_UNDEFINED(status)) { | 427 if (IS_UNDEFINED(status)) { |
399 throw MakeTypeError(kNotAPromise, this); | 428 throw MakeTypeError(kNotAPromise, this); |
400 } | 429 } |
401 | 430 |
402 var constructor = SpeciesConstructor(this, GlobalPromise); | 431 var constructor = SpeciesConstructor(this, GlobalPromise); |
403 onResolve = IS_CALLABLE(onResolve) ? onResolve : PromiseIdResolveHandler; | 432 var resultCapability = NewPromiseCapability(constructor); |
404 onReject = IS_CALLABLE(onReject) ? onReject : PromiseIdRejectHandler; | 433 return PerformPromiseThen(this, onResolve, onReject, resultCapability); |
405 var deferred = NewPromiseCapability(constructor); | |
406 switch (status) { | |
407 case kPending: | |
408 PromiseAttachCallbacks(this, deferred, onResolve, onReject); | |
409 break; | |
410 case kFulfilled: | |
411 PromiseEnqueue(GET_PRIVATE(this, promiseResultSymbol), | |
412 onResolve, deferred, kFulfilled); | |
413 break; | |
414 case kRejected: | |
415 if (!HAS_DEFINED_PRIVATE(this, promiseHasHandlerSymbol)) { | |
416 // Promise has already been rejected, but had no handler. | |
417 // Revoke previously triggered reject event. | |
418 %PromiseRevokeReject(this); | |
419 } | |
420 PromiseEnqueue(GET_PRIVATE(this, promiseResultSymbol), | |
421 onReject, deferred, kRejected); | |
422 break; | |
423 } | |
424 // Mark this promise as having handler. | |
425 SET_PRIVATE(this, promiseHasHandlerSymbol, true); | |
426 return deferred.promise; | |
427 } | 434 } |
428 | 435 |
429 // Unspecified V8-specific legacy function | 436 // Unspecified V8-specific legacy function |
430 // Chain is left around for now as an alias for then | 437 // Chain is left around for now as an alias for then |
431 function PromiseChain(onResolve, onReject) { | 438 function PromiseChain(onResolve, onReject) { |
432 %IncrementUseCounter(kPromiseChain); | 439 %IncrementUseCounter(kPromiseChain); |
433 return %_Call(PromiseThen, this, onResolve, onReject); | 440 return %_Call(PromiseThen, this, onResolve, onReject); |
434 } | 441 } |
435 | 442 |
436 // ES#sec-promise.prototype.catch | 443 // ES#sec-promise.prototype.catch |
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
615 "createPromise", PromiseCreate, | 622 "createPromise", PromiseCreate, |
616 "resolvePromise", ResolvePromise, | 623 "resolvePromise", ResolvePromise, |
617 "rejectPromise", RejectPromise | 624 "rejectPromise", RejectPromise |
618 ]); | 625 ]); |
619 | 626 |
620 // TODO(v8:4567): Allow experimental natives to remove function prototype | 627 // TODO(v8:4567): Allow experimental natives to remove function prototype |
621 [PromiseChain, PromiseDefer, PromiseAccept].forEach( | 628 [PromiseChain, PromiseDefer, PromiseAccept].forEach( |
622 fn => %FunctionRemovePrototype(fn)); | 629 fn => %FunctionRemovePrototype(fn)); |
623 | 630 |
624 utils.Export(function(to) { | 631 utils.Export(function(to) { |
| 632 to.IsPromise = IsPromise; |
| 633 |
625 to.PromiseChain = PromiseChain; | 634 to.PromiseChain = PromiseChain; |
626 to.PromiseDefer = PromiseDefer; | 635 to.PromiseDefer = PromiseDefer; |
627 to.PromiseAccept = PromiseAccept; | 636 to.PromiseAccept = PromiseAccept; |
628 | 637 |
629 to.PromiseCreateRejected = PromiseCreateRejected; | 638 to.PromiseCreateRejected = PromiseCreateRejected; |
630 to.PromiseCreateResolved = PromiseCreateResolved; | 639 to.PromiseCreateResolved = PromiseCreateResolved; |
631 to.PromiseThen = PromiseThen; | 640 to.PromiseThen = PromiseThen; |
| 641 |
| 642 to.GlobalPromise = GlobalPromise; |
| 643 to.NewPromiseCapability = NewPromiseCapability; |
| 644 to.PerformPromiseThen = PerformPromiseThen; |
632 }); | 645 }); |
633 | 646 |
634 }) | 647 }) |
OLD | NEW |