OLD | NEW |
1 // Copyright 2016 the V8 project authors. All rights reserved. | 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 | 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 #include "src/builtins/builtins-promise.h" | 5 #include "src/builtins/builtins-promise.h" |
6 #include "src/builtins/builtins-constructor.h" | 6 #include "src/builtins/builtins-constructor.h" |
7 #include "src/builtins/builtins-utils.h" | 7 #include "src/builtins/builtins-utils.h" |
8 #include "src/builtins/builtins.h" | 8 #include "src/builtins/builtins.h" |
9 #include "src/code-factory.h" | 9 #include "src/code-factory.h" |
10 #include "src/code-stub-assembler.h" | 10 #include "src/code-stub-assembler.h" |
11 #include "src/promise-utils.h" | |
12 | 11 |
13 namespace v8 { | 12 namespace v8 { |
14 namespace internal { | 13 namespace internal { |
15 | 14 |
16 typedef compiler::Node Node; | 15 typedef compiler::Node Node; |
17 typedef CodeStubAssembler::ParameterMode ParameterMode; | 16 typedef CodeStubAssembler::ParameterMode ParameterMode; |
18 typedef compiler::CodeAssemblerState CodeAssemblerState; | 17 typedef compiler::CodeAssemblerState CodeAssemblerState; |
19 | 18 |
20 Node* PromiseBuiltinsAssembler::AllocateJSPromise(Node* context) { | 19 Node* PromiseBuiltinsAssembler::AllocateJSPromise(Node* context) { |
21 Node* const native_context = LoadNativeContext(context); | 20 Node* const native_context = LoadNativeContext(context); |
(...skipping 182 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
204 StoreContextElementNoWriteBarrier(context, Context::EXTENSION_INDEX, | 203 StoreContextElementNoWriteBarrier(context, Context::EXTENSION_INDEX, |
205 TheHoleConstant()); | 204 TheHoleConstant()); |
206 StoreContextElementNoWriteBarrier(context, Context::NATIVE_CONTEXT_INDEX, | 205 StoreContextElementNoWriteBarrier(context, Context::NATIVE_CONTEXT_INDEX, |
207 native_context); | 206 native_context); |
208 return context; | 207 return context; |
209 } | 208 } |
210 | 209 |
211 Node* PromiseBuiltinsAssembler::CreatePromiseResolvingFunctionsContext( | 210 Node* PromiseBuiltinsAssembler::CreatePromiseResolvingFunctionsContext( |
212 Node* promise, Node* debug_event, Node* native_context) { | 211 Node* promise, Node* debug_event, Node* native_context) { |
213 Node* const context = | 212 Node* const context = |
214 CreatePromiseContext(native_context, PromiseUtils::kPromiseContextLength); | 213 CreatePromiseContext(native_context, kPromiseContextLength); |
215 StoreContextElementNoWriteBarrier(context, PromiseUtils::kAlreadyVisitedSlot, | 214 StoreContextElementNoWriteBarrier(context, kAlreadyVisitedSlot, |
216 SmiConstant(0)); | 215 SmiConstant(0)); |
217 StoreContextElementNoWriteBarrier(context, PromiseUtils::kPromiseSlot, | 216 StoreContextElementNoWriteBarrier(context, kPromiseSlot, promise); |
218 promise); | 217 StoreContextElementNoWriteBarrier(context, kDebugEventSlot, debug_event); |
219 StoreContextElementNoWriteBarrier(context, PromiseUtils::kDebugEventSlot, | |
220 debug_event); | |
221 return context; | 218 return context; |
222 } | 219 } |
223 | 220 |
224 Node* PromiseBuiltinsAssembler::CreatePromiseGetCapabilitiesExecutorContext( | 221 Node* PromiseBuiltinsAssembler::CreatePromiseGetCapabilitiesExecutorContext( |
225 Node* promise_capability, Node* native_context) { | 222 Node* promise_capability, Node* native_context) { |
226 int kContextLength = GetPromiseCapabilityExecutor::kContextLength; | 223 int kContextLength = kCapabilitiesContextLength; |
227 Node* context = CreatePromiseContext(native_context, kContextLength); | 224 Node* context = CreatePromiseContext(native_context, kContextLength); |
228 StoreContextElementNoWriteBarrier( | 225 StoreContextElementNoWriteBarrier(context, kCapabilitySlot, |
229 context, GetPromiseCapabilityExecutor::kCapabilitySlot, | 226 promise_capability); |
230 promise_capability); | |
231 return context; | 227 return context; |
232 } | 228 } |
233 | 229 |
234 Node* PromiseBuiltinsAssembler::ThrowIfNotJSReceiver( | 230 Node* PromiseBuiltinsAssembler::ThrowIfNotJSReceiver( |
235 Node* context, Node* value, MessageTemplate::Template msg_template, | 231 Node* context, Node* value, MessageTemplate::Template msg_template, |
236 const char* method_name) { | 232 const char* method_name) { |
237 Label out(this), throw_exception(this, Label::kDeferred); | 233 Label out(this), throw_exception(this, Label::kDeferred); |
238 Variable var_value_map(this, MachineRepresentation::kTagged); | 234 Variable var_value_map(this, MachineRepresentation::kTagged); |
239 | 235 |
240 GotoIf(TaggedIsSmi(value), &throw_exception); | 236 GotoIf(TaggedIsSmi(value), &throw_exception); |
(...skipping 738 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
979 | 975 |
980 // ES#sec-promise-reject-functions | 976 // ES#sec-promise-reject-functions |
981 // Promise Reject Functions | 977 // Promise Reject Functions |
982 TF_BUILTIN(PromiseRejectClosure, PromiseBuiltinsAssembler) { | 978 TF_BUILTIN(PromiseRejectClosure, PromiseBuiltinsAssembler) { |
983 Node* const value = Parameter(1); | 979 Node* const value = Parameter(1); |
984 Node* const context = Parameter(4); | 980 Node* const context = Parameter(4); |
985 | 981 |
986 Label out(this); | 982 Label out(this); |
987 | 983 |
988 // 3. Let alreadyResolved be F.[[AlreadyResolved]]. | 984 // 3. Let alreadyResolved be F.[[AlreadyResolved]]. |
989 int has_already_visited_slot = PromiseUtils::kAlreadyVisitedSlot; | 985 int has_already_visited_slot = kAlreadyVisitedSlot; |
990 | 986 |
991 Node* const has_already_visited = | 987 Node* const has_already_visited = |
992 LoadContextElement(context, has_already_visited_slot); | 988 LoadContextElement(context, has_already_visited_slot); |
993 | 989 |
994 // 4. If alreadyResolved.[[Value]] is true, return undefined. | 990 // 4. If alreadyResolved.[[Value]] is true, return undefined. |
995 GotoIf(SmiEqual(has_already_visited, SmiConstant(1)), &out); | 991 GotoIf(SmiEqual(has_already_visited, SmiConstant(1)), &out); |
996 | 992 |
997 // 5.Set alreadyResolved.[[Value]] to true. | 993 // 5.Set alreadyResolved.[[Value]] to true. |
998 StoreContextElementNoWriteBarrier(context, has_already_visited_slot, | 994 StoreContextElementNoWriteBarrier(context, has_already_visited_slot, |
999 SmiConstant(1)); | 995 SmiConstant(1)); |
1000 | 996 |
1001 // 2. Let promise be F.[[Promise]]. | 997 // 2. Let promise be F.[[Promise]]. |
1002 Node* const promise = | 998 Node* const promise = |
1003 LoadContextElement(context, IntPtrConstant(PromiseUtils::kPromiseSlot)); | 999 LoadContextElement(context, IntPtrConstant(kPromiseSlot)); |
1004 Node* const debug_event = LoadContextElement( | 1000 Node* const debug_event = |
1005 context, IntPtrConstant(PromiseUtils::kDebugEventSlot)); | 1001 LoadContextElement(context, IntPtrConstant(kDebugEventSlot)); |
1006 | 1002 |
1007 InternalPromiseReject(context, promise, value, debug_event); | 1003 InternalPromiseReject(context, promise, value, debug_event); |
1008 Return(UndefinedConstant()); | 1004 Return(UndefinedConstant()); |
1009 | 1005 |
1010 Bind(&out); | 1006 Bind(&out); |
1011 Return(UndefinedConstant()); | 1007 Return(UndefinedConstant()); |
1012 } | 1008 } |
1013 | 1009 |
1014 TF_BUILTIN(PromiseConstructor, PromiseBuiltinsAssembler) { | 1010 TF_BUILTIN(PromiseConstructor, PromiseBuiltinsAssembler) { |
1015 Node* const executor = Parameter(1); | 1011 Node* const executor = Parameter(1); |
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1186 | 1182 |
1187 // ES#sec-promise-resolve-functions | 1183 // ES#sec-promise-resolve-functions |
1188 // Promise Resolve Functions | 1184 // Promise Resolve Functions |
1189 TF_BUILTIN(PromiseResolveClosure, PromiseBuiltinsAssembler) { | 1185 TF_BUILTIN(PromiseResolveClosure, PromiseBuiltinsAssembler) { |
1190 Node* const value = Parameter(1); | 1186 Node* const value = Parameter(1); |
1191 Node* const context = Parameter(4); | 1187 Node* const context = Parameter(4); |
1192 | 1188 |
1193 Label out(this); | 1189 Label out(this); |
1194 | 1190 |
1195 // 3. Let alreadyResolved be F.[[AlreadyResolved]]. | 1191 // 3. Let alreadyResolved be F.[[AlreadyResolved]]. |
1196 int has_already_visited_slot = PromiseUtils::kAlreadyVisitedSlot; | 1192 int has_already_visited_slot = kAlreadyVisitedSlot; |
1197 | 1193 |
1198 Node* const has_already_visited = | 1194 Node* const has_already_visited = |
1199 LoadContextElement(context, has_already_visited_slot); | 1195 LoadContextElement(context, has_already_visited_slot); |
1200 | 1196 |
1201 // 4. If alreadyResolved.[[Value]] is true, return undefined. | 1197 // 4. If alreadyResolved.[[Value]] is true, return undefined. |
1202 GotoIf(SmiEqual(has_already_visited, SmiConstant(1)), &out); | 1198 GotoIf(SmiEqual(has_already_visited, SmiConstant(1)), &out); |
1203 | 1199 |
1204 // 5.Set alreadyResolved.[[Value]] to true. | 1200 // 5.Set alreadyResolved.[[Value]] to true. |
1205 StoreContextElementNoWriteBarrier(context, has_already_visited_slot, | 1201 StoreContextElementNoWriteBarrier(context, has_already_visited_slot, |
1206 SmiConstant(1)); | 1202 SmiConstant(1)); |
1207 | 1203 |
1208 // 2. Let promise be F.[[Promise]]. | 1204 // 2. Let promise be F.[[Promise]]. |
1209 Node* const promise = | 1205 Node* const promise = |
1210 LoadContextElement(context, IntPtrConstant(PromiseUtils::kPromiseSlot)); | 1206 LoadContextElement(context, IntPtrConstant(kPromiseSlot)); |
1211 | 1207 |
1212 InternalResolvePromise(context, promise, value); | 1208 InternalResolvePromise(context, promise, value); |
1213 Return(UndefinedConstant()); | 1209 Return(UndefinedConstant()); |
1214 | 1210 |
1215 Bind(&out); | 1211 Bind(&out); |
1216 Return(UndefinedConstant()); | 1212 Return(UndefinedConstant()); |
1217 } | 1213 } |
1218 | 1214 |
1219 TF_BUILTIN(ResolvePromise, PromiseBuiltinsAssembler) { | 1215 TF_BUILTIN(ResolvePromise, PromiseBuiltinsAssembler) { |
1220 Node* const promise = Parameter(1); | 1216 Node* const promise = Parameter(1); |
(...skipping 232 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1453 Return(result); | 1449 Return(result); |
1454 } | 1450 } |
1455 } | 1451 } |
1456 } | 1452 } |
1457 | 1453 |
1458 TF_BUILTIN(PromiseGetCapabilitiesExecutor, PromiseBuiltinsAssembler) { | 1454 TF_BUILTIN(PromiseGetCapabilitiesExecutor, PromiseBuiltinsAssembler) { |
1459 Node* const resolve = Parameter(1); | 1455 Node* const resolve = Parameter(1); |
1460 Node* const reject = Parameter(2); | 1456 Node* const reject = Parameter(2); |
1461 Node* const context = Parameter(5); | 1457 Node* const context = Parameter(5); |
1462 | 1458 |
1463 Node* const capability = LoadContextElement( | 1459 Node* const capability = LoadContextElement(context, kCapabilitySlot); |
1464 context, GetPromiseCapabilityExecutor::kCapabilitySlot); | |
1465 | 1460 |
1466 Label if_alreadyinvoked(this, Label::kDeferred); | 1461 Label if_alreadyinvoked(this, Label::kDeferred); |
1467 GotoIf(WordNotEqual( | 1462 GotoIf(WordNotEqual( |
1468 LoadObjectField(capability, JSPromiseCapability::kResolveOffset), | 1463 LoadObjectField(capability, JSPromiseCapability::kResolveOffset), |
1469 UndefinedConstant()), | 1464 UndefinedConstant()), |
1470 &if_alreadyinvoked); | 1465 &if_alreadyinvoked); |
1471 GotoIf(WordNotEqual( | 1466 GotoIf(WordNotEqual( |
1472 LoadObjectField(capability, JSPromiseCapability::kRejectOffset), | 1467 LoadObjectField(capability, JSPromiseCapability::kRejectOffset), |
1473 UndefinedConstant()), | 1468 UndefinedConstant()), |
1474 &if_alreadyinvoked); | 1469 &if_alreadyinvoked); |
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1542 Node* const reason = Parameter(2); | 1537 Node* const reason = Parameter(2); |
1543 Node* const debug_event = Parameter(3); | 1538 Node* const debug_event = Parameter(3); |
1544 Node* const context = Parameter(6); | 1539 Node* const context = Parameter(6); |
1545 | 1540 |
1546 InternalPromiseReject(context, promise, reason, debug_event); | 1541 InternalPromiseReject(context, promise, reason, debug_event); |
1547 Return(UndefinedConstant()); | 1542 Return(UndefinedConstant()); |
1548 } | 1543 } |
1549 | 1544 |
1550 } // namespace internal | 1545 } // namespace internal |
1551 } // namespace v8 | 1546 } // namespace v8 |
OLD | NEW |