Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include <map> | 5 #include <map> |
| 6 #include <set> | 6 #include <set> |
| 7 #include <string> | 7 #include <string> |
| 8 | 8 |
| 9 #include "vm/kernel_to_il.h" | 9 #include "vm/kernel_to_il.h" |
| 10 | 10 |
| (...skipping 702 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 713 (depth_.function_ == 0) ? &result_->yield_context_variable : &temp, | 713 (depth_.function_ == 0) ? &result_->yield_context_variable : &temp, |
| 714 Symbols::AwaitContextVar()); | 714 Symbols::AwaitContextVar()); |
| 715 } | 715 } |
| 716 { | 716 { |
| 717 LocalVariable* temp = | 717 LocalVariable* temp = |
| 718 scope_->LookupVariable(Symbols::AsyncOperation(), true); | 718 scope_->LookupVariable(Symbols::AsyncOperation(), true); |
| 719 if (temp != NULL) { | 719 if (temp != NULL) { |
| 720 scope_->CaptureVariable(temp); | 720 scope_->CaptureVariable(temp); |
| 721 } | 721 } |
| 722 } | 722 } |
| 723 if (FLAG_causal_async_stacks) { | |
| 724 // TODO(28777): Either remove the variable here, or update the dart side | |
|
Kevin Millikin (Google)
2017/02/22 10:42:17
The comment is confusing. It's not entirely clear
jensj
2017/02/23 09:40:26
I have attempted to move the call to _asyncStackTr
| |
| 725 // so we don't always generate it if this flag is not set. | |
| 726 LocalVariable* temp = | |
| 727 scope_->LookupVariable(Symbols::AsyncStackTraceVar(), true); | |
| 728 if (temp != NULL) { | |
| 729 scope_->CaptureVariable(temp); | |
| 730 } | |
| 731 } | |
| 723 } | 732 } |
| 724 } | 733 } |
| 725 | 734 |
| 726 | 735 |
| 727 void ScopeBuilder::VisitYieldStatement(YieldStatement* node) { | 736 void ScopeBuilder::VisitYieldStatement(YieldStatement* node) { |
| 728 ASSERT(node->is_native()); | 737 ASSERT(node->is_native()); |
| 729 if (depth_.function_ == 0) { | 738 if (depth_.function_ == 0) { |
| 730 AddSwitchVariable(); | 739 AddSwitchVariable(); |
| 731 // Promote all currently visible local variables into the context. | 740 // Promote all currently visible local variables into the context. |
| 732 // TODO(27590) CaptureLocalVariables promotes to many variables into | 741 // TODO(27590) CaptureLocalVariables promotes to many variables into |
| (...skipping 1815 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 2548 Value* value = Pop(); | 2557 Value* value = Pop(); |
| 2549 ASSERT(stack_ == NULL); | 2558 ASSERT(stack_ == NULL); |
| 2550 | 2559 |
| 2551 const Function& function = parsed_function_->function(); | 2560 const Function& function = parsed_function_->function(); |
| 2552 if (FLAG_support_debugger && position.IsDebugPause() && | 2561 if (FLAG_support_debugger && position.IsDebugPause() && |
| 2553 !function.is_native()) { | 2562 !function.is_native()) { |
| 2554 instructions <<= | 2563 instructions <<= |
| 2555 new (Z) DebugStepCheckInstr(position, RawPcDescriptors::kRuntimeCall); | 2564 new (Z) DebugStepCheckInstr(position, RawPcDescriptors::kRuntimeCall); |
| 2556 } | 2565 } |
| 2557 | 2566 |
| 2567 if (FLAG_causal_async_stacks && | |
| 2568 function.name() == Symbols::AsyncOperation().raw()) { | |
|
Kevin Millikin (Google)
2017/02/22 10:42:18
We should set the function to be correctly IsAsync
jensj
2017/02/23 09:40:26
Done.
| |
| 2569 // We are returning from an asynchronous closure. Before we do that, be | |
| 2570 // sure to clear the thread's asynchronous stack trace. | |
| 2571 const Function& target = Function::ZoneHandle( | |
| 2572 Z, I->object_store()->async_clear_thread_stack_trace()); | |
| 2573 ASSERT(!target.IsNull()); | |
| 2574 instructions += StaticCall(TokenPosition::kNoSource, target, 0); | |
| 2575 instructions += Drop(); | |
| 2576 } | |
| 2577 | |
| 2558 ReturnInstr* return_instr = new (Z) ReturnInstr(position, value); | 2578 ReturnInstr* return_instr = new (Z) ReturnInstr(position, value); |
| 2559 if (exit_collector_ != NULL) exit_collector_->AddExit(return_instr); | 2579 if (exit_collector_ != NULL) exit_collector_->AddExit(return_instr); |
| 2560 | 2580 |
| 2561 instructions <<= return_instr; | 2581 instructions <<= return_instr; |
| 2562 | 2582 |
| 2563 return instructions.closed(); | 2583 return instructions.closed(); |
| 2564 } | 2584 } |
| 2565 | 2585 |
| 2566 | 2586 |
| 2567 Fragment FlowGraphBuilder::StaticCall(TokenPosition position, | 2587 Fragment FlowGraphBuilder::StaticCall(TokenPosition position, |
| (...skipping 596 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3164 body += NullConstant(); | 3184 body += NullConstant(); |
| 3165 body += Return(dart_function.end_token_pos()); | 3185 body += Return(dart_function.end_token_pos()); |
| 3166 } | 3186 } |
| 3167 | 3187 |
| 3168 // If functions body contains any yield points build switch statement that | 3188 // If functions body contains any yield points build switch statement that |
| 3169 // selects a continuation point based on the value of :await_jump_var. | 3189 // selects a continuation point based on the value of :await_jump_var. |
| 3170 if (!yield_continuations_.is_empty()) { | 3190 if (!yield_continuations_.is_empty()) { |
| 3171 // The code we are building will be executed right after we enter | 3191 // The code we are building will be executed right after we enter |
| 3172 // the function and before any nested contexts are allocated. | 3192 // the function and before any nested contexts are allocated. |
| 3173 // Reset current context_depth_ to match this. | 3193 // Reset current context_depth_ to match this. |
| 3174 intptr_t current_context_depth = context_depth_; | 3194 const intptr_t current_context_depth = context_depth_; |
| 3175 context_depth_ = scopes_->yield_jump_variable->owner()->context_level(); | 3195 context_depth_ = scopes_->yield_jump_variable->owner()->context_level(); |
| 3176 | 3196 |
| 3177 // Prepend an entry corresponding to normal entry to the function. | 3197 // Prepend an entry corresponding to normal entry to the function. |
| 3178 yield_continuations_.InsertAt( | 3198 yield_continuations_.InsertAt( |
| 3179 0, YieldContinuation(new (Z) DropTempsInstr(0, NULL), | 3199 0, YieldContinuation(new (Z) DropTempsInstr(0, NULL), |
| 3180 CatchClauseNode::kInvalidTryIndex)); | 3200 CatchClauseNode::kInvalidTryIndex)); |
| 3181 yield_continuations_[0].entry->LinkTo(body.entry); | 3201 yield_continuations_[0].entry->LinkTo(body.entry); |
| 3182 | 3202 |
| 3183 // Build a switch statement. | 3203 // Build a switch statement. |
| 3184 Fragment dispatch; | 3204 Fragment dispatch; |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 3230 | 3250 |
| 3231 // False branch will contain the next comparison. | 3251 // False branch will contain the next comparison. |
| 3232 dispatch = Fragment(dispatch.entry, otherwise); | 3252 dispatch = Fragment(dispatch.entry, otherwise); |
| 3233 block = otherwise; | 3253 block = otherwise; |
| 3234 } | 3254 } |
| 3235 body = dispatch; | 3255 body = dispatch; |
| 3236 | 3256 |
| 3237 context_depth_ = current_context_depth; | 3257 context_depth_ = current_context_depth; |
| 3238 } | 3258 } |
| 3239 | 3259 |
| 3260 if (FLAG_causal_async_stacks && | |
| 3261 dart_function.name() == Symbols::AsyncOperation().raw()) { | |
|
Kevin Millikin (Google)
2017/02/22 10:42:17
Also here, I'd rather not use the name if we don't
jensj
2017/02/23 09:40:26
Done.
| |
| 3262 // The code we are building will be executed right after we enter | |
| 3263 // the function and before any nested contexts are allocated. | |
| 3264 // Reset current context_depth_ to match this. | |
| 3265 const intptr_t current_context_depth = context_depth_; | |
| 3266 context_depth_ = scopes_->yield_jump_variable->owner()->context_level(); | |
| 3267 | |
| 3268 Fragment instructions; | |
| 3269 LocalScope* scope = parsed_function_->node_sequence()->scope(); | |
| 3270 | |
| 3271 const Function& target = Function::ZoneHandle( | |
| 3272 Z, I->object_store()->async_set_thread_stack_trace()); | |
| 3273 ASSERT(!target.IsNull()); | |
| 3274 | |
| 3275 // Fetch and load :async_stack_trace | |
| 3276 LocalVariable* async_stack_trace_var = | |
| 3277 scope->LookupVariable(Symbols::AsyncStackTraceVar(), false); | |
| 3278 ASSERT((async_stack_trace_var != NULL) && | |
| 3279 async_stack_trace_var->is_captured()); | |
| 3280 instructions += LoadLocal(async_stack_trace_var); | |
| 3281 instructions += PushArgument(); | |
| 3282 | |
| 3283 // Call _asyncSetThreadStackTrace | |
| 3284 instructions += StaticCall(TokenPosition::kNoSource, target, 1); | |
| 3285 instructions += Drop(); | |
| 3286 | |
| 3287 body = instructions + body; | |
| 3288 context_depth_ = current_context_depth; | |
| 3289 } | |
| 3290 | |
| 3240 if (FLAG_support_debugger && function->position().IsDebugPause() && | 3291 if (FLAG_support_debugger && function->position().IsDebugPause() && |
| 3241 !dart_function.is_native() && dart_function.is_debuggable()) { | 3292 !dart_function.is_native() && dart_function.is_debuggable()) { |
| 3242 // If a switch was added above: Start the switch by injecting a debugable | 3293 // If a switch was added above: Start the switch by injecting a debugable |
| 3243 // safepoint so stepping over an await works. | 3294 // safepoint so stepping over an await works. |
| 3244 // If not, still start the body with a debugable safepoint to ensure | 3295 // If not, still start the body with a debugable safepoint to ensure |
| 3245 // breaking on a method always happens, even if there are no | 3296 // breaking on a method always happens, even if there are no |
| 3246 // assignments/calls/runtimecalls in the first basic block. | 3297 // assignments/calls/runtimecalls in the first basic block. |
| 3247 // Place this check at the last parameter to ensure parameters | 3298 // Place this check at the last parameter to ensure parameters |
| 3248 // are in scope in the debugger at method entry. | 3299 // are in scope in the debugger at method entry. |
| 3249 const int num_params = dart_function.NumParameters(); | 3300 const int num_params = dart_function.NumParameters(); |
| (...skipping 2874 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 6124 if (parent->IsFunctionExpression()) { | 6175 if (parent->IsFunctionExpression()) { |
| 6125 name = &Symbols::AnonymousClosure(); | 6176 name = &Symbols::AnonymousClosure(); |
| 6126 } else { | 6177 } else { |
| 6127 ASSERT(parent->IsFunctionDeclaration()); | 6178 ASSERT(parent->IsFunctionDeclaration()); |
| 6128 name = &H.DartSymbol( | 6179 name = &H.DartSymbol( |
| 6129 FunctionDeclaration::Cast(parent)->variable()->name()); | 6180 FunctionDeclaration::Cast(parent)->variable()->name()); |
| 6130 } | 6181 } |
| 6131 // NOTE: This is not TokenPosition in the general sense! | 6182 // NOTE: This is not TokenPosition in the general sense! |
| 6132 function = Function::NewClosureFunction( | 6183 function = Function::NewClosureFunction( |
| 6133 *name, parsed_function_->function(), position); | 6184 *name, parsed_function_->function(), position); |
| 6134 function.set_is_debuggable(node->debuggable()); | 6185 function.set_is_debuggable(node->original_async_marker() == |
| 6186 FunctionNode::kSync); | |
| 6135 function.set_end_token_pos(node->end_position()); | 6187 function.set_end_token_pos(node->end_position()); |
| 6136 LocalScope* scope = scopes_->function_scopes[i].scope; | 6188 LocalScope* scope = scopes_->function_scopes[i].scope; |
| 6137 const ContextScope& context_scope = | 6189 const ContextScope& context_scope = |
| 6138 ContextScope::Handle(Z, scope->PreserveOuterScope(context_depth_)); | 6190 ContextScope::Handle(Z, scope->PreserveOuterScope(context_depth_)); |
| 6139 function.set_context_scope(context_scope); | 6191 function.set_context_scope(context_scope); |
| 6140 function.set_kernel_function(node); | 6192 function.set_kernel_function(node); |
| 6141 KernelReader::SetupFunctionParameters(H, T, dart::Class::Handle(Z), | 6193 KernelReader::SetupFunctionParameters(H, T, dart::Class::Handle(Z), |
| 6142 function, node, | 6194 function, node, |
| 6143 false, // is_method | 6195 false, // is_method |
| 6144 true); // is_closure | 6196 true); // is_closure |
| (...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 6280 thread->clear_sticky_error(); | 6332 thread->clear_sticky_error(); |
| 6281 return error.raw(); | 6333 return error.raw(); |
| 6282 } | 6334 } |
| 6283 } | 6335 } |
| 6284 | 6336 |
| 6285 | 6337 |
| 6286 } // namespace kernel | 6338 } // namespace kernel |
| 6287 } // namespace dart | 6339 } // namespace dart |
| 6288 | 6340 |
| 6289 #endif // !defined(DART_PRECOMPILED_RUNTIME) | 6341 #endif // !defined(DART_PRECOMPILED_RUNTIME) |
| OLD | NEW |