OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2016 the V8 project authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #include "src/builtins/builtins-async.h" | |
6 #include "src/builtins/builtins-utils.h" | |
7 #include "src/builtins/builtins.h" | |
8 #include "src/code-factory.h" | |
9 #include "src/code-stub-assembler.h" | |
10 #include "src/frames-inl.h" | |
11 | |
12 namespace v8 { | |
13 namespace internal { | |
14 | |
15 Node* AsyncBuiltinsAssembler::Await( | |
16 Node* context, Node* generator, Node* value, Node* outer_promise, | |
17 const NodeGenerator1& create_closure_context, int on_resolve_context_index, | |
18 int on_reject_context_index, bool is_catchable) { | |
19 // Let promiseCapability be ! NewPromiseCapability(%Promise%). | |
20 Node* const wrapped_value = AllocateAndInitJSPromise(context); | |
21 | |
22 // Perform ! Call(promiseCapability.[[Resolve]], undefined, « promise »). | |
23 InternalResolvePromise(context, wrapped_value, value); | |
24 | |
25 Node* const native_context = LoadNativeContext(context); | |
26 | |
27 Node* const closure_context = create_closure_context(native_context); | |
28 Node* const map = LoadContextElement( | |
29 native_context, Context::STRICT_FUNCTION_WITHOUT_PROTOTYPE_MAP_INDEX); | |
30 | |
31 // Load and allocate on_resolve closure | |
32 Node* const on_resolve_shared_fun = | |
33 LoadContextElement(native_context, on_resolve_context_index); | |
34 CSA_SLOW_ASSERT( | |
35 this, HasInstanceType(on_resolve_shared_fun, SHARED_FUNCTION_INFO_TYPE)); | |
36 Node* const on_resolve = AllocateFunctionWithMapAndContext( | |
37 map, on_resolve_shared_fun, closure_context); | |
38 | |
39 // Load and allocate on_reject closure | |
40 Node* const on_reject_shared_fun = | |
41 LoadContextElement(native_context, on_reject_context_index); | |
42 CSA_SLOW_ASSERT( | |
43 this, HasInstanceType(on_reject_shared_fun, SHARED_FUNCTION_INFO_TYPE)); | |
44 Node* const on_reject = AllocateFunctionWithMapAndContext( | |
45 map, on_reject_shared_fun, closure_context); | |
46 | |
47 Node* const throwaway_promise = | |
48 AllocateAndInitJSPromise(context, wrapped_value); | |
49 | |
50 // The Promise will be thrown away and not handled, but it shouldn't trigger | |
51 // unhandled reject events as its work is done | |
52 PromiseSetHasHandler(throwaway_promise); | |
53 | |
54 Label do_perform_promise_then(this); | |
55 GotoUnless(IsDebugActive(), &do_perform_promise_then); | |
56 { | |
57 Label common(this); | |
58 GotoUnless(HasInstanceType(value, JS_PROMISE_TYPE), &common); | |
59 { | |
60 // Mark the reject handler callback to be a forwarding edge, rather | |
61 // than a meaningful catch handler | |
62 Node* const key = | |
63 HeapConstant(factory()->promise_forwarding_handler_symbol()); | |
64 CallRuntime(Runtime::kSetProperty, on_reject, key, TrueConstant(), | |
jgruber
2017/01/20 08:17:19
Just noticed that context is missing here as the s
| |
65 SmiConstant(STRICT)); | |
66 | |
67 if (!is_catchable) { | |
68 PromiseSetHasHandler(value); | |
69 } | |
70 } | |
71 | |
72 Goto(&common); | |
73 Bind(&common); | |
74 // Mark the dependency to outer Promise in case the throwaway Promise is | |
75 // found on the Promise stack | |
76 CSA_SLOW_ASSERT(this, HasInstanceType(outer_promise, JS_PROMISE_TYPE)); | |
77 | |
78 Node* const key = HeapConstant(factory()->promise_handled_by_symbol()); | |
79 CallRuntime(Runtime::kSetProperty, throwaway_promise, key, outer_promise, | |
80 SmiConstant(STRICT)); | |
81 } | |
82 | |
83 Goto(&do_perform_promise_then); | |
84 Bind(&do_perform_promise_then); | |
85 InternalPerformPromiseThen(context, wrapped_value, on_resolve, on_reject, | |
86 throwaway_promise, UndefinedConstant(), | |
87 UndefinedConstant()); | |
88 | |
89 return wrapped_value; | |
90 } | |
91 | |
92 } // namespace internal | |
93 } // namespace v8 | |
OLD | NEW |