Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(783)

Side by Side Diff: runtime/vm/flow_graph_builder.cc

Issue 634603002: Await always waits (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 6 years, 2 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2012, 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 "vm/flow_graph_builder.h" 5 #include "vm/flow_graph_builder.h"
6 6
7 #include "lib/invocation_mirror.h" 7 #include "lib/invocation_mirror.h"
8 #include "vm/ast_printer.h" 8 #include "vm/ast_printer.h"
9 #include "vm/bit_vector.h" 9 #include "vm/bit_vector.h"
10 #include "vm/class_finalizer.h" 10 #include "vm/class_finalizer.h"
(...skipping 240 matching lines...) Expand 10 before | Expand all | Expand 10 after
251 exit_collector_(exit_collector), 251 exit_collector_(exit_collector),
252 guarded_fields_(new(I) ZoneGrowableArray<const Field*>()), 252 guarded_fields_(new(I) ZoneGrowableArray<const Field*>()),
253 last_used_block_id_(0), // 0 is used for the graph entry. 253 last_used_block_id_(0), // 0 is used for the graph entry.
254 try_index_(CatchClauseNode::kInvalidTryIndex), 254 try_index_(CatchClauseNode::kInvalidTryIndex),
255 catch_try_index_(CatchClauseNode::kInvalidTryIndex), 255 catch_try_index_(CatchClauseNode::kInvalidTryIndex),
256 loop_depth_(0), 256 loop_depth_(0),
257 graph_entry_(NULL), 257 graph_entry_(NULL),
258 temp_count_(0), 258 temp_count_(0),
259 args_pushed_(0), 259 args_pushed_(0),
260 nesting_stack_(NULL), 260 nesting_stack_(NULL),
261 osr_id_(osr_id), 261 osr_id_(osr_id) { }
262 jump_cnt_(0),
263 await_joins_(new(I) ZoneGrowableArray<JoinEntryInstr*>()),
264 await_levels_(new(I) ZoneGrowableArray<intptr_t>()) { }
265 262
266 263
267 void FlowGraphBuilder::AddCatchEntry(CatchBlockEntryInstr* entry) { 264 void FlowGraphBuilder::AddCatchEntry(CatchBlockEntryInstr* entry) {
268 graph_entry_->AddCatchEntry(entry); 265 graph_entry_->AddCatchEntry(entry);
269 } 266 }
270 267
271 268
272 void InlineExitCollector::PrepareGraphs(FlowGraph* callee_graph) { 269 void InlineExitCollector::PrepareGraphs(FlowGraph* callee_graph) {
273 ASSERT(callee_graph->graph_entry()->SuccessorCount() == 1); 270 ASSERT(callee_graph->graph_entry()->SuccessorCount() == 1);
274 ASSERT(callee_graph->max_block_id() > caller_graph_->max_block_id()); 271 ASSERT(callee_graph->max_block_id() > caller_graph_->max_block_id());
(...skipping 813 matching lines...) Expand 10 before | Expand all | Expand 10 after
1088 ASSERT(current_context_level >= 0); 1085 ASSERT(current_context_level >= 0);
1089 if (owner()->parsed_function()->saved_entry_context_var() != NULL) { 1086 if (owner()->parsed_function()->saved_entry_context_var() != NULL) {
1090 // CTX on entry was saved, but not linked as context parent. 1087 // CTX on entry was saved, but not linked as context parent.
1091 BuildRestoreContext(*owner()->parsed_function()->saved_entry_context_var()); 1088 BuildRestoreContext(*owner()->parsed_function()->saved_entry_context_var());
1092 } else { 1089 } else {
1093 UnchainContexts(current_context_level); 1090 UnchainContexts(current_context_level);
1094 } 1091 }
1095 1092
1096 1093
1097 AddReturnExit(node->token_pos(), return_value); 1094 AddReturnExit(node->token_pos(), return_value);
1095
1096 if (function.is_async_closure() &&
1097 (node->return_type() == ReturnNode::kContinuationTarget)) {
1098 JoinEntryInstr* const join = new(I) JoinEntryInstr(
1099 owner()->AllocateBlockId(), owner()->try_index());
1100 owner()->await_joins().Add(join);
1101 exit_ = join;
1102 }
1098 } 1103 }
1099 1104
1100 1105
1101 // <Expression> ::= Literal { literal: Instance } 1106 // <Expression> ::= Literal { literal: Instance }
1102 void EffectGraphVisitor::VisitLiteralNode(LiteralNode* node) { 1107 void EffectGraphVisitor::VisitLiteralNode(LiteralNode* node) {
1103 ReturnDefinition(new(I) ConstantInstr(node->literal())); 1108 ReturnDefinition(new(I) ConstantInstr(node->literal()));
1104 } 1109 }
1105 1110
1106 1111
1107 // Type nodes are used when a type is referenced as a literal. Type nodes 1112 // Type nodes are used when a type is referenced as a literal. Type nodes
(...skipping 1114 matching lines...) Expand 10 before | Expand all | Expand 10 after
2222 LocalVariable* jump_var = node->scope()->LookupVariable( 2227 LocalVariable* jump_var = node->scope()->LookupVariable(
2223 Symbols::AwaitJumpVar(), false); 2228 Symbols::AwaitJumpVar(), false);
2224 LocalVariable* ctx_var = node->scope()->LookupVariable( 2229 LocalVariable* ctx_var = node->scope()->LookupVariable(
2225 Symbols::AwaitContextVar(), false); 2230 Symbols::AwaitContextVar(), false);
2226 ASSERT((jump_var != NULL) && jump_var->is_captured()); 2231 ASSERT((jump_var != NULL) && jump_var->is_captured());
2227 ASSERT((ctx_var != NULL) && ctx_var->is_captured()); 2232 ASSERT((ctx_var != NULL) && ctx_var->is_captured());
2228 const intptr_t jump_cnt = owner()->next_await_counter(); 2233 const intptr_t jump_cnt = owner()->next_await_counter();
2229 ASSERT(jump_cnt >= 0); 2234 ASSERT(jump_cnt >= 0);
2230 // Sanity check that we always add a JoinEntryInstr before adding a new 2235 // Sanity check that we always add a JoinEntryInstr before adding a new
2231 // state. 2236 // state.
2232 ASSERT(jump_cnt == owner()->await_joins()->length()); 2237 ASSERT(jump_cnt == owner()->await_joins().length());
2233 // Store the counter in :await_jump_var. 2238 // Store the counter in :await_jump_var.
2234 Value* jump_val = Bind(new (I) ConstantInstr( 2239 Value* jump_val = Bind(new (I) ConstantInstr(
2235 Smi::ZoneHandle(I, Smi::New(jump_cnt)))); 2240 Smi::ZoneHandle(I, Smi::New(jump_cnt))));
2236 Do(BuildStoreLocal(*jump_var, jump_val)); 2241 Do(BuildStoreLocal(*jump_var, jump_val));
2237 // Save the current context for resuming. 2242 // Save the current context for resuming.
2238 BuildSaveContext(*ctx_var); 2243 BuildSaveContext(*ctx_var);
2239 owner()->await_levels()->Add(owner()->context_level()); 2244 owner()->await_levels().Add(owner()->context_level());
2240 return; 2245 return;
2241 } 2246 }
2242 if (node->marker_type() == AwaitMarkerNode::kTargetForContinuation) { 2247 if (node->marker_type() == AwaitMarkerNode::kTargetForContinuation) {
2243 // We need to create a new await target which involves: 2248 UNREACHABLE(); //XXX
2244 // * Append a join that is also added to the list that will later result in
2245 // a preamble.
2246 JoinEntryInstr* const join = new(I) JoinEntryInstr(
2247 owner()->AllocateBlockId(), owner()->try_index());
2248 owner()->await_joins()->Add(join);
2249 Goto(join);
2250 exit_ = join;
2251 return;
2252 } 2249 }
2253 UNREACHABLE(); 2250 UNREACHABLE();
2254 } 2251 }
2255 2252
2256 2253
2257 intptr_t EffectGraphVisitor::GetCurrentTempLocalIndex() const { 2254 intptr_t EffectGraphVisitor::GetCurrentTempLocalIndex() const {
2258 return kFirstLocalSlotFromFp 2255 return kFirstLocalSlotFromFp
2259 - owner()->num_stack_locals() 2256 - owner()->num_stack_locals()
2260 - owner()->num_copied_params() 2257 - owner()->num_copied_params()
2261 - owner()->args_pushed() 2258 - owner()->args_pushed()
(...skipping 1612 matching lines...) Expand 10 before | Expand all | Expand 10 after
3874 ASSERT(jump_var != NULL && jump_var->is_captured()); 3871 ASSERT(jump_var != NULL && jump_var->is_captured());
3875 3872
3876 Instruction* saved_entry = entry_; 3873 Instruction* saved_entry = entry_;
3877 Instruction* saved_exit = exit_; 3874 Instruction* saved_exit = exit_;
3878 entry_ = NULL; 3875 entry_ = NULL;
3879 exit_ = NULL; 3876 exit_ = NULL;
3880 3877
3881 LoadLocalNode* load_jump_cnt = new(I) LoadLocalNode( 3878 LoadLocalNode* load_jump_cnt = new(I) LoadLocalNode(
3882 Scanner::kNoSourcePos, jump_var); 3879 Scanner::kNoSourcePos, jump_var);
3883 ComparisonNode* check_jump_cnt; 3880 ComparisonNode* check_jump_cnt;
3884 const intptr_t num_await_states = owner()->await_joins()->length(); 3881 const intptr_t num_await_states = owner()->await_joins().length();
3885 for (intptr_t i = 0; i < num_await_states; i++) { 3882 for (intptr_t i = 0; i < num_await_states; i++) {
3886 check_jump_cnt = new(I) ComparisonNode( 3883 check_jump_cnt = new(I) ComparisonNode(
3887 Scanner::kNoSourcePos, 3884 Scanner::kNoSourcePos,
3888 Token::kEQ, 3885 Token::kEQ,
3889 load_jump_cnt, 3886 load_jump_cnt,
3890 new(I) LiteralNode( 3887 new(I) LiteralNode(
3891 Scanner::kNoSourcePos, Smi::ZoneHandle(I, Smi::New(i)))); 3888 Scanner::kNoSourcePos, Smi::ZoneHandle(I, Smi::New(i))));
3892 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos); 3889 TestGraphVisitor for_test(owner(), Scanner::kNoSourcePos);
3893 check_jump_cnt->Visit(&for_test); 3890 check_jump_cnt->Visit(&for_test);
3894 EffectGraphVisitor for_true(owner()); 3891 EffectGraphVisitor for_true(owner());
3895 EffectGraphVisitor for_false(owner()); 3892 EffectGraphVisitor for_false(owner());
3896 3893
3897 for_true.BuildAwaitJump(top_scope, 3894 for_true.BuildAwaitJump(top_scope,
3898 (*owner()->await_levels())[i], 3895 owner()->await_levels()[i],
3899 (*owner()->await_joins())[i]); 3896 owner()->await_joins()[i]);
3900 Join(for_test, for_true, for_false); 3897 Join(for_test, for_true, for_false);
3901 3898
3902 if (i == 0) { 3899 if (i == 0) {
3903 // Manually link up the preamble start. 3900 // Manually link up the preamble start.
3904 preamble_start->previous()->set_next(for_test.entry()); 3901 preamble_start->previous()->set_next(for_test.entry());
3905 for_test.entry()->set_previous(preamble_start->previous()); 3902 for_test.entry()->set_previous(preamble_start->previous());
3906 } 3903 }
3907 if (i == (num_await_states - 1)) { 3904 if (i == (num_await_states - 1)) {
3908 // Link up preamble end. 3905 // Link up preamble end.
3909 if (exit_ == NULL) { 3906 if (exit_ == NULL) {
(...skipping 375 matching lines...) Expand 10 before | Expand all | Expand 10 after
4285 Report::MessageF(Report::kBailout, 4282 Report::MessageF(Report::kBailout,
4286 Script::Handle(function.script()), 4283 Script::Handle(function.script()),
4287 function.token_pos(), 4284 function.token_pos(),
4288 "FlowGraphBuilder Bailout: %s %s", 4285 "FlowGraphBuilder Bailout: %s %s",
4289 String::Handle(function.name()).ToCString(), 4286 String::Handle(function.name()).ToCString(),
4290 reason); 4287 reason);
4291 UNREACHABLE(); 4288 UNREACHABLE();
4292 } 4289 }
4293 4290
4294 } // namespace dart 4291 } // namespace dart
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698