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 "vm/kernel_binary_flowgraph.h" | 5 #include "vm/kernel_binary_flowgraph.h" |
6 | 6 |
7 #include "vm/compiler.h" | 7 #include "vm/compiler.h" |
8 #include "vm/longjump.h" | 8 #include "vm/longjump.h" |
9 #include "vm/object_store.h" | 9 #include "vm/object_store.h" |
10 | 10 |
11 #if !defined(DART_PRECOMPILED_RUNTIME) | 11 #if !defined(DART_PRECOMPILED_RUNTIME) |
12 | 12 |
13 namespace dart { | 13 namespace dart { |
14 namespace kernel { | 14 namespace kernel { |
15 | 15 |
16 #define Z (zone_) | 16 #define Z (zone_) |
17 #define H (translation_helper_) | 17 #define H (translation_helper_) |
18 #define T (type_translator_) | 18 #define T (type_translator_) |
19 #define I Isolate::Current() | 19 #define I Isolate::Current() |
20 | 20 |
21 static bool IsStaticInitializer(const Function& function, Zone* zone) { | 21 static bool IsStaticInitializer(const Function& function, Zone* zone) { |
22 return (function.kind() == RawFunction::kImplicitStaticFinalGetter) && | 22 return (function.kind() == RawFunction::kImplicitStaticFinalGetter) && |
23 dart::String::Handle(zone, function.name()) | 23 dart::String::Handle(zone, function.name()) |
24 .StartsWith(Symbols::InitPrefix()); | 24 .StartsWith(Symbols::InitPrefix()); |
25 } | 25 } |
26 | 26 |
27 StreamingScopeBuilder::StreamingScopeBuilder(ParsedFunction* parsed_function, | 27 StreamingScopeBuilder::StreamingScopeBuilder(ParsedFunction* parsed_function, |
28 intptr_t kernel_offset, | 28 intptr_t relative_kernel_offset, |
29 const uint8_t* buffer, | 29 const TypedData& body) |
30 intptr_t buffer_length) | |
31 : result_(NULL), | 30 : result_(NULL), |
32 parsed_function_(parsed_function), | 31 parsed_function_(parsed_function), |
33 kernel_offset_(kernel_offset), | 32 relative_kernel_offset_(relative_kernel_offset), |
34 translation_helper_(Thread::Current()), | 33 translation_helper_(Thread::Current()), |
35 zone_(translation_helper_.zone()), | 34 zone_(translation_helper_.zone()), |
36 current_function_scope_(NULL), | 35 current_function_scope_(NULL), |
37 scope_(NULL), | 36 scope_(NULL), |
38 depth_(0), | 37 depth_(0), |
39 name_index_(0), | 38 name_index_(0), |
40 needs_expr_temp_(false), | 39 needs_expr_temp_(false), |
41 builder_(new StreamingFlowGraphBuilder(&translation_helper_, | 40 builder_(new StreamingFlowGraphBuilder(&translation_helper_, |
42 zone_, | 41 zone_, |
43 buffer, | 42 relative_kernel_offset, |
44 buffer_length)), | 43 body)), |
45 type_translator_(builder_, /*finalize=*/true) { | 44 type_translator_(builder_, /*finalize=*/true) { |
46 Script& script = Script::Handle(Z, parsed_function->function().script()); | 45 Script& script = Script::Handle(Z, parsed_function->function().script()); |
47 H.SetStringOffsets(TypedData::Handle(Z, script.kernel_string_offsets())); | 46 H.SetStringOffsets(TypedData::Handle(Z, script.kernel_string_offsets())); |
48 H.SetStringData(TypedData::Handle(Z, script.kernel_string_data())); | 47 H.SetStringData(TypedData::Handle(Z, script.kernel_string_data())); |
49 H.SetCanonicalNames(TypedData::Handle(Z, script.kernel_canonical_names())); | 48 H.SetCanonicalNames(TypedData::Handle(Z, script.kernel_canonical_names())); |
50 type_translator_.active_class_ = &active_class_; | 49 type_translator_.active_class_ = &active_class_; |
51 } | 50 } |
52 | 51 |
53 StreamingScopeBuilder::~StreamingScopeBuilder() { | 52 StreamingScopeBuilder::~StreamingScopeBuilder() { |
54 delete builder_; | 53 delete builder_; |
55 } | 54 } |
56 | 55 |
57 ScopeBuildingResult* StreamingScopeBuilder::BuildScopes() { | 56 ScopeBuildingResult* StreamingScopeBuilder::BuildScopes() { |
58 if (result_ != NULL) return result_; | 57 if (result_ != NULL) return result_; |
59 | 58 |
60 ASSERT(scope_ == NULL && depth_.loop_ == 0 && depth_.function_ == 0); | 59 ASSERT(scope_ == NULL && depth_.loop_ == 0 && depth_.function_ == 0); |
61 result_ = new (Z) ScopeBuildingResult(); | 60 result_ = new (Z) ScopeBuildingResult(); |
62 | 61 |
63 ParsedFunction* parsed_function = parsed_function_; | 62 const Function& function = parsed_function_->function(); |
64 const Function& function = parsed_function->function(); | |
65 | 63 |
66 // Setup a [ActiveClassScope] and a [ActiveMemberScope] which will be used | 64 // Setup a [ActiveClassScope] and a [ActiveMemberScope] which will be used |
67 // e.g. for type translation. | 65 // e.g. for type translation. |
68 const dart::Class& klass = | 66 const dart::Class& klass = |
69 dart::Class::Handle(zone_, parsed_function_->function().Owner()); | 67 dart::Class::Handle(zone_, parsed_function_->function().Owner()); |
70 | 68 |
71 Function& outermost_function = Function::Handle(Z); | 69 Function& outermost_function = Function::Handle(Z); |
72 builder_->DiscoverEnclosingElements(Z, function, &outermost_function); | 70 builder_->DiscoverEnclosingElements(Z, function, &outermost_function); |
73 | 71 |
74 ActiveClassScope active_class_scope(&active_class_, &klass); | 72 ActiveClassScope active_class_scope(&active_class_, &klass); |
(...skipping 10 matching lines...) Expand all Loading... |
85 | 83 |
86 // Add function type arguments variable before current context variable. | 84 // Add function type arguments variable before current context variable. |
87 if (FLAG_reify_generic_functions && function.IsGeneric()) { | 85 if (FLAG_reify_generic_functions && function.IsGeneric()) { |
88 LocalVariable* type_args_var = MakeVariable( | 86 LocalVariable* type_args_var = MakeVariable( |
89 TokenPosition::kNoSource, TokenPosition::kNoSource, | 87 TokenPosition::kNoSource, TokenPosition::kNoSource, |
90 Symbols::FunctionTypeArgumentsVar(), AbstractType::dynamic_type()); | 88 Symbols::FunctionTypeArgumentsVar(), AbstractType::dynamic_type()); |
91 scope_->AddVariable(type_args_var); | 89 scope_->AddVariable(type_args_var); |
92 parsed_function_->set_function_type_arguments(type_args_var); | 90 parsed_function_->set_function_type_arguments(type_args_var); |
93 } | 91 } |
94 | 92 |
95 LocalVariable* context_var = parsed_function->current_context_var(); | 93 LocalVariable* context_var = parsed_function_->current_context_var(); |
96 context_var->set_is_forced_stack(); | 94 context_var->set_is_forced_stack(); |
97 scope_->AddVariable(context_var); | 95 scope_->AddVariable(context_var); |
98 | 96 |
99 parsed_function->SetNodeSequence( | 97 parsed_function_->SetNodeSequence( |
100 new SequenceNode(TokenPosition::kNoSource, scope_)); | 98 new SequenceNode(TokenPosition::kNoSource, scope_)); |
101 | 99 |
102 builder_->SetOffset(kernel_offset_); | 100 builder_->SetOffset(0); |
103 | 101 |
104 FunctionNodeHelper function_node_helper(builder_); | 102 FunctionNodeHelper function_node_helper(builder_); |
105 | 103 |
106 switch (function.kind()) { | 104 switch (function.kind()) { |
107 case RawFunction::kClosureFunction: | 105 case RawFunction::kClosureFunction: |
108 case RawFunction::kImplicitClosureFunction: | 106 case RawFunction::kImplicitClosureFunction: |
109 case RawFunction::kConvertedClosureFunction: | 107 case RawFunction::kConvertedClosureFunction: |
110 case RawFunction::kRegularFunction: | 108 case RawFunction::kRegularFunction: |
111 case RawFunction::kGetterFunction: | 109 case RawFunction::kGetterFunction: |
112 case RawFunction::kSetterFunction: | 110 case RawFunction::kSetterFunction: |
113 case RawFunction::kConstructor: { | 111 case RawFunction::kConstructor: { |
114 const Tag tag = builder_->PeekTag(); | 112 const Tag tag = builder_->PeekTag(); |
115 intptr_t parent_offset = builder_->ReadUntilFunctionNode(); | 113 builder_->ReadUntilFunctionNode(); |
116 function_node_helper.ReadUntilExcluding( | 114 function_node_helper.ReadUntilExcluding( |
117 FunctionNodeHelper::kPositionalParameters); | 115 FunctionNodeHelper::kPositionalParameters); |
118 current_function_async_marker_ = function_node_helper.async_marker_; | 116 current_function_async_marker_ = function_node_helper.async_marker_; |
119 // NOTE: FunctionNode is read further below the if. | 117 // NOTE: FunctionNode is read further below the if. |
120 | 118 |
121 intptr_t pos = 0; | 119 intptr_t pos = 0; |
122 if (function.IsClosureFunction()) { | 120 if (function.IsClosureFunction()) { |
123 LocalVariable* variable = MakeVariable( | 121 LocalVariable* variable = MakeVariable( |
124 TokenPosition::kNoSource, TokenPosition::kNoSource, | 122 TokenPosition::kNoSource, TokenPosition::kNoSource, |
125 Symbols::ClosureParameter(), AbstractType::dynamic_type()); | 123 Symbols::ClosureParameter(), AbstractType::dynamic_type()); |
126 variable->set_is_forced_stack(); | 124 variable->set_is_forced_stack(); |
127 scope_->InsertParameterAt(pos++, variable); | 125 scope_->InsertParameterAt(pos++, variable); |
128 } else if (!function.is_static()) { | 126 } else if (!function.is_static()) { |
129 // We use [is_static] instead of [IsStaticFunction] because the latter | 127 // We use [is_static] instead of [IsStaticFunction] because the latter |
130 // returns `false` for constructors. | 128 // returns `false` for constructors. |
131 dart::Class& klass = dart::Class::Handle(Z, function.Owner()); | 129 dart::Class& klass = dart::Class::Handle(Z, function.Owner()); |
132 Type& klass_type = H.GetCanonicalType(klass); | 130 Type& klass_type = H.GetCanonicalType(klass); |
133 LocalVariable* variable = | 131 LocalVariable* variable = |
134 MakeVariable(TokenPosition::kNoSource, TokenPosition::kNoSource, | 132 MakeVariable(TokenPosition::kNoSource, TokenPosition::kNoSource, |
135 Symbols::This(), klass_type); | 133 Symbols::This(), klass_type); |
136 scope_->InsertParameterAt(pos++, variable); | 134 scope_->InsertParameterAt(pos++, variable); |
137 result_->this_variable = variable; | 135 result_->this_variable = variable; |
138 | 136 |
139 // We visit instance field initializers because they might contain | 137 // We visit instance field initializers because they might contain |
140 // [Let] expressions and we need to have a mapping. | 138 // [Let] expressions and we need to have a mapping. |
141 if (tag == kConstructor) { | 139 if (tag == kConstructor) { |
142 ASSERT(parent_offset >= 0); | 140 Class& parent_class = Class::Handle(Z, function.Owner()); |
143 AlternativeReadingScope alt(builder_->reader_, parent_offset); | 141 Array& class_fields = Array::Handle(Z, parent_class.fields()); |
144 ClassHelper class_helper(builder_); | 142 dart::Field& class_field = dart::Field::Handle(Z); |
145 class_helper.ReadUntilExcluding(ClassHelper::kFields); | 143 for (intptr_t i = 0; i < class_fields.Length(); ++i) { |
146 intptr_t list_length = | 144 class_field ^= class_fields.At(i); |
147 builder_->ReadListLength(); // read fields list length. | 145 if (!class_field.is_static()) { |
148 for (intptr_t i = 0; i < list_length; i++) { | 146 TypedData& kernel_body = |
149 intptr_t field_offset = builder_->ReaderOffset(); | 147 TypedData::Handle(Z, class_field.kernel_body()); |
150 FieldHelper field_helper(builder_); | 148 ASSERT(!kernel_body.IsNull()); |
151 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); | 149 AlternativeReadingScope alt(builder_->reader_, &kernel_body, 0); |
152 Tag initializer_tag = | 150 intptr_t saved_relative_kernel_offset_ = relative_kernel_offset_; |
153 builder_->ReadTag(); // read first part of initializer. | 151 relative_kernel_offset_ = class_field.kernel_offset(); |
154 if (!field_helper.IsStatic() && initializer_tag == kSomething) { | 152 FieldHelper field_helper(builder_); |
155 EnterScope(field_offset); | 153 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); |
156 VisitExpression(); // read initializer. | 154 Tag initializer_tag = |
157 ExitScope(field_helper.position_, field_helper.end_position_); | 155 builder_->ReadTag(); // read first part of initializer. |
158 } else if (initializer_tag == kSomething) { | 156 if (initializer_tag == kSomething) { |
159 builder_->SkipExpression(); // read initializer. | 157 EnterScope(class_field.kernel_offset()); |
| 158 VisitExpression(); // read initializer. |
| 159 ExitScope(field_helper.position_, field_helper.end_position_); |
| 160 } |
| 161 relative_kernel_offset_ = saved_relative_kernel_offset_; |
160 } | 162 } |
161 } | 163 } |
162 } | 164 } |
163 } else if (function.IsFactory()) { | 165 } else if (function.IsFactory()) { |
164 LocalVariable* variable = MakeVariable( | 166 LocalVariable* variable = MakeVariable( |
165 TokenPosition::kNoSource, TokenPosition::kNoSource, | 167 TokenPosition::kNoSource, TokenPosition::kNoSource, |
166 Symbols::TypeArgumentsParameter(), AbstractType::dynamic_type()); | 168 Symbols::TypeArgumentsParameter(), AbstractType::dynamic_type()); |
167 scope_->InsertParameterAt(pos++, variable); | 169 scope_->InsertParameterAt(pos++, variable); |
168 result_->type_arguments_variable = variable; | 170 result_->type_arguments_variable = variable; |
169 } | 171 } |
170 | 172 |
171 // Continue reading FunctionNode: | 173 // Continue reading FunctionNode: |
172 // read positional_parameters and named_parameters. | 174 // read positional_parameters and named_parameters. |
173 AddPositionalAndNamedParameters(pos); | 175 AddPositionalAndNamedParameters(pos); |
174 | 176 |
175 // We generate a syntethic body for implicit closure functions - which | 177 // We generate a synthetic body for implicit closure functions - which |
176 // will forward the call to the real function. | 178 // will forward the call to the real function. |
177 // -> see BuildGraphOfImplicitClosureFunction | 179 // -> see BuildGraphOfImplicitClosureFunction |
178 if (!function.IsImplicitClosureFunction()) { | 180 if (!function.IsImplicitClosureFunction()) { |
179 builder_->SetOffset(kernel_offset_); | 181 builder_->SetOffset(0); |
180 first_body_token_position_ = TokenPosition::kNoSource; | 182 first_body_token_position_ = TokenPosition::kNoSource; |
181 VisitNode(); | 183 VisitNode(); |
182 | 184 |
183 // TODO(jensj): HACK: Push the begin token to after any parameters to | 185 // TODO(jensj): HACK: Push the begin token to after any parameters to |
184 // avoid crash when breaking on definition line of async method in | 186 // avoid crash when breaking on definition line of async method in |
185 // debugger. It seems that another scope needs to be added | 187 // debugger. It seems that another scope needs to be added |
186 // in which captures are made, but I can't make that work. | 188 // in which captures are made, but I can't make that work. |
187 // This 'solution' doesn't crash, but I cannot see the parameters at | 189 // This 'solution' doesn't crash, but I cannot see the parameters at |
188 // that particular breakpoint either. | 190 // that particular breakpoint either. |
189 // Also push the end token to after the "}" to avoid crashing on | 191 // Also push the end token to after the "}" to avoid crashing on |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
249 scope_->InsertParameterAt(i, variable); | 251 scope_->InsertParameterAt(i, variable); |
250 } | 252 } |
251 break; | 253 break; |
252 case RawFunction::kSignatureFunction: | 254 case RawFunction::kSignatureFunction: |
253 case RawFunction::kIrregexpFunction: | 255 case RawFunction::kIrregexpFunction: |
254 UNREACHABLE(); | 256 UNREACHABLE(); |
255 } | 257 } |
256 if (needs_expr_temp_) { | 258 if (needs_expr_temp_) { |
257 scope_->AddVariable(parsed_function_->EnsureExpressionTemp()); | 259 scope_->AddVariable(parsed_function_->EnsureExpressionTemp()); |
258 } | 260 } |
259 parsed_function->AllocateVariables(); | 261 parsed_function_->AllocateVariables(); |
260 | 262 |
261 return result_; | 263 return result_; |
262 } | 264 } |
263 | 265 |
264 void StreamingScopeBuilder::VisitNode() { | 266 void StreamingScopeBuilder::VisitNode() { |
265 Tag tag = builder_->PeekTag(); | 267 Tag tag = builder_->PeekTag(); |
266 switch (tag) { | 268 switch (tag) { |
267 case kConstructor: | 269 case kConstructor: |
268 VisitConstructor(); | 270 VisitConstructor(); |
269 return; | 271 return; |
(...skipping 13 matching lines...) Expand all Loading... |
283 } | 285 } |
284 | 286 |
285 void StreamingScopeBuilder::VisitConstructor() { | 287 void StreamingScopeBuilder::VisitConstructor() { |
286 // Field initializers that come from non-static field declarations are | 288 // Field initializers that come from non-static field declarations are |
287 // compiled as if they appear in the constructor initializer list. This is | 289 // compiled as if they appear in the constructor initializer list. This is |
288 // important for closure-valued field initializers because the VM expects the | 290 // important for closure-valued field initializers because the VM expects the |
289 // corresponding closure functions to appear as if they were nested inside the | 291 // corresponding closure functions to appear as if they were nested inside the |
290 // constructor. | 292 // constructor. |
291 ConstructorHelper constructor_helper(builder_); | 293 ConstructorHelper constructor_helper(builder_); |
292 constructor_helper.ReadUntilExcluding(ConstructorHelper::kFunction); | 294 constructor_helper.ReadUntilExcluding(ConstructorHelper::kFunction); |
293 intptr_t parent_offset = constructor_helper.parent_class_binary_offset_; | |
294 ASSERT(parent_offset >= 0); | |
295 { | 295 { |
296 AlternativeReadingScope alt(builder_->reader_, parent_offset); | 296 const Function& function = parsed_function_->function(); |
297 ClassHelper class_helper(builder_); | 297 Class& parent_class = Class::Handle(Z, function.Owner()); |
298 class_helper.ReadUntilExcluding(ClassHelper::kFields); | 298 Array& class_fields = Array::Handle(Z, parent_class.fields()); |
299 | 299 dart::Field& class_field = dart::Field::Handle(Z); |
300 intptr_t list_length = | 300 for (intptr_t i = 0; i < class_fields.Length(); ++i) { |
301 builder_->ReadListLength(); // read fields list length. | 301 class_field ^= class_fields.At(i); |
302 for (intptr_t i = 0; i < list_length; i++) { | 302 if (!class_field.is_static()) { |
303 FieldHelper field_helper(builder_); | 303 TypedData& kernel_body = |
304 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); | 304 TypedData::Handle(Z, class_field.kernel_body()); |
305 Tag initializer_tag = builder_->ReadTag(); | 305 ASSERT(!kernel_body.IsNull()); |
306 if (!field_helper.IsStatic() && initializer_tag == kSomething) { | 306 AlternativeReadingScope alt(builder_->reader_, &kernel_body, 0); |
307 VisitExpression(); // read initializer. | 307 intptr_t saved_relative_kernel_offset_ = relative_kernel_offset_; |
308 } else if (initializer_tag == kSomething) { | 308 relative_kernel_offset_ = class_field.kernel_offset(); |
309 builder_->SkipExpression(); // read initializer. | 309 FieldHelper field_helper(builder_); |
| 310 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); |
| 311 Tag initializer_tag = builder_->ReadTag(); |
| 312 if (initializer_tag == kSomething) { |
| 313 VisitExpression(); // read initializer. |
| 314 } |
| 315 relative_kernel_offset_ = saved_relative_kernel_offset_; |
310 } | 316 } |
311 } | 317 } |
312 } | 318 } |
313 | 319 |
314 // Visit children (note that there's no reason to visit the name). | 320 // Visit children (note that there's no reason to visit the name). |
315 VisitFunctionNode(); | 321 VisitFunctionNode(); |
316 intptr_t list_length = | 322 intptr_t list_length = |
317 builder_->ReadListLength(); // read initializers list length. | 323 builder_->ReadListLength(); // read initializers list length. |
318 for (intptr_t i = 0; i < list_length; i++) { | 324 for (intptr_t i = 0; i < list_length; i++) { |
319 VisitInitializer(); | 325 VisitInitializer(); |
(...skipping 293 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
613 intptr_t offset = | 619 intptr_t offset = |
614 builder_->ReaderOffset() - 1; // -1 to include tag byte. | 620 builder_->ReaderOffset() - 1; // -1 to include tag byte. |
615 HandleLocalFunction(offset); // read function node. | 621 HandleLocalFunction(offset); // read function node. |
616 return; | 622 return; |
617 } | 623 } |
618 case kLet: { | 624 case kLet: { |
619 PositionScope scope(builder_->reader_); | 625 PositionScope scope(builder_->reader_); |
620 intptr_t offset = | 626 intptr_t offset = |
621 builder_->ReaderOffset() - 1; // -1 to include tag byte. | 627 builder_->ReaderOffset() - 1; // -1 to include tag byte. |
622 | 628 |
623 EnterScope(offset); | 629 EnterScope(relative_kernel_offset_ + offset); |
624 | 630 |
625 VisitVariableDeclaration(); // read variable declaration. | 631 VisitVariableDeclaration(); // read variable declaration. |
626 VisitExpression(); // read expression. | 632 VisitExpression(); // read expression. |
627 | 633 |
628 ExitScope(builder_->reader_->min_position(), | 634 ExitScope(builder_->reader_->min_position(), |
629 builder_->reader_->max_position()); | 635 builder_->reader_->max_position()); |
630 return; | 636 return; |
631 } | 637 } |
632 case kBigIntLiteral: | 638 case kBigIntLiteral: |
633 builder_->SkipStringReference(); // read string reference. | 639 builder_->SkipStringReference(); // read string reference. |
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
683 case kInvalidStatement: | 689 case kInvalidStatement: |
684 return; | 690 return; |
685 case kExpressionStatement: | 691 case kExpressionStatement: |
686 VisitExpression(); // read expression. | 692 VisitExpression(); // read expression. |
687 return; | 693 return; |
688 case kBlock: { | 694 case kBlock: { |
689 PositionScope scope(builder_->reader_); | 695 PositionScope scope(builder_->reader_); |
690 intptr_t offset = | 696 intptr_t offset = |
691 builder_->ReaderOffset() - 1; // -1 to include tag byte. | 697 builder_->ReaderOffset() - 1; // -1 to include tag byte. |
692 | 698 |
693 EnterScope(offset); | 699 EnterScope(relative_kernel_offset_ + offset); |
694 | 700 |
695 intptr_t list_length = | 701 intptr_t list_length = |
696 builder_->ReadListLength(); // read number of statements. | 702 builder_->ReadListLength(); // read number of statements. |
697 for (intptr_t i = 0; i < list_length; ++i) { | 703 for (intptr_t i = 0; i < list_length; ++i) { |
698 VisitStatement(); // read ith statement. | 704 VisitStatement(); // read ith statement. |
699 } | 705 } |
700 | 706 |
701 ExitScope(builder_->reader_->min_position(), | 707 ExitScope(builder_->reader_->min_position(), |
702 builder_->reader_->max_position()); | 708 builder_->reader_->max_position()); |
703 return; | 709 return; |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
742 VisitStatement(); // read body. | 748 VisitStatement(); // read body. |
743 VisitExpression(); // read condition. | 749 VisitExpression(); // read condition. |
744 --depth_.loop_; | 750 --depth_.loop_; |
745 return; | 751 return; |
746 case kForStatement: { | 752 case kForStatement: { |
747 PositionScope scope(builder_->reader_); | 753 PositionScope scope(builder_->reader_); |
748 | 754 |
749 intptr_t offset = | 755 intptr_t offset = |
750 builder_->ReaderOffset() - 1; // -1 to include tag byte. | 756 builder_->ReaderOffset() - 1; // -1 to include tag byte. |
751 | 757 |
752 EnterScope(offset); | 758 EnterScope(relative_kernel_offset_ + offset); |
753 | 759 |
754 intptr_t list_length = | 760 intptr_t list_length = |
755 builder_->ReadListLength(); // read number of variables. | 761 builder_->ReadListLength(); // read number of variables. |
756 for (intptr_t i = 0; i < list_length; ++i) { | 762 for (intptr_t i = 0; i < list_length; ++i) { |
757 VisitVariableDeclaration(); // read ith variable. | 763 VisitVariableDeclaration(); // read ith variable. |
758 } | 764 } |
759 | 765 |
760 ++depth_.loop_; | 766 ++depth_.loop_; |
761 | 767 |
762 Tag tag = builder_->ReadTag(); // Read first part of condition. | 768 Tag tag = builder_->ReadTag(); // Read first part of condition. |
(...skipping 23 matching lines...) Expand all Loading... |
786 | 792 |
787 // Notice the ordering: We skip the variable, read the iterable, go back, | 793 // Notice the ordering: We skip the variable, read the iterable, go back, |
788 // re-read the variable, go forward to after having read the iterable. | 794 // re-read the variable, go forward to after having read the iterable. |
789 intptr_t offset = builder_->ReaderOffset(); | 795 intptr_t offset = builder_->ReaderOffset(); |
790 builder_->SkipVariableDeclaration(); // read variable. | 796 builder_->SkipVariableDeclaration(); // read variable. |
791 VisitExpression(); // read iterable. | 797 VisitExpression(); // read iterable. |
792 | 798 |
793 ++depth_.for_in_; | 799 ++depth_.for_in_; |
794 AddIteratorVariable(); | 800 AddIteratorVariable(); |
795 ++depth_.loop_; | 801 ++depth_.loop_; |
796 EnterScope(start_offset); | 802 EnterScope(relative_kernel_offset_ + start_offset); |
797 | 803 |
798 { | 804 { |
799 AlternativeReadingScope alt(builder_->reader_, offset); | 805 AlternativeReadingScope alt(builder_->reader_, offset); |
800 VisitVariableDeclaration(); // read variable. | 806 VisitVariableDeclaration(); // read variable. |
801 } | 807 } |
802 VisitStatement(); // read body. | 808 VisitStatement(); // read body. |
803 | 809 |
804 if (!position.IsReal()) { | 810 if (!position.IsReal()) { |
805 position = builder_->reader_->min_position(); | 811 position = builder_->reader_->min_position(); |
806 } | 812 } |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
862 ++depth_.catch_; | 868 ++depth_.catch_; |
863 AddCatchVariables(); | 869 AddCatchVariables(); |
864 | 870 |
865 builder_->ReadBool(); // read any_catch_needs_stack_trace. | 871 builder_->ReadBool(); // read any_catch_needs_stack_trace. |
866 intptr_t catch_count = | 872 intptr_t catch_count = |
867 builder_->ReadListLength(); // read number of catches. | 873 builder_->ReadListLength(); // read number of catches. |
868 for (intptr_t i = 0; i < catch_count; ++i) { | 874 for (intptr_t i = 0; i < catch_count; ++i) { |
869 PositionScope scope(builder_->reader_); | 875 PositionScope scope(builder_->reader_); |
870 intptr_t offset = builder_->ReaderOffset(); // Catch has no tag. | 876 intptr_t offset = builder_->ReaderOffset(); // Catch has no tag. |
871 | 877 |
872 EnterScope(offset); | 878 EnterScope(relative_kernel_offset_ + offset); |
873 | 879 |
874 VisitDartType(); // Read the guard. | 880 VisitDartType(); // Read the guard. |
875 tag = builder_->ReadTag(); // read first part of exception. | 881 tag = builder_->ReadTag(); // read first part of exception. |
876 if (tag == kSomething) { | 882 if (tag == kSomething) { |
877 VisitVariableDeclaration(); // read exception. | 883 VisitVariableDeclaration(); // read exception. |
878 } | 884 } |
879 tag = builder_->ReadTag(); // read first part of stack trace. | 885 tag = builder_->ReadTag(); // read first part of stack trace. |
880 if (tag == kSomething) { | 886 if (tag == kSomething) { |
881 VisitVariableDeclaration(); // read stack trace. | 887 VisitVariableDeclaration(); // read stack trace. |
882 } | 888 } |
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
991 TokenPosition end_position = builder_->reader_->max_position(); | 997 TokenPosition end_position = builder_->reader_->max_position(); |
992 if (end_position.IsReal()) { | 998 if (end_position.IsReal()) { |
993 end_position.Next(); | 999 end_position.Next(); |
994 } | 1000 } |
995 LocalVariable* variable = | 1001 LocalVariable* variable = |
996 MakeVariable(helper.position_, end_position, name, type); | 1002 MakeVariable(helper.position_, end_position, name, type); |
997 if (helper.IsFinal()) { | 1003 if (helper.IsFinal()) { |
998 variable->set_is_final(); | 1004 variable->set_is_final(); |
999 } | 1005 } |
1000 scope_->AddVariable(variable); | 1006 scope_->AddVariable(variable); |
1001 result_->locals.Insert(kernel_offset_no_tag, variable); | 1007 result_->locals.Insert(relative_kernel_offset_ + kernel_offset_no_tag, |
| 1008 variable); |
1002 } | 1009 } |
1003 | 1010 |
1004 void StreamingScopeBuilder::VisitDartType() { | 1011 void StreamingScopeBuilder::VisitDartType() { |
1005 Tag tag = builder_->ReadTag(); | 1012 Tag tag = builder_->ReadTag(); |
1006 switch (tag) { | 1013 switch (tag) { |
1007 case kInvalidType: | 1014 case kInvalidType: |
1008 case kDynamicType: | 1015 case kDynamicType: |
1009 case kVoidType: | 1016 case kVoidType: |
1010 case kBottomType: | 1017 case kBottomType: |
1011 case kVectorType: | 1018 case kVectorType: |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1100 | 1107 |
1101 FunctionNodeHelper function_node_helper(builder_); | 1108 FunctionNodeHelper function_node_helper(builder_); |
1102 function_node_helper.ReadUntilExcluding( | 1109 function_node_helper.ReadUntilExcluding( |
1103 FunctionNodeHelper::kPositionalParameters); | 1110 FunctionNodeHelper::kPositionalParameters); |
1104 | 1111 |
1105 LocalScope* saved_function_scope = current_function_scope_; | 1112 LocalScope* saved_function_scope = current_function_scope_; |
1106 FunctionNode::AsyncMarker saved_function_async_marker = | 1113 FunctionNode::AsyncMarker saved_function_async_marker = |
1107 current_function_async_marker_; | 1114 current_function_async_marker_; |
1108 StreamingScopeBuilder::DepthState saved_depth_state = depth_; | 1115 StreamingScopeBuilder::DepthState saved_depth_state = depth_; |
1109 depth_ = DepthState(depth_.function_ + 1); | 1116 depth_ = DepthState(depth_.function_ + 1); |
1110 EnterScope(parent_kernel_offset); | 1117 EnterScope(relative_kernel_offset_ + parent_kernel_offset); |
1111 current_function_scope_ = scope_; | 1118 current_function_scope_ = scope_; |
1112 current_function_async_marker_ = function_node_helper.async_marker_; | 1119 current_function_async_marker_ = function_node_helper.async_marker_; |
1113 if (depth_.function_ == 1) { | 1120 if (depth_.function_ == 1) { |
1114 FunctionScope function_scope = {offset, scope_}; | 1121 FunctionScope function_scope = {relative_kernel_offset_ + offset, scope_}; |
1115 result_->function_scopes.Add(function_scope); | 1122 result_->function_scopes.Add(function_scope); |
1116 } | 1123 } |
1117 | 1124 |
1118 // read positional_parameters and named_parameters. | 1125 // read positional_parameters and named_parameters. |
1119 AddPositionalAndNamedParameters(); | 1126 AddPositionalAndNamedParameters(); |
1120 | 1127 |
1121 // "Peek" is now done. | 1128 // "Peek" is now done. |
1122 builder_->SetOffset(offset); | 1129 builder_->SetOffset(offset); |
1123 | 1130 |
1124 VisitFunctionNode(); // read function node. | 1131 VisitFunctionNode(); // read function node. |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1167 | 1174 |
1168 LocalVariable* variable = | 1175 LocalVariable* variable = |
1169 MakeVariable(helper.position_, helper.position_, name, type); | 1176 MakeVariable(helper.position_, helper.position_, name, type); |
1170 if (helper.IsFinal()) { | 1177 if (helper.IsFinal()) { |
1171 variable->set_is_final(); | 1178 variable->set_is_final(); |
1172 } | 1179 } |
1173 if (variable->name().raw() == Symbols::IteratorParameter().raw()) { | 1180 if (variable->name().raw() == Symbols::IteratorParameter().raw()) { |
1174 variable->set_is_forced_stack(); | 1181 variable->set_is_forced_stack(); |
1175 } | 1182 } |
1176 scope_->InsertParameterAt(pos, variable); | 1183 scope_->InsertParameterAt(pos, variable); |
1177 result_->locals.Insert(kernel_offset, variable); | 1184 result_->locals.Insert(relative_kernel_offset_ + kernel_offset, variable); |
1178 | 1185 |
1179 // The default value may contain 'let' bindings for which the constant | 1186 // The default value may contain 'let' bindings for which the constant |
1180 // evaluator needs scope bindings. | 1187 // evaluator needs scope bindings. |
1181 Tag tag = builder_->ReadTag(); | 1188 Tag tag = builder_->ReadTag(); |
1182 if (tag == kSomething) { | 1189 if (tag == kSomething) { |
1183 VisitExpression(); // read initializer. | 1190 VisitExpression(); // read initializer. |
1184 } | 1191 } |
1185 } | 1192 } |
1186 | 1193 |
1187 LocalVariable* StreamingScopeBuilder::MakeVariable( | 1194 LocalVariable* StreamingScopeBuilder::MakeVariable( |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1265 if ((depth_.function_ == 0) && (result_->switch_variable == NULL)) { | 1272 if ((depth_.function_ == 0) && (result_->switch_variable == NULL)) { |
1266 LocalVariable* variable = | 1273 LocalVariable* variable = |
1267 MakeVariable(TokenPosition::kNoSource, TokenPosition::kNoSource, | 1274 MakeVariable(TokenPosition::kNoSource, TokenPosition::kNoSource, |
1268 Symbols::SwitchExpr(), AbstractType::dynamic_type()); | 1275 Symbols::SwitchExpr(), AbstractType::dynamic_type()); |
1269 variable->set_is_forced_stack(); | 1276 variable->set_is_forced_stack(); |
1270 current_function_scope_->AddVariable(variable); | 1277 current_function_scope_->AddVariable(variable); |
1271 result_->switch_variable = variable; | 1278 result_->switch_variable = variable; |
1272 } | 1279 } |
1273 } | 1280 } |
1274 | 1281 |
1275 void StreamingScopeBuilder::LookupVariable(intptr_t declaration_binary_offest) { | 1282 void StreamingScopeBuilder::LookupVariable(intptr_t declaration_binary_offset) { |
1276 LocalVariable* variable = result_->locals.Lookup(declaration_binary_offest); | 1283 LocalVariable* variable = result_->locals.Lookup(declaration_binary_offset); |
1277 if (variable == NULL) { | 1284 if (variable == NULL) { |
1278 // We have not seen a declaration of the variable, so it must be the | 1285 // We have not seen a declaration of the variable, so it must be the |
1279 // case that we are compiling a nested function and the variable is | 1286 // case that we are compiling a nested function and the variable is |
1280 // declared in an outer scope. In that case, look it up in the scope by | 1287 // declared in an outer scope. In that case, look it up in the scope by |
1281 // name and add it to the variable map to simplify later lookup. | 1288 // name and add it to the variable map to simplify later lookup. |
1282 ASSERT(current_function_scope_->parent() != NULL); | 1289 ASSERT(current_function_scope_->parent() != NULL); |
1283 | 1290 StringIndex var_name = builder_->GetNameFromVariableDeclaration( |
1284 StringIndex var_name = | 1291 declaration_binary_offset, parsed_function_->function()); |
1285 builder_->GetNameFromVariableDeclaration(declaration_binary_offest); | |
1286 | 1292 |
1287 const dart::String& name = H.DartSymbol(var_name); | 1293 const dart::String& name = H.DartSymbol(var_name); |
1288 variable = current_function_scope_->parent()->LookupVariable(name, true); | 1294 variable = current_function_scope_->parent()->LookupVariable(name, true); |
1289 ASSERT(variable != NULL); | 1295 ASSERT(variable != NULL); |
1290 result_->locals.Insert(declaration_binary_offest, variable); | 1296 result_->locals.Insert(declaration_binary_offset, variable); |
1291 } | 1297 } |
1292 | 1298 |
1293 if (variable->owner()->function_level() < scope_->function_level()) { | 1299 if (variable->owner()->function_level() < scope_->function_level()) { |
1294 // We call `LocalScope->CaptureVariable(variable)` in two scenarios for two | 1300 // We call `LocalScope->CaptureVariable(variable)` in two scenarios for two |
1295 // different reasons: | 1301 // different reasons: |
1296 // Scenario 1: | 1302 // Scenario 1: |
1297 // We need to know which variables defined in this function | 1303 // We need to know which variables defined in this function |
1298 // are closed over by nested closures in order to ensure we will | 1304 // are closed over by nested closures in order to ensure we will |
1299 // create a [Context] object of appropriate size and store captured | 1305 // create a [Context] object of appropriate size and store captured |
1300 // variables there instead of the stack. | 1306 // variables there instead of the stack. |
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1456 dart::Object::Handle(Z, H.LookupClassByKernelClass(klass_name)); | 1462 dart::Object::Handle(Z, H.LookupClassByKernelClass(klass_name)); |
1457 result_ = Type::New(klass, type_arguments, TokenPosition::kNoSource); | 1463 result_ = Type::New(klass, type_arguments, TokenPosition::kNoSource); |
1458 if (finalize_) { | 1464 if (finalize_) { |
1459 ASSERT(active_class_->klass != NULL); | 1465 ASSERT(active_class_->klass != NULL); |
1460 result_ = ClassFinalizer::FinalizeType(*active_class_->klass, result_); | 1466 result_ = ClassFinalizer::FinalizeType(*active_class_->klass, result_); |
1461 } | 1467 } |
1462 } | 1468 } |
1463 | 1469 |
1464 void StreamingDartTypeTranslator::BuildFunctionType(bool simple) { | 1470 void StreamingDartTypeTranslator::BuildFunctionType(bool simple) { |
1465 intptr_t list_length = 0; | 1471 intptr_t list_length = 0; |
1466 intptr_t first_item_offest = -1; | |
1467 if (!simple) { | 1472 if (!simple) { |
1468 list_length = | 1473 list_length = |
1469 builder_->ReadListLength(); // read type_parameters list length | 1474 builder_->ReadListLength(); // read type_parameters list length |
1470 first_item_offest = builder_->ReaderOffset(); | |
1471 for (int i = 0; i < list_length; ++i) { | 1475 for (int i = 0; i < list_length; ++i) { |
1472 builder_->SkipStringReference(); // read string index (name). | 1476 builder_->SkipStringReference(); // read string index (name). |
1473 builder_->SkipDartType(); // read dart type. | 1477 builder_->SkipDartType(); // read dart type. |
1474 } | 1478 } |
1475 } | 1479 } |
1476 | 1480 |
1477 // The spec describes in section "19.1 Static Types": | 1481 // The spec describes in section "19.1 Static Types": |
1478 // | 1482 // |
1479 // Any use of a malformed type gives rise to a static warning. A | 1483 // Any use of a malformed type gives rise to a static warning. A |
1480 // malformed type is then interpreted as dynamic by the static type | 1484 // malformed type is then interpreted as dynamic by the static type |
1481 // checker and the runtime unless explicitly specified otherwise. | 1485 // checker and the runtime unless explicitly specified otherwise. |
1482 // | 1486 // |
1483 // So we convert malformed return/parameter types to `dynamic`. | 1487 // So we convert malformed return/parameter types to `dynamic`. |
1484 TypeParameterScope scope(this, first_item_offest, list_length); | 1488 TypeParameterScope scope(this, list_length); |
1485 | 1489 |
1486 Function& signature_function = Function::ZoneHandle( | 1490 Function& signature_function = Function::ZoneHandle( |
1487 Z, | 1491 Z, |
1488 Function::NewSignatureFunction(*active_class_->klass, Function::Handle(Z), | 1492 Function::NewSignatureFunction(*active_class_->klass, Function::Handle(Z), |
1489 TokenPosition::kNoSource)); | 1493 TokenPosition::kNoSource)); |
1490 | 1494 |
1491 intptr_t required_count; | 1495 intptr_t required_count; |
1492 intptr_t all_count; | 1496 intptr_t all_count; |
1493 intptr_t positional_count; | 1497 intptr_t positional_count; |
1494 if (!simple) { | 1498 if (!simple) { |
(...skipping 729 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2224 | 2228 |
2225 // NOTE: This needs to be kept in sync with `runtime/lib/immutable_map.dart`! | 2229 // NOTE: This needs to be kept in sync with `runtime/lib/immutable_map.dart`! |
2226 result_ = Instance::New(map_class, Heap::kOld); | 2230 result_ = Instance::New(map_class, Heap::kOld); |
2227 ASSERT(!result_.IsNull()); | 2231 ASSERT(!result_.IsNull()); |
2228 result_.SetTypeArguments(type_arguments); | 2232 result_.SetTypeArguments(type_arguments); |
2229 result_.SetField(field, const_kv_array); | 2233 result_.SetField(field, const_kv_array); |
2230 result_ = H.Canonicalize(result_); | 2234 result_ = H.Canonicalize(result_); |
2231 } | 2235 } |
2232 | 2236 |
2233 void StreamingConstantEvaluator::EvaluateLet() { | 2237 void StreamingConstantEvaluator::EvaluateLet() { |
2234 intptr_t kernel_position = builder_->ReaderOffset(); | 2238 intptr_t kernel_position = |
| 2239 builder_->ReaderOffset() + builder_->relative_kernel_offset_; |
2235 LocalVariable* local = builder_->LookupVariable(kernel_position); | 2240 LocalVariable* local = builder_->LookupVariable(kernel_position); |
2236 | 2241 |
2237 // read variable declaration. | 2242 // read variable declaration. |
2238 VariableDeclarationHelper helper(builder_); | 2243 VariableDeclarationHelper helper(builder_); |
2239 helper.ReadUntilExcluding(VariableDeclarationHelper::kInitializer); | 2244 helper.ReadUntilExcluding(VariableDeclarationHelper::kInitializer); |
2240 Tag tag = builder_->ReadTag(); // read (first part of) initializer. | 2245 Tag tag = builder_->ReadTag(); // read (first part of) initializer. |
2241 if (tag == kNothing) { | 2246 if (tag == kNothing) { |
2242 local->SetConstValue(Instance::ZoneHandle(Z, dart::Instance::null())); | 2247 local->SetConstValue(Instance::ZoneHandle(Z, dart::Instance::null())); |
2243 } else { | 2248 } else { |
2244 local->SetConstValue(EvaluateExpression( | 2249 local->SetConstValue(EvaluateExpression( |
(...skipping 184 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2429 // evaluated only once. | 2434 // evaluated only once. |
2430 return false; | 2435 return false; |
2431 } | 2436 } |
2432 | 2437 |
2433 bool is_present = false; | 2438 bool is_present = false; |
2434 ASSERT(!script_.InVMHeap()); | 2439 ASSERT(!script_.InVMHeap()); |
2435 if (script_.compile_time_constants() == Array::null()) { | 2440 if (script_.compile_time_constants() == Array::null()) { |
2436 return false; | 2441 return false; |
2437 } | 2442 } |
2438 KernelConstantsMap constants(script_.compile_time_constants()); | 2443 KernelConstantsMap constants(script_.compile_time_constants()); |
2439 *value ^= constants.GetOrNull(kernel_offset, &is_present); | 2444 *value ^= constants.GetOrNull( |
| 2445 kernel_offset + builder_->relative_kernel_offset_, &is_present); |
2440 // Mutator compiler thread may add constants while background compiler | 2446 // Mutator compiler thread may add constants while background compiler |
2441 // is running, and thus change the value of 'compile_time_constants'; | 2447 // is running, and thus change the value of 'compile_time_constants'; |
2442 // do not assert that 'compile_time_constants' has not changed. | 2448 // do not assert that 'compile_time_constants' has not changed. |
2443 constants.Release(); | 2449 constants.Release(); |
2444 if (FLAG_compiler_stats && is_present) { | 2450 if (FLAG_compiler_stats && is_present) { |
2445 ++H.thread()->compiler_stats()->num_const_cache_hits; | 2451 ++H.thread()->compiler_stats()->num_const_cache_hits; |
2446 } | 2452 } |
2447 return is_present; | 2453 return is_present; |
2448 } | 2454 } |
2449 | 2455 |
(...skipping 10 matching lines...) Expand all Loading... |
2460 return; | 2466 return; |
2461 } | 2467 } |
2462 const intptr_t kInitialConstMapSize = 16; | 2468 const intptr_t kInitialConstMapSize = 16; |
2463 ASSERT(!script_.InVMHeap()); | 2469 ASSERT(!script_.InVMHeap()); |
2464 if (script_.compile_time_constants() == Array::null()) { | 2470 if (script_.compile_time_constants() == Array::null()) { |
2465 const Array& array = Array::Handle( | 2471 const Array& array = Array::Handle( |
2466 HashTables::New<KernelConstantsMap>(kInitialConstMapSize, Heap::kNew)); | 2472 HashTables::New<KernelConstantsMap>(kInitialConstMapSize, Heap::kNew)); |
2467 script_.set_compile_time_constants(array); | 2473 script_.set_compile_time_constants(array); |
2468 } | 2474 } |
2469 KernelConstantsMap constants(script_.compile_time_constants()); | 2475 KernelConstantsMap constants(script_.compile_time_constants()); |
2470 constants.InsertNewOrGetValue(kernel_offset, value); | 2476 constants.InsertNewOrGetValue( |
| 2477 kernel_offset + builder_->relative_kernel_offset_, value); |
2471 script_.set_compile_time_constants(constants.Release()); | 2478 script_.set_compile_time_constants(constants.Release()); |
2472 } | 2479 } |
2473 | 2480 |
2474 void StreamingFlowGraphBuilder::DiscoverEnclosingElements( | 2481 void StreamingFlowGraphBuilder::DiscoverEnclosingElements( |
2475 Zone* zone, | 2482 Zone* zone, |
2476 const Function& function, | 2483 const Function& function, |
2477 Function* outermost_function) { | 2484 Function* outermost_function) { |
2478 // Find out if there is an enclosing kernel class (which will be used to | 2485 // Find out if there is an enclosing kernel class (which will be used to |
2479 // resolve type parameters). | 2486 // resolve type parameters). |
2480 *outermost_function = function.raw(); | 2487 *outermost_function = function.raw(); |
2481 while (outermost_function->parent_function() != Object::null()) { | 2488 while (outermost_function->parent_function() != Object::null()) { |
2482 *outermost_function = outermost_function->parent_function(); | 2489 *outermost_function = outermost_function->parent_function(); |
2483 } | 2490 } |
2484 } | 2491 } |
2485 | 2492 |
2486 intptr_t StreamingFlowGraphBuilder::ReadUntilFunctionNode() { | 2493 void StreamingFlowGraphBuilder::ReadUntilFunctionNode() { |
2487 const Tag tag = PeekTag(); | 2494 const Tag tag = PeekTag(); |
2488 if (tag == kProcedure) { | 2495 if (tag == kProcedure) { |
2489 ProcedureHelper procedure_helper(this); | 2496 ProcedureHelper procedure_helper(this); |
2490 procedure_helper.ReadUntilExcluding(ProcedureHelper::kFunction); | 2497 procedure_helper.ReadUntilExcluding(ProcedureHelper::kFunction); |
2491 if (ReadTag() == kNothing) { // read function node tag. | 2498 if (ReadTag() == kNothing) { // read function node tag. |
2492 // Running a procedure without a function node doesn't make sense. | 2499 // Running a procedure without a function node doesn't make sense. |
2493 UNREACHABLE(); | 2500 UNREACHABLE(); |
2494 } | 2501 } |
2495 return -1; | 2502 return; |
2496 // Now at start of FunctionNode. | 2503 // Now at start of FunctionNode. |
2497 } else if (tag == kConstructor) { | 2504 } else if (tag == kConstructor) { |
2498 ConstructorHelper constructor_helper(this); | 2505 ConstructorHelper constructor_helper(this); |
2499 constructor_helper.ReadUntilExcluding(ConstructorHelper::kFunction); | 2506 constructor_helper.ReadUntilExcluding(ConstructorHelper::kFunction); |
2500 return constructor_helper.parent_class_binary_offset_; | 2507 return; |
2501 // Now at start of FunctionNode. | 2508 // Now at start of FunctionNode. |
2502 // Notice that we also have a list of initializers after that! | 2509 // Notice that we also have a list of initializers after that! |
2503 } else if (tag == kFunctionNode) { | 2510 } else if (tag == kFunctionNode) { |
2504 // Already at start of FunctionNode. | 2511 // Already at start of FunctionNode. |
2505 } else { | 2512 } else { |
2506 UNREACHABLE(); | 2513 UNREACHABLE(); |
2507 } | 2514 } |
2508 return -1; | 2515 return; |
2509 } | 2516 } |
2510 | 2517 |
2511 StringIndex StreamingFlowGraphBuilder::GetNameFromVariableDeclaration( | 2518 StringIndex StreamingFlowGraphBuilder::GetNameFromVariableDeclaration( |
2512 intptr_t kernel_offset) { | 2519 intptr_t kernel_offset, |
| 2520 const Function& function) { |
| 2521 Function& function_or_parent = Function::Handle(Z, function.raw()); |
| 2522 intptr_t function_start_relative = |
| 2523 function_or_parent.kernel_offset() - kernel_offset; |
| 2524 while (function_start_relative > 0) { |
| 2525 function_or_parent = function_or_parent.parent_function(); |
| 2526 function_start_relative = |
| 2527 function_or_parent.kernel_offset() - kernel_offset; |
| 2528 } |
| 2529 TypedData& kernel_body = |
| 2530 TypedData::Handle(Z, function_or_parent.kernel_body()); |
| 2531 ASSERT(!kernel_body.IsNull()); |
| 2532 |
2513 // Temporarily go to the variable declaration, read the name. | 2533 // Temporarily go to the variable declaration, read the name. |
2514 AlternativeReadingScope alt(reader_, kernel_offset); | 2534 AlternativeReadingScope alt( |
| 2535 reader_, &kernel_body, |
| 2536 kernel_offset - function_or_parent.kernel_offset()); |
2515 VariableDeclarationHelper helper(this); | 2537 VariableDeclarationHelper helper(this); |
2516 helper.ReadUntilIncluding(VariableDeclarationHelper::kNameIndex); | 2538 helper.ReadUntilIncluding(VariableDeclarationHelper::kNameIndex); |
2517 return helper.name_index_; | 2539 return helper.name_index_; |
2518 } | 2540 } |
2519 | 2541 |
2520 FlowGraph* StreamingFlowGraphBuilder::BuildGraphOfStaticFieldInitializer() { | 2542 FlowGraph* StreamingFlowGraphBuilder::BuildGraphOfStaticFieldInitializer() { |
2521 FieldHelper field_helper(this); | 2543 FieldHelper field_helper(this); |
2522 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); | 2544 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); |
2523 ASSERT(field_helper.IsStatic()); | 2545 ASSERT(field_helper.IsStatic()); |
2524 | 2546 |
(...skipping 169 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2694 } | 2716 } |
2695 | 2717 |
2696 Fragment instructions; | 2718 Fragment instructions; |
2697 instructions += LoadLocal(scopes()->this_variable); | 2719 instructions += LoadLocal(scopes()->this_variable); |
2698 instructions += BuildExpression(); | 2720 instructions += BuildExpression(); |
2699 instructions += flow_graph_builder_->StoreInstanceFieldGuarded(field, true); | 2721 instructions += flow_graph_builder_->StoreInstanceFieldGuarded(field, true); |
2700 return instructions; | 2722 return instructions; |
2701 } | 2723 } |
2702 | 2724 |
2703 Fragment StreamingFlowGraphBuilder::BuildInitializers( | 2725 Fragment StreamingFlowGraphBuilder::BuildInitializers( |
2704 intptr_t constructor_class_parent_offset) { | 2726 const Class& parent_class) { |
2705 Fragment instructions; | 2727 Fragment instructions; |
2706 | 2728 |
2707 // Start by getting the position of the constructors initializer. | 2729 // Start by getting the position of the constructors initializer. |
2708 intptr_t initializers_offset = -1; | 2730 intptr_t initializers_offset = -1; |
2709 { | 2731 { |
2710 AlternativeReadingScope alt(reader_); | 2732 AlternativeReadingScope alt(reader_); |
2711 SkipFunctionNode(); // read constructors function node. | 2733 SkipFunctionNode(); // read constructors function node. |
2712 initializers_offset = ReaderOffset(); | 2734 initializers_offset = ReaderOffset(); |
2713 } | 2735 } |
2714 | 2736 |
2715 // These come from: | 2737 // These come from: |
2716 // class A { | 2738 // class A { |
2717 // var x = (expr); | 2739 // var x = (expr); |
2718 // } | 2740 // } |
2719 // We don't want to do that when this is a Redirecting Constructors though | 2741 // We don't want to do that when this is a Redirecting Constructors though |
2720 // (i.e. has a single initializer being of type kRedirectingInitializer). | 2742 // (i.e. has a single initializer being of type kRedirectingInitializer). |
2721 bool is_redirecting_constructor = false; | 2743 bool is_redirecting_constructor = false; |
2722 { | 2744 { |
2723 AlternativeReadingScope alt(reader_, initializers_offset); | 2745 AlternativeReadingScope alt(reader_, initializers_offset); |
2724 intptr_t list_length = ReadListLength(); // read initializers list length. | 2746 intptr_t list_length = ReadListLength(); // read initializers list length. |
2725 if (list_length == 1) { | 2747 if (list_length == 1) { |
2726 Tag tag = ReadTag(); | 2748 Tag tag = ReadTag(); |
2727 if (tag == kRedirectingInitializer) is_redirecting_constructor = true; | 2749 if (tag == kRedirectingInitializer) is_redirecting_constructor = true; |
2728 } | 2750 } |
2729 } | 2751 } |
2730 | 2752 |
2731 if (!is_redirecting_constructor) { | 2753 if (!is_redirecting_constructor) { |
2732 AlternativeReadingScope alt(reader_, constructor_class_parent_offset); | 2754 Array& class_fields = Array::Handle(Z, parent_class.fields()); |
2733 ClassHelper class_helper(this); | 2755 dart::Field& class_field = dart::Field::Handle(Z); |
2734 class_helper.ReadUntilExcluding(ClassHelper::kFields); | 2756 for (intptr_t i = 0; i < class_fields.Length(); ++i) { |
2735 intptr_t list_length = ReadListLength(); // read fields list length. | 2757 class_field ^= class_fields.At(i); |
2736 | 2758 if (!class_field.is_static()) { |
2737 for (intptr_t i = 0; i < list_length; ++i) { | 2759 TypedData& kernel_body = |
2738 intptr_t field_offset = ReaderOffset(); | 2760 TypedData::Handle(Z, class_field.kernel_body()); |
2739 FieldHelper field_helper(this); | 2761 ASSERT(!kernel_body.IsNull()); |
2740 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); | 2762 AlternativeReadingScope alt(reader_, &kernel_body, 0); |
2741 Tag initializer_tag = ReadTag(); // read first part of initializer. | 2763 intptr_t saved_relative_kernel_offset_ = relative_kernel_offset_; |
2742 if (!field_helper.IsStatic() && initializer_tag == kSomething) { | 2764 relative_kernel_offset_ = class_field.kernel_offset(); |
2743 EnterScope(field_offset); | 2765 FieldHelper field_helper(this); |
2744 instructions += BuildFieldInitializer( | 2766 field_helper.ReadUntilExcluding(FieldHelper::kInitializer); |
2745 field_helper.canonical_name_); // read initializer. | 2767 Tag initializer_tag = ReadTag(); // read first part of initializer. |
2746 ExitScope(field_offset); | 2768 if (initializer_tag == kSomething) { |
2747 } else if (initializer_tag == kSomething) { | 2769 EnterScope(class_field.kernel_offset()); |
2748 SkipExpression(); // read initializer. | 2770 instructions += BuildFieldInitializer( |
| 2771 field_helper.canonical_name_); // read initializer. |
| 2772 ExitScope(class_field.kernel_offset()); |
| 2773 } |
| 2774 relative_kernel_offset_ = saved_relative_kernel_offset_; |
2749 } | 2775 } |
2750 } | 2776 } |
2751 } | 2777 } |
2752 | 2778 |
2753 // These to come from: | 2779 // These to come from: |
2754 // class A { | 2780 // class A { |
2755 // var x; | 2781 // var x; |
2756 // var y; | 2782 // var y; |
2757 // A(this.x) : super(expr), y = (expr); | 2783 // A(this.x) : super(expr), y = (expr); |
2758 // } | 2784 // } |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2830 // | 2856 // |
2831 // to | 2857 // to |
2832 // | 2858 // |
2833 // class A { | 2859 // class A { |
2834 // var x; | 2860 // var x; |
2835 // A(a, b) : tmp = a + b, x = 2*b, super(tmp) {} | 2861 // A(a, b) : tmp = a + b, x = 2*b, super(tmp) {} |
2836 // } | 2862 // } |
2837 // | 2863 // |
2838 // (This is strictly speaking not what one should do in terms of the | 2864 // (This is strictly speaking not what one should do in terms of the |
2839 // specification but that is how it is currently implemented.) | 2865 // specification but that is how it is currently implemented.) |
2840 LocalVariable* variable = LookupVariable(ReaderOffset()); | 2866 LocalVariable* variable = |
| 2867 LookupVariable(ReaderOffset() + relative_kernel_offset_); |
2841 | 2868 |
2842 // Variable declaration | 2869 // Variable declaration |
2843 VariableDeclarationHelper helper(this); | 2870 VariableDeclarationHelper helper(this); |
2844 helper.ReadUntilExcluding(VariableDeclarationHelper::kInitializer); | 2871 helper.ReadUntilExcluding(VariableDeclarationHelper::kInitializer); |
2845 ASSERT(!helper.IsConst()); | 2872 ASSERT(!helper.IsConst()); |
2846 Tag tag = ReadTag(); // read (first part of) initializer. | 2873 Tag tag = ReadTag(); // read (first part of) initializer. |
2847 if (tag != kSomething) { | 2874 if (tag != kSomething) { |
2848 UNREACHABLE(); | 2875 UNREACHABLE(); |
2849 } | 2876 } |
2850 | 2877 |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2882 body += PushArgument(); | 2909 body += PushArgument(); |
2883 } | 2910 } |
2884 | 2911 |
2885 FunctionNodeHelper function_node_helper(this); | 2912 FunctionNodeHelper function_node_helper(this); |
2886 function_node_helper.ReadUntilExcluding( | 2913 function_node_helper.ReadUntilExcluding( |
2887 FunctionNodeHelper::kPositionalParameters); | 2914 FunctionNodeHelper::kPositionalParameters); |
2888 | 2915 |
2889 // Positional. | 2916 // Positional. |
2890 intptr_t positional_argument_count = ReadListLength(); | 2917 intptr_t positional_argument_count = ReadListLength(); |
2891 for (intptr_t i = 0; i < positional_argument_count; ++i) { | 2918 for (intptr_t i = 0; i < positional_argument_count; ++i) { |
2892 body += LoadLocal(LookupVariable(ReaderOffset())); // ith variable offset. | 2919 body += LoadLocal(LookupVariable( |
| 2920 ReaderOffset() + relative_kernel_offset_)); // ith variable offset. |
2893 body += PushArgument(); | 2921 body += PushArgument(); |
2894 SkipVariableDeclaration(); // read ith variable. | 2922 SkipVariableDeclaration(); // read ith variable. |
2895 } | 2923 } |
2896 | 2924 |
2897 // Named. | 2925 // Named. |
2898 intptr_t named_argument_count = ReadListLength(); | 2926 intptr_t named_argument_count = ReadListLength(); |
2899 Array& argument_names = Array::ZoneHandle(Z); | 2927 Array& argument_names = Array::ZoneHandle(Z); |
2900 if (named_argument_count > 0) { | 2928 if (named_argument_count > 0) { |
2901 argument_names = Array::New(named_argument_count); | 2929 argument_names = Array::New(named_argument_count); |
2902 for (intptr_t i = 0; i < named_argument_count; ++i) { | 2930 for (intptr_t i = 0; i < named_argument_count; ++i) { |
2903 // ith variable offset. | 2931 // ith variable offset. |
2904 body += LoadLocal(LookupVariable(ReaderOffset())); | 2932 body += |
| 2933 LoadLocal(LookupVariable(ReaderOffset() + relative_kernel_offset_)); |
2905 body += PushArgument(); | 2934 body += PushArgument(); |
2906 StringIndex name = GetNameFromVariableDeclaration(ReaderOffset()); | 2935 |
2907 argument_names.SetAt(i, H.DartSymbol(name)); | 2936 // read ith variable. |
2908 SkipVariableDeclaration(); // read ith variable. | 2937 VariableDeclarationHelper helper(this); |
| 2938 helper.ReadUntilExcluding(VariableDeclarationHelper::kEnd); |
| 2939 |
| 2940 argument_names.SetAt(i, H.DartSymbol(helper.name_index_)); |
2909 } | 2941 } |
2910 } | 2942 } |
2911 | 2943 |
2912 // Forward them to the target. | 2944 // Forward them to the target. |
2913 intptr_t argument_count = positional_argument_count + named_argument_count; | 2945 intptr_t argument_count = positional_argument_count + named_argument_count; |
2914 if (!target.is_static()) ++argument_count; | 2946 if (!target.is_static()) ++argument_count; |
2915 body += StaticCall(TokenPosition::kNoSource, target, argument_count, | 2947 body += StaticCall(TokenPosition::kNoSource, target, argument_count, |
2916 argument_names); | 2948 argument_names); |
2917 | 2949 |
2918 // Return the result. | 2950 // Return the result. |
(...skipping 27 matching lines...) Expand all Loading... |
2946 function_node_helper.ReadUntilExcluding( | 2978 function_node_helper.ReadUntilExcluding( |
2947 FunctionNodeHelper::kPositionalParameters); | 2979 FunctionNodeHelper::kPositionalParameters); |
2948 | 2980 |
2949 // Positional. | 2981 // Positional. |
2950 const intptr_t positional_argument_count = ReadListLength(); | 2982 const intptr_t positional_argument_count = ReadListLength(); |
2951 | 2983 |
2952 // The first argument is the instance of the closure class. For converted | 2984 // The first argument is the instance of the closure class. For converted |
2953 // closures its context field contains the context vector that is used by the | 2985 // closures its context field contains the context vector that is used by the |
2954 // converted top-level function (target) explicitly and that should be passed | 2986 // converted top-level function (target) explicitly and that should be passed |
2955 // to that function as the first parameter. | 2987 // to that function as the first parameter. |
2956 body += LoadLocal(LookupVariable(ReaderOffset())); // 0th variable offset. | 2988 body += LoadLocal(LookupVariable( |
| 2989 ReaderOffset() + relative_kernel_offset_)); // 0th variable offset. |
2957 body += flow_graph_builder_->LoadField(Closure::context_offset()); | 2990 body += flow_graph_builder_->LoadField(Closure::context_offset()); |
2958 body += PushArgument(); | 2991 body += PushArgument(); |
2959 SkipVariableDeclaration(); // read 0th variable. | 2992 SkipVariableDeclaration(); // read 0th variable. |
2960 | 2993 |
2961 // The rest of the parameters are the same for the method of the Closure class | 2994 // The rest of the parameters are the same for the method of the Closure class |
2962 // being invoked and the top-level function (target). | 2995 // being invoked and the top-level function (target). |
2963 for (intptr_t i = 1; i < positional_argument_count; i++) { | 2996 for (intptr_t i = 1; i < positional_argument_count; i++) { |
2964 body += LoadLocal(LookupVariable(ReaderOffset())); // ith variable offset. | 2997 body += LoadLocal(LookupVariable( |
| 2998 ReaderOffset() + relative_kernel_offset_)); // ith variable offset. |
2965 body += PushArgument(); | 2999 body += PushArgument(); |
2966 SkipVariableDeclaration(); // read ith variable. | 3000 SkipVariableDeclaration(); // read ith variable. |
2967 } | 3001 } |
2968 | 3002 |
2969 // Named. | 3003 // Named. |
2970 const intptr_t named_argument_count = ReadListLength(); | 3004 const intptr_t named_argument_count = ReadListLength(); |
2971 Array& argument_names = Array::ZoneHandle(Z); | 3005 Array& argument_names = Array::ZoneHandle(Z); |
2972 if (named_argument_count > 0) { | 3006 if (named_argument_count > 0) { |
2973 argument_names = Array::New(named_argument_count); | 3007 argument_names = Array::New(named_argument_count); |
2974 for (intptr_t i = 0; i < named_argument_count; i++) { | 3008 for (intptr_t i = 0; i < named_argument_count; i++) { |
| 3009 // ith variable offset. |
2975 body += | 3010 body += |
2976 LoadLocal(LookupVariable(ReaderOffset())); // ith variable offset. | 3011 LoadLocal(LookupVariable(ReaderOffset() + relative_kernel_offset_)); |
2977 body += PushArgument(); | 3012 body += PushArgument(); |
2978 argument_names.SetAt( | 3013 |
2979 i, H.DartSymbol(GetNameFromVariableDeclaration(ReaderOffset()))); | 3014 // read ith variable. |
2980 SkipVariableDeclaration(); // read ith variable. | 3015 VariableDeclarationHelper helper(this); |
| 3016 helper.ReadUntilExcluding(VariableDeclarationHelper::kEnd); |
| 3017 |
| 3018 argument_names.SetAt(i, H.DartSymbol(helper.name_index_)); |
2981 } | 3019 } |
2982 } | 3020 } |
2983 | 3021 |
2984 // Forward them to the target. | 3022 // Forward them to the target. |
2985 const intptr_t argument_count = | 3023 const intptr_t argument_count = |
2986 positional_argument_count + named_argument_count; | 3024 positional_argument_count + named_argument_count; |
2987 body += StaticCall(TokenPosition::kNoSource, target, argument_count, | 3025 body += StaticCall(TokenPosition::kNoSource, target, argument_count, |
2988 argument_names); | 3026 argument_names); |
2989 | 3027 |
2990 // Return the result. | 3028 // Return the result. |
2991 body += Return(function_node_helper.end_position_); | 3029 body += Return(function_node_helper.end_position_); |
2992 | 3030 |
2993 return new (Z) | 3031 return new (Z) |
2994 FlowGraph(*parsed_function(), flow_graph_builder_->graph_entry_, | 3032 FlowGraph(*parsed_function(), flow_graph_builder_->graph_entry_, |
2995 flow_graph_builder_->next_block_id_ - 1); | 3033 flow_graph_builder_->next_block_id_ - 1); |
2996 } | 3034 } |
2997 | 3035 |
2998 FlowGraph* StreamingFlowGraphBuilder::BuildGraphOfFunction( | 3036 FlowGraph* StreamingFlowGraphBuilder::BuildGraphOfFunction(bool constructor) { |
2999 intptr_t constructor_class_parent_offset) { | |
3000 const Function& dart_function = parsed_function()->function(); | 3037 const Function& dart_function = parsed_function()->function(); |
3001 TargetEntryInstr* normal_entry = flow_graph_builder_->BuildTargetEntry(); | 3038 TargetEntryInstr* normal_entry = flow_graph_builder_->BuildTargetEntry(); |
3002 flow_graph_builder_->graph_entry_ = new (Z) GraphEntryInstr( | 3039 flow_graph_builder_->graph_entry_ = new (Z) GraphEntryInstr( |
3003 *parsed_function(), normal_entry, flow_graph_builder_->osr_id_); | 3040 *parsed_function(), normal_entry, flow_graph_builder_->osr_id_); |
3004 | 3041 |
3005 SetupDefaultParameterValues(); | 3042 SetupDefaultParameterValues(); |
3006 | 3043 |
3007 Fragment body; | 3044 Fragment body; |
3008 if (!dart_function.is_native()) | 3045 if (!dart_function.is_native()) |
3009 body += flow_graph_builder_->CheckStackOverflowInPrologue(); | 3046 body += flow_graph_builder_->CheckStackOverflowInPrologue(); |
(...skipping 28 matching lines...) Expand all Loading... |
3038 body += flow_graph_builder_->StoreInstanceField( | 3075 body += flow_graph_builder_->StoreInstanceField( |
3039 TokenPosition::kNoSource, | 3076 TokenPosition::kNoSource, |
3040 Context::variable_offset(variable->index())); | 3077 Context::variable_offset(variable->index())); |
3041 body += NullConstant(); | 3078 body += NullConstant(); |
3042 body += StoreLocal(TokenPosition::kNoSource, parameter); | 3079 body += StoreLocal(TokenPosition::kNoSource, parameter); |
3043 body += Drop(); | 3080 body += Drop(); |
3044 } | 3081 } |
3045 } | 3082 } |
3046 body += Drop(); // The context. | 3083 body += Drop(); // The context. |
3047 } | 3084 } |
3048 if (constructor_class_parent_offset > 0) { | 3085 if (constructor) { |
3049 // TODO(27590): Currently the [VariableDeclaration]s from the | 3086 // TODO(27590): Currently the [VariableDeclaration]s from the |
3050 // initializers will be visible inside the entire body of the constructor. | 3087 // initializers will be visible inside the entire body of the constructor. |
3051 // We should make a separate scope for them. | 3088 // We should make a separate scope for them. |
3052 body += BuildInitializers(constructor_class_parent_offset); | 3089 body += BuildInitializers(Class::Handle(Z, dart_function.Owner())); |
3053 } | 3090 } |
3054 | 3091 |
3055 FunctionNodeHelper function_node_helper(this); | 3092 FunctionNodeHelper function_node_helper(this); |
3056 function_node_helper.ReadUntilExcluding( | 3093 function_node_helper.ReadUntilExcluding( |
3057 FunctionNodeHelper::kPositionalParameters); | 3094 FunctionNodeHelper::kPositionalParameters); |
3058 intptr_t first_parameter_offset = -1; | 3095 intptr_t first_parameter_offset = -1; |
3059 { | 3096 { |
3060 AlternativeReadingScope alt(reader_); | 3097 AlternativeReadingScope alt(reader_); |
3061 intptr_t list_length = ReadListLength(); // read number of positionals. | 3098 intptr_t list_length = ReadListLength(); // read number of positionals. |
3062 if (list_length > 0) { | 3099 if (list_length > 0) { |
3063 first_parameter_offset = ReaderOffset(); | 3100 first_parameter_offset = ReaderOffset() + relative_kernel_offset_; |
3064 } | 3101 } |
3065 } | 3102 } |
3066 // Current position: About to read list of positionals. | 3103 // Current position: About to read list of positionals. |
3067 | 3104 |
3068 // The specification defines the result of `a == b` to be: | 3105 // The specification defines the result of `a == b` to be: |
3069 // | 3106 // |
3070 // a) if either side is `null` then the result is `identical(a, b)`. | 3107 // a) if either side is `null` then the result is `identical(a, b)`. |
3071 // b) else the result is `a.operator==(b)` | 3108 // b) else the result is `a.operator==(b)` |
3072 // | 3109 // |
3073 // For user-defined implementations of `operator==` we need therefore | 3110 // For user-defined implementations of `operator==` we need therefore |
(...skipping 23 matching lines...) Expand all Loading... |
3097 body = Fragment(body.entry, non_null_entry); | 3134 body = Fragment(body.entry, non_null_entry); |
3098 } | 3135 } |
3099 | 3136 |
3100 // If we run in checked mode, we have to check the type of the passed | 3137 // If we run in checked mode, we have to check the type of the passed |
3101 // arguments. | 3138 // arguments. |
3102 if (I->type_checks()) { | 3139 if (I->type_checks()) { |
3103 // Positional. | 3140 // Positional. |
3104 intptr_t list_length = ReadListLength(); | 3141 intptr_t list_length = ReadListLength(); |
3105 for (intptr_t i = 0; i < list_length; ++i) { | 3142 for (intptr_t i = 0; i < list_length; ++i) { |
3106 // ith variable offset. | 3143 // ith variable offset. |
3107 body += LoadLocal(LookupVariable(ReaderOffset())); | 3144 body += |
3108 body += CheckVariableTypeInCheckedMode(ReaderOffset()); | 3145 LoadLocal(LookupVariable(ReaderOffset() + relative_kernel_offset_)); |
| 3146 body += CheckVariableTypeInCheckedMode(ReaderOffset() + |
| 3147 relative_kernel_offset_); |
3109 body += Drop(); | 3148 body += Drop(); |
3110 SkipVariableDeclaration(); // read ith variable. | 3149 SkipVariableDeclaration(); // read ith variable. |
3111 } | 3150 } |
3112 | 3151 |
3113 // Named. | 3152 // Named. |
3114 list_length = ReadListLength(); | 3153 list_length = ReadListLength(); |
3115 for (intptr_t i = 0; i < list_length; ++i) { | 3154 for (intptr_t i = 0; i < list_length; ++i) { |
3116 // ith variable offset. | 3155 // ith variable offset. |
3117 body += LoadLocal(LookupVariable(ReaderOffset())); | 3156 body += |
3118 body += CheckVariableTypeInCheckedMode(ReaderOffset()); | 3157 LoadLocal(LookupVariable(ReaderOffset() + relative_kernel_offset_)); |
| 3158 body += CheckVariableTypeInCheckedMode(ReaderOffset() + |
| 3159 relative_kernel_offset_); |
3119 body += Drop(); | 3160 body += Drop(); |
3120 SkipVariableDeclaration(); // read ith variable. | 3161 SkipVariableDeclaration(); // read ith variable. |
3121 } | 3162 } |
3122 | 3163 |
3123 function_node_helper.SetJustRead(FunctionNodeHelper::kNamedParameters); | 3164 function_node_helper.SetJustRead(FunctionNodeHelper::kNamedParameters); |
3124 } | 3165 } |
3125 | 3166 |
3126 function_node_helper.ReadUntilExcluding(FunctionNodeHelper::kBody); | 3167 function_node_helper.ReadUntilExcluding(FunctionNodeHelper::kBody); |
3127 | 3168 |
3128 bool has_body = ReadTag() == kSomething; // read first part of body. | 3169 bool has_body = ReadTag() == kSomething; // read first part of body. |
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3280 // become unreachable after OSR. | 3321 // become unreachable after OSR. |
3281 if (flow_graph_builder_->osr_id_ != Compiler::kNoOSRDeoptId) { | 3322 if (flow_graph_builder_->osr_id_ != Compiler::kNoOSRDeoptId) { |
3282 graph_entry->RelinkToOsrEntry(Z, flow_graph_builder_->next_block_id_); | 3323 graph_entry->RelinkToOsrEntry(Z, flow_graph_builder_->next_block_id_); |
3283 } | 3324 } |
3284 return new (Z) FlowGraph(*parsed_function(), graph_entry, | 3325 return new (Z) FlowGraph(*parsed_function(), graph_entry, |
3285 flow_graph_builder_->next_block_id_ - 1); | 3326 flow_graph_builder_->next_block_id_ - 1); |
3286 } | 3327 } |
3287 | 3328 |
3288 FlowGraph* StreamingFlowGraphBuilder::BuildGraph(intptr_t kernel_offset) { | 3329 FlowGraph* StreamingFlowGraphBuilder::BuildGraph(intptr_t kernel_offset) { |
3289 const Function& function = parsed_function()->function(); | 3330 const Function& function = parsed_function()->function(); |
| 3331 TypedData& kernel_body = TypedData::Handle(Z, function.kernel_body()); |
| 3332 if (kernel_body.IsNull() && kernel_offset > 0) { |
| 3333 UNREACHABLE(); |
| 3334 } |
3290 | 3335 |
3291 // Setup a [ActiveClassScope] and a [ActiveMemberScope] which will be used | 3336 // Setup a [ActiveClassScope] and a [ActiveMemberScope] which will be used |
3292 // e.g. for type translation. | 3337 // e.g. for type translation. |
3293 const dart::Class& klass = | 3338 const dart::Class& klass = |
3294 dart::Class::Handle(zone_, parsed_function()->function().Owner()); | 3339 dart::Class::Handle(zone_, parsed_function()->function().Owner()); |
3295 | 3340 |
3296 Function& outermost_function = Function::Handle(Z); | 3341 Function& outermost_function = Function::Handle(Z); |
3297 DiscoverEnclosingElements(Z, function, &outermost_function); | 3342 DiscoverEnclosingElements(Z, function, &outermost_function); |
3298 | 3343 |
3299 ActiveClassScope active_class_scope(active_class(), &klass); | 3344 ActiveClassScope active_class_scope(active_class(), &klass); |
(...skipping 14 matching lines...) Expand all Loading... |
3314 case RawFunction::kConvertedClosureFunction: | 3359 case RawFunction::kConvertedClosureFunction: |
3315 case RawFunction::kRegularFunction: | 3360 case RawFunction::kRegularFunction: |
3316 case RawFunction::kGetterFunction: | 3361 case RawFunction::kGetterFunction: |
3317 case RawFunction::kSetterFunction: { | 3362 case RawFunction::kSetterFunction: { |
3318 ReadUntilFunctionNode(); // read until function node. | 3363 ReadUntilFunctionNode(); // read until function node. |
3319 if (function.IsImplicitClosureFunction()) { | 3364 if (function.IsImplicitClosureFunction()) { |
3320 return BuildGraphOfImplicitClosureFunction(function); | 3365 return BuildGraphOfImplicitClosureFunction(function); |
3321 } else if (function.IsConvertedClosureFunction()) { | 3366 } else if (function.IsConvertedClosureFunction()) { |
3322 return BuildGraphOfConvertedClosureFunction(function); | 3367 return BuildGraphOfConvertedClosureFunction(function); |
3323 } | 3368 } |
3324 return BuildGraphOfFunction(); | 3369 return BuildGraphOfFunction(false); |
3325 } | 3370 } |
3326 case RawFunction::kConstructor: { | 3371 case RawFunction::kConstructor: { |
3327 bool is_factory = function.IsFactory(); | 3372 ReadUntilFunctionNode(); // read until function node. |
3328 if (is_factory) { | 3373 return BuildGraphOfFunction(!function.IsFactory()); |
3329 ReadUntilFunctionNode(); // read until function node. | |
3330 return BuildGraphOfFunction(); | |
3331 } else { | |
3332 // Constructor: Pass offset to parent class. | |
3333 return BuildGraphOfFunction( | |
3334 ReadUntilFunctionNode()); // read until function node. | |
3335 } | |
3336 } | 3374 } |
3337 case RawFunction::kImplicitGetter: | 3375 case RawFunction::kImplicitGetter: |
3338 case RawFunction::kImplicitStaticFinalGetter: | 3376 case RawFunction::kImplicitStaticFinalGetter: |
3339 case RawFunction::kImplicitSetter: { | 3377 case RawFunction::kImplicitSetter: { |
3340 return IsStaticInitializer(function, Z) | 3378 return IsStaticInitializer(function, Z) |
3341 ? BuildGraphOfStaticFieldInitializer() | 3379 ? BuildGraphOfStaticFieldInitializer() |
3342 : BuildGraphOfFieldAccessor(scopes()->setter_value); | 3380 : BuildGraphOfFieldAccessor(scopes()->setter_value); |
3343 } | 3381 } |
3344 case RawFunction::kMethodExtractor: | 3382 case RawFunction::kMethodExtractor: |
3345 return flow_graph_builder_->BuildGraphOfMethodExtractor(function); | 3383 return flow_graph_builder_->BuildGraphOfMethodExtractor(function); |
(...skipping 2294 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5640 const dart::Class& map_class = | 5678 const dart::Class& map_class = |
5641 dart::Class::Handle(Z, dart::Library::LookupCoreClass(Symbols::Map())); | 5679 dart::Class::Handle(Z, dart::Library::LookupCoreClass(Symbols::Map())); |
5642 const Function& factory_method = Function::ZoneHandle( | 5680 const Function& factory_method = Function::ZoneHandle( |
5643 Z, map_class.LookupFactory( | 5681 Z, map_class.LookupFactory( |
5644 dart::Library::PrivateCoreLibName(Symbols::MapLiteralFactory()))); | 5682 dart::Library::PrivateCoreLibName(Symbols::MapLiteralFactory()))); |
5645 | 5683 |
5646 return instructions + StaticCall(position, factory_method, 2); | 5684 return instructions + StaticCall(position, factory_method, 2); |
5647 } | 5685 } |
5648 | 5686 |
5649 Fragment StreamingFlowGraphBuilder::BuildFunctionExpression() { | 5687 Fragment StreamingFlowGraphBuilder::BuildFunctionExpression() { |
5650 intptr_t offset = ReaderOffset() - 1; // -1 to include tag byte. | 5688 return BuildFunctionNode(TokenPosition::kNoSource, StringIndex()); |
5651 return BuildFunctionNode(offset, TokenPosition::kNoSource, false, -1); | |
5652 } | 5689 } |
5653 | 5690 |
5654 Fragment StreamingFlowGraphBuilder::BuildLet(TokenPosition* position) { | 5691 Fragment StreamingFlowGraphBuilder::BuildLet(TokenPosition* position) { |
5655 if (position != NULL) *position = TokenPosition::kNoSource; | 5692 if (position != NULL) *position = TokenPosition::kNoSource; |
5656 | 5693 |
5657 Fragment instructions = BuildVariableDeclaration(); // read variable. | 5694 Fragment instructions = BuildVariableDeclaration(); // read variable. |
5658 instructions += BuildExpression(); // read body. | 5695 instructions += BuildExpression(); // read body. |
5659 return instructions; | 5696 return instructions; |
5660 } | 5697 } |
5661 | 5698 |
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5814 Fragment instructions = BuildExpression(); // read expression. | 5851 Fragment instructions = BuildExpression(); // read expression. |
5815 instructions += Drop(); | 5852 instructions += Drop(); |
5816 return instructions; | 5853 return instructions; |
5817 } | 5854 } |
5818 | 5855 |
5819 Fragment StreamingFlowGraphBuilder::BuildBlock() { | 5856 Fragment StreamingFlowGraphBuilder::BuildBlock() { |
5820 intptr_t offset = ReaderOffset() - 1; // Include the tag. | 5857 intptr_t offset = ReaderOffset() - 1; // Include the tag. |
5821 | 5858 |
5822 Fragment instructions; | 5859 Fragment instructions; |
5823 | 5860 |
5824 instructions += EnterScope(offset); | 5861 instructions += EnterScope(offset + relative_kernel_offset_); |
5825 intptr_t list_length = ReadListLength(); // read number of statements. | 5862 intptr_t list_length = ReadListLength(); // read number of statements. |
5826 for (intptr_t i = 0; i < list_length; ++i) { | 5863 for (intptr_t i = 0; i < list_length; ++i) { |
5827 if (instructions.is_open()) { | 5864 if (instructions.is_open()) { |
5828 instructions += BuildStatement(); // read ith statement. | 5865 instructions += BuildStatement(); // read ith statement. |
5829 } else { | 5866 } else { |
5830 SkipStatement(); // read ith statement. | 5867 SkipStatement(); // read ith statement. |
5831 } | 5868 } |
5832 } | 5869 } |
5833 instructions += ExitScope(offset); | 5870 instructions += ExitScope(offset + relative_kernel_offset_); |
5834 | 5871 |
5835 return instructions; | 5872 return instructions; |
5836 } | 5873 } |
5837 | 5874 |
5838 Fragment StreamingFlowGraphBuilder::BuildEmptyStatement() { | 5875 Fragment StreamingFlowGraphBuilder::BuildEmptyStatement() { |
5839 return Fragment(); | 5876 return Fragment(); |
5840 } | 5877 } |
5841 | 5878 |
5842 Fragment StreamingFlowGraphBuilder::BuildAssertStatement() { | 5879 Fragment StreamingFlowGraphBuilder::BuildAssertStatement() { |
5843 if (!I->asserts()) { | 5880 if (!I->asserts()) { |
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5996 return Fragment(new (Z) GotoInstr(join, Thread::Current()->GetNextDeoptId()), | 6033 return Fragment(new (Z) GotoInstr(join, Thread::Current()->GetNextDeoptId()), |
5997 loop_exit); | 6034 loop_exit); |
5998 } | 6035 } |
5999 | 6036 |
6000 Fragment StreamingFlowGraphBuilder::BuildForStatement() { | 6037 Fragment StreamingFlowGraphBuilder::BuildForStatement() { |
6001 intptr_t offset = ReaderOffset() - 1; // Include the tag. | 6038 intptr_t offset = ReaderOffset() - 1; // Include the tag. |
6002 | 6039 |
6003 Fragment declarations; | 6040 Fragment declarations; |
6004 | 6041 |
6005 bool new_context = false; | 6042 bool new_context = false; |
6006 declarations += EnterScope(offset, &new_context); | 6043 declarations += EnterScope(offset + relative_kernel_offset_, &new_context); |
6007 | 6044 |
6008 intptr_t list_length = ReadListLength(); // read number of variables. | 6045 intptr_t list_length = ReadListLength(); // read number of variables. |
6009 for (intptr_t i = 0; i < list_length; ++i) { | 6046 for (intptr_t i = 0; i < list_length; ++i) { |
6010 declarations += BuildVariableDeclaration(); // read ith variable. | 6047 declarations += BuildVariableDeclaration(); // read ith variable. |
6011 } | 6048 } |
6012 | 6049 |
6013 loop_depth_inc(); | 6050 loop_depth_inc(); |
6014 bool negate = false; | 6051 bool negate = false; |
6015 Tag tag = ReadTag(); // Read first part of condition. | 6052 Tag tag = ReadTag(); // Read first part of condition. |
6016 Fragment condition = | 6053 Fragment condition = |
(...skipping 29 matching lines...) Expand all Loading... |
6046 Fragment loop(join); | 6083 Fragment loop(join); |
6047 loop += CheckStackOverflow(); | 6084 loop += CheckStackOverflow(); |
6048 loop += condition; | 6085 loop += condition; |
6049 } else { | 6086 } else { |
6050 declarations += condition; | 6087 declarations += condition; |
6051 } | 6088 } |
6052 | 6089 |
6053 Fragment loop(declarations.entry, loop_exit); | 6090 Fragment loop(declarations.entry, loop_exit); |
6054 loop_depth_dec(); | 6091 loop_depth_dec(); |
6055 | 6092 |
6056 loop += ExitScope(offset); | 6093 loop += ExitScope(offset + relative_kernel_offset_); |
6057 | 6094 |
6058 return loop; | 6095 return loop; |
6059 } | 6096 } |
6060 | 6097 |
6061 Fragment StreamingFlowGraphBuilder::BuildForInStatement(bool async) { | 6098 Fragment StreamingFlowGraphBuilder::BuildForInStatement(bool async) { |
6062 intptr_t offset = ReaderOffset() - 1; // Include the tag. | 6099 intptr_t offset = ReaderOffset() - 1; // Include the tag. |
6063 | 6100 |
6064 TokenPosition position = ReadPosition(); // read position. | 6101 TokenPosition position = ReadPosition(); // read position. |
6065 intptr_t variable_kernel_position = ReaderOffset(); | 6102 intptr_t variable_kernel_position = ReaderOffset() + relative_kernel_offset_; |
6066 SkipVariableDeclaration(); // read variable. | 6103 SkipVariableDeclaration(); // read variable. |
6067 | 6104 |
6068 TokenPosition iterable_position = TokenPosition::kNoSource; | 6105 TokenPosition iterable_position = TokenPosition::kNoSource; |
6069 Fragment instructions = | 6106 Fragment instructions = |
6070 BuildExpression(&iterable_position); // read iterable. | 6107 BuildExpression(&iterable_position); // read iterable. |
6071 instructions += PushArgument(); | 6108 instructions += PushArgument(); |
6072 | 6109 |
6073 const dart::String& iterator_getter = dart::String::ZoneHandle( | 6110 const dart::String& iterator_getter = dart::String::ZoneHandle( |
6074 Z, dart::Field::GetterSymbol(Symbols::Iterator())); | 6111 Z, dart::Field::GetterSymbol(Symbols::Iterator())); |
6075 instructions += | 6112 instructions += |
6076 InstanceCall(iterable_position, iterator_getter, Token::kGET, 1); | 6113 InstanceCall(iterable_position, iterator_getter, Token::kGET, 1); |
6077 LocalVariable* iterator = scopes()->iterator_variables[for_in_depth()]; | 6114 LocalVariable* iterator = scopes()->iterator_variables[for_in_depth()]; |
6078 instructions += StoreLocal(TokenPosition::kNoSource, iterator); | 6115 instructions += StoreLocal(TokenPosition::kNoSource, iterator); |
6079 instructions += Drop(); | 6116 instructions += Drop(); |
6080 | 6117 |
6081 for_in_depth_inc(); | 6118 for_in_depth_inc(); |
6082 loop_depth_inc(); | 6119 loop_depth_inc(); |
6083 Fragment condition = LoadLocal(iterator); | 6120 Fragment condition = LoadLocal(iterator); |
6084 condition += PushArgument(); | 6121 condition += PushArgument(); |
6085 condition += | 6122 condition += |
6086 InstanceCall(iterable_position, Symbols::MoveNext(), Token::kILLEGAL, 1); | 6123 InstanceCall(iterable_position, Symbols::MoveNext(), Token::kILLEGAL, 1); |
6087 TargetEntryInstr* body_entry; | 6124 TargetEntryInstr* body_entry; |
6088 TargetEntryInstr* loop_exit; | 6125 TargetEntryInstr* loop_exit; |
6089 condition += BranchIfTrue(&body_entry, &loop_exit, false); | 6126 condition += BranchIfTrue(&body_entry, &loop_exit, false); |
6090 | 6127 |
6091 Fragment body(body_entry); | 6128 Fragment body(body_entry); |
6092 body += EnterScope(offset); | 6129 body += EnterScope(offset + relative_kernel_offset_); |
6093 body += LoadLocal(iterator); | 6130 body += LoadLocal(iterator); |
6094 body += PushArgument(); | 6131 body += PushArgument(); |
6095 const dart::String& current_getter = dart::String::ZoneHandle( | 6132 const dart::String& current_getter = dart::String::ZoneHandle( |
6096 Z, dart::Field::GetterSymbol(Symbols::Current())); | 6133 Z, dart::Field::GetterSymbol(Symbols::Current())); |
6097 body += InstanceCall(position, current_getter, Token::kGET, 1); | 6134 body += InstanceCall(position, current_getter, Token::kGET, 1); |
6098 body += StoreLocal(TokenPosition::kNoSource, | 6135 body += StoreLocal(TokenPosition::kNoSource, |
6099 LookupVariable(variable_kernel_position)); | 6136 LookupVariable(variable_kernel_position)); |
6100 body += Drop(); | 6137 body += Drop(); |
6101 body += BuildStatement(); // read body. | 6138 body += BuildStatement(); // read body. |
6102 body += ExitScope(offset); | 6139 body += ExitScope(offset + relative_kernel_offset_); |
6103 | 6140 |
6104 if (body.is_open()) { | 6141 if (body.is_open()) { |
6105 JoinEntryInstr* join = BuildJoinEntry(); | 6142 JoinEntryInstr* join = BuildJoinEntry(); |
6106 instructions += Goto(join); | 6143 instructions += Goto(join); |
6107 body += Goto(join); | 6144 body += Goto(join); |
6108 | 6145 |
6109 Fragment loop(join); | 6146 Fragment loop(join); |
6110 loop += CheckStackOverflow(); | 6147 loop += CheckStackOverflow(); |
6111 loop += condition; | 6148 loop += condition; |
6112 } else { | 6149 } else { |
(...skipping 320 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6433 Tag tag = PeekTag(); // peek guard type. | 6470 Tag tag = PeekTag(); // peek guard type. |
6434 AbstractType* type_guard = NULL; | 6471 AbstractType* type_guard = NULL; |
6435 if (tag != kDynamicType) { | 6472 if (tag != kDynamicType) { |
6436 type_guard = &T.BuildType(); // read guard. | 6473 type_guard = &T.BuildType(); // read guard. |
6437 handler_types.SetAt(i, *type_guard); | 6474 handler_types.SetAt(i, *type_guard); |
6438 } else { | 6475 } else { |
6439 SkipDartType(); // read guard. | 6476 SkipDartType(); // read guard. |
6440 handler_types.SetAt(i, Object::dynamic_type()); | 6477 handler_types.SetAt(i, Object::dynamic_type()); |
6441 } | 6478 } |
6442 | 6479 |
6443 Fragment catch_handler_body = EnterScope(catch_offset); | 6480 Fragment catch_handler_body = |
| 6481 EnterScope(catch_offset + relative_kernel_offset_); |
6444 | 6482 |
6445 tag = ReadTag(); // read first part of exception. | 6483 tag = ReadTag(); // read first part of exception. |
6446 if (tag == kSomething) { | 6484 if (tag == kSomething) { |
6447 catch_handler_body += LoadLocal(CurrentException()); | 6485 catch_handler_body += LoadLocal(CurrentException()); |
6448 catch_handler_body += | 6486 catch_handler_body += |
6449 StoreLocal(TokenPosition::kNoSource, LookupVariable(ReaderOffset())); | 6487 StoreLocal(TokenPosition::kNoSource, |
| 6488 LookupVariable(ReaderOffset() + relative_kernel_offset_)); |
6450 catch_handler_body += Drop(); | 6489 catch_handler_body += Drop(); |
6451 SkipVariableDeclaration(); // read exception. | 6490 SkipVariableDeclaration(); // read exception. |
6452 } | 6491 } |
6453 | 6492 |
6454 tag = ReadTag(); // read first part of stack trace. | 6493 tag = ReadTag(); // read first part of stack trace. |
6455 if (tag == kSomething) { | 6494 if (tag == kSomething) { |
6456 catch_handler_body += LoadLocal(CurrentStackTrace()); | 6495 catch_handler_body += LoadLocal(CurrentStackTrace()); |
6457 catch_handler_body += | 6496 catch_handler_body += |
6458 StoreLocal(TokenPosition::kNoSource, LookupVariable(ReaderOffset())); | 6497 StoreLocal(TokenPosition::kNoSource, |
| 6498 LookupVariable(ReaderOffset() + relative_kernel_offset_)); |
6459 catch_handler_body += Drop(); | 6499 catch_handler_body += Drop(); |
6460 SkipVariableDeclaration(); // read stack trace. | 6500 SkipVariableDeclaration(); // read stack trace. |
6461 } | 6501 } |
6462 | 6502 |
6463 { | 6503 { |
6464 CatchBlock block(flow_graph_builder_, CurrentException(), | 6504 CatchBlock block(flow_graph_builder_, CurrentException(), |
6465 CurrentStackTrace(), try_handler_index); | 6505 CurrentStackTrace(), try_handler_index); |
6466 | 6506 |
6467 catch_handler_body += BuildStatement(); // read body. | 6507 catch_handler_body += BuildStatement(); // read body. |
6468 | 6508 |
6469 // Note: ExitScope adjusts context_depth_ so even if catch_handler_body | 6509 // Note: ExitScope adjusts context_depth_ so even if catch_handler_body |
6470 // is closed we still need to execute ExitScope for its side effect. | 6510 // is closed we still need to execute ExitScope for its side effect. |
6471 catch_handler_body += ExitScope(catch_offset); | 6511 catch_handler_body += ExitScope(catch_offset + relative_kernel_offset_); |
6472 if (catch_handler_body.is_open()) { | 6512 if (catch_handler_body.is_open()) { |
6473 catch_handler_body += Goto(after_try); | 6513 catch_handler_body += Goto(after_try); |
6474 } | 6514 } |
6475 } | 6515 } |
6476 | 6516 |
6477 if (type_guard != NULL) { | 6517 if (type_guard != NULL) { |
6478 if (type_guard->IsMalformed()) { | 6518 if (type_guard->IsMalformed()) { |
6479 catch_body += ThrowTypeError(); | 6519 catch_body += ThrowTypeError(); |
6480 catch_body += Drop(); | 6520 catch_body += Drop(); |
6481 } else { | 6521 } else { |
(...skipping 203 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6685 rethrow += RethrowException(position, CatchClauseNode::kInvalidTryIndex); | 6725 rethrow += RethrowException(position, CatchClauseNode::kInvalidTryIndex); |
6686 Drop(); | 6726 Drop(); |
6687 | 6727 |
6688 continuation = Fragment(continuation.entry, no_error); | 6728 continuation = Fragment(continuation.entry, no_error); |
6689 } | 6729 } |
6690 | 6730 |
6691 return continuation; | 6731 return continuation; |
6692 } | 6732 } |
6693 | 6733 |
6694 Fragment StreamingFlowGraphBuilder::BuildVariableDeclaration() { | 6734 Fragment StreamingFlowGraphBuilder::BuildVariableDeclaration() { |
6695 intptr_t kernel_position_no_tag = ReaderOffset(); | 6735 intptr_t kernel_position_no_tag = ReaderOffset() + relative_kernel_offset_; |
6696 LocalVariable* variable = LookupVariable(kernel_position_no_tag); | 6736 LocalVariable* variable = LookupVariable(kernel_position_no_tag); |
6697 | 6737 |
6698 VariableDeclarationHelper helper(this); | 6738 VariableDeclarationHelper helper(this); |
6699 helper.ReadUntilExcluding(VariableDeclarationHelper::kType); | 6739 helper.ReadUntilExcluding(VariableDeclarationHelper::kType); |
6700 dart::String& name = H.DartSymbol(helper.name_index_); | 6740 dart::String& name = H.DartSymbol(helper.name_index_); |
6701 AbstractType& type = T.BuildType(); // read type. | 6741 AbstractType& type = T.BuildType(); // read type. |
6702 Tag tag = ReadTag(); // read (first part of) initializer. | 6742 Tag tag = ReadTag(); // read (first part of) initializer. |
6703 | 6743 |
6704 Fragment instructions; | 6744 Fragment instructions; |
6705 if (tag == kNothing) { | 6745 if (tag == kNothing) { |
(...skipping 18 matching lines...) Expand all Loading... |
6724 Utils::Maximum(helper.position_, helper.equals_position_); | 6764 Utils::Maximum(helper.position_, helper.equals_position_); |
6725 if (NeedsDebugStepCheck(stack(), debug_position)) { | 6765 if (NeedsDebugStepCheck(stack(), debug_position)) { |
6726 instructions = DebugStepCheck(debug_position) + instructions; | 6766 instructions = DebugStepCheck(debug_position) + instructions; |
6727 } | 6767 } |
6728 instructions += StoreLocal(helper.position_, variable); | 6768 instructions += StoreLocal(helper.position_, variable); |
6729 instructions += Drop(); | 6769 instructions += Drop(); |
6730 return instructions; | 6770 return instructions; |
6731 } | 6771 } |
6732 | 6772 |
6733 Fragment StreamingFlowGraphBuilder::BuildFunctionDeclaration() { | 6773 Fragment StreamingFlowGraphBuilder::BuildFunctionDeclaration() { |
6734 intptr_t offset = ReaderOffset() - 1; // -1 to include tag byte. | |
6735 TokenPosition position = ReadPosition(); // read position. | 6774 TokenPosition position = ReadPosition(); // read position. |
6736 intptr_t variable_offeset = ReaderOffset(); | 6775 intptr_t variable_offset = ReaderOffset() + relative_kernel_offset_; |
6737 SkipVariableDeclaration(); // read variable declaration. | 6776 |
| 6777 // read variable declaration. |
| 6778 VariableDeclarationHelper helper(this); |
| 6779 helper.ReadUntilExcluding(VariableDeclarationHelper::kEnd); |
6738 | 6780 |
6739 Fragment instructions = DebugStepCheck(position); | 6781 Fragment instructions = DebugStepCheck(position); |
6740 instructions += BuildFunctionNode(offset, position, true, variable_offeset); | 6782 instructions += BuildFunctionNode(position, helper.name_index_); |
6741 instructions += StoreLocal(position, LookupVariable(variable_offeset)); | 6783 instructions += StoreLocal(position, LookupVariable(variable_offset)); |
6742 instructions += Drop(); | 6784 instructions += Drop(); |
6743 return instructions; | 6785 return instructions; |
6744 } | 6786 } |
6745 | 6787 |
6746 Fragment StreamingFlowGraphBuilder::BuildFunctionNode( | 6788 Fragment StreamingFlowGraphBuilder::BuildFunctionNode( |
6747 intptr_t parent_kernel_offset, | |
6748 TokenPosition parent_position, | 6789 TokenPosition parent_position, |
6749 bool declaration, | 6790 StringIndex name_index) { |
6750 intptr_t variable_offeset) { | 6791 intptr_t offset = ReaderOffset() + relative_kernel_offset_; |
6751 intptr_t offset = ReaderOffset(); | |
6752 | 6792 |
6753 FunctionNodeHelper function_node_helper(this); | 6793 FunctionNodeHelper function_node_helper(this); |
6754 function_node_helper.ReadUntilExcluding( | 6794 function_node_helper.ReadUntilExcluding( |
6755 FunctionNodeHelper::kTotalParameterCount); | 6795 FunctionNodeHelper::kTotalParameterCount); |
6756 TokenPosition position = function_node_helper.position_; | 6796 TokenPosition position = function_node_helper.position_; |
6757 | 6797 |
| 6798 bool declaration = name_index >= 0; |
| 6799 |
6758 if (declaration) { | 6800 if (declaration) { |
6759 position = parent_position; | 6801 position = parent_position; |
6760 } | 6802 } |
6761 if (!position.IsReal()) { | 6803 if (!position.IsReal()) { |
6762 // Positions has to be unique in regards to the parent. | 6804 // Positions has to be unique in regards to the parent. |
6763 // A non-real at this point is probably -1, we cannot blindly use that | 6805 // A non-real at this point is probably -1, we cannot blindly use that |
6764 // as others might use it too. Create a new dummy non-real TokenPosition. | 6806 // as others might use it too. Create a new dummy non-real TokenPosition. |
6765 position = TokenPosition(offset).ToSynthetic(); | 6807 position = TokenPosition(offset).ToSynthetic(); |
6766 } | 6808 } |
6767 | 6809 |
6768 // The VM has a per-isolate table of functions indexed by the enclosing | 6810 // The VM has a per-isolate table of functions indexed by the enclosing |
6769 // function and token position. | 6811 // function and token position. |
6770 Function& function = Function::ZoneHandle(Z); | 6812 Function& function = Function::ZoneHandle(Z); |
6771 | 6813 |
6772 // NOTE: This is not TokenPosition in the general sense! | 6814 // NOTE: This is not TokenPosition in the general sense! |
6773 function = I->LookupClosureFunction(parsed_function()->function(), position); | 6815 function = I->LookupClosureFunction(parsed_function()->function(), position); |
6774 if (function.IsNull()) { | 6816 if (function.IsNull()) { |
6775 for (intptr_t i = 0; i < scopes()->function_scopes.length(); ++i) { | 6817 for (intptr_t i = 0; i < scopes()->function_scopes.length(); ++i) { |
6776 if (scopes()->function_scopes[i].kernel_offset != offset) { | 6818 if (scopes()->function_scopes[i].kernel_offset != offset) { |
6777 continue; | 6819 continue; |
6778 } | 6820 } |
6779 | 6821 |
6780 const dart::String* name; | 6822 const dart::String* name; |
6781 if (!declaration) { | 6823 if (declaration) { |
| 6824 name = &H.DartSymbol(name_index); |
| 6825 } else { |
6782 name = &Symbols::AnonymousClosure(); | 6826 name = &Symbols::AnonymousClosure(); |
6783 } else { | |
6784 name = &H.DartSymbol(GetNameFromVariableDeclaration(variable_offeset)); | |
6785 } | 6827 } |
6786 // NOTE: This is not TokenPosition in the general sense! | 6828 // NOTE: This is not TokenPosition in the general sense! |
6787 function = Function::NewClosureFunction( | 6829 function = Function::NewClosureFunction( |
6788 *name, parsed_function()->function(), position); | 6830 *name, parsed_function()->function(), position); |
6789 | 6831 |
6790 function.set_is_debuggable(function_node_helper.dart_async_marker_ == | 6832 function.set_is_debuggable(function_node_helper.dart_async_marker_ == |
6791 FunctionNode::kSync); | 6833 FunctionNode::kSync); |
6792 switch (function_node_helper.dart_async_marker_) { | 6834 switch (function_node_helper.dart_async_marker_) { |
6793 case FunctionNode::kSyncStar: | 6835 case FunctionNode::kSyncStar: |
6794 function.set_modifier(RawFunction::kSyncGen); | 6836 function.set_modifier(RawFunction::kSyncGen); |
(...skipping 19 matching lines...) Expand all Loading... |
6814 function.set_end_token_pos(function_node_helper.end_position_); | 6856 function.set_end_token_pos(function_node_helper.end_position_); |
6815 LocalScope* scope = scopes()->function_scopes[i].scope; | 6857 LocalScope* scope = scopes()->function_scopes[i].scope; |
6816 const ContextScope& context_scope = ContextScope::Handle( | 6858 const ContextScope& context_scope = ContextScope::Handle( |
6817 Z, scope->PreserveOuterScope(flow_graph_builder_->context_depth_)); | 6859 Z, scope->PreserveOuterScope(flow_graph_builder_->context_depth_)); |
6818 function.set_context_scope(context_scope); | 6860 function.set_context_scope(context_scope); |
6819 function.set_kernel_offset(offset); | 6861 function.set_kernel_offset(offset); |
6820 SetupFunctionParameters(dart::Class::Handle(Z), function, | 6862 SetupFunctionParameters(dart::Class::Handle(Z), function, |
6821 false, // is_method | 6863 false, // is_method |
6822 true, // is_closure | 6864 true, // is_closure |
6823 &function_node_helper); | 6865 &function_node_helper); |
| 6866 function_node_helper.ReadUntilExcluding(FunctionNodeHelper::kEnd); |
| 6867 TypedData& body_data = reader_->CopyDataToVMHeap( |
| 6868 Z, offset - relative_kernel_offset_, ReaderOffset()); |
| 6869 function.set_kernel_body(body_data); |
6824 | 6870 |
6825 // Finalize function type. | 6871 // Finalize function type. |
6826 Type& signature_type = Type::Handle(Z, function.SignatureType()); | 6872 Type& signature_type = Type::Handle(Z, function.SignatureType()); |
6827 signature_type ^= | 6873 signature_type ^= |
6828 ClassFinalizer::FinalizeType(*active_class()->klass, signature_type); | 6874 ClassFinalizer::FinalizeType(*active_class()->klass, signature_type); |
6829 function.SetSignatureType(signature_type); | 6875 function.SetSignatureType(signature_type); |
6830 | 6876 |
6831 I->AddClosureFunction(function); | 6877 I->AddClosureFunction(function); |
6832 break; | 6878 break; |
6833 } | 6879 } |
(...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7039 Instance& value = constant_evaluator_.EvaluateExpression(ReaderOffset()); | 7085 Instance& value = constant_evaluator_.EvaluateExpression(ReaderOffset()); |
7040 SkipExpression(); // read (actual) initializer. | 7086 SkipExpression(); // read (actual) initializer. |
7041 metadata_values.SetAt(i, value); | 7087 metadata_values.SetAt(i, value); |
7042 } | 7088 } |
7043 | 7089 |
7044 return metadata_values.raw(); | 7090 return metadata_values.raw(); |
7045 } | 7091 } |
7046 | 7092 |
7047 void StreamingFlowGraphBuilder::CollectTokenPositionsFor( | 7093 void StreamingFlowGraphBuilder::CollectTokenPositionsFor( |
7048 intptr_t script_index, | 7094 intptr_t script_index, |
| 7095 intptr_t initial_script_index, |
7049 GrowableArray<intptr_t>* record_token_positions_in, | 7096 GrowableArray<intptr_t>* record_token_positions_in, |
7050 GrowableArray<intptr_t>* record_yield_positions_in) { | 7097 GrowableArray<intptr_t>* record_yield_positions_in) { |
7051 record_token_positions_into_ = record_token_positions_in; | 7098 record_token_positions_into_ = record_token_positions_in; |
7052 record_yield_positions_into_ = record_yield_positions_in; | 7099 record_yield_positions_into_ = record_yield_positions_in; |
7053 record_for_script_id_ = script_index; | 7100 record_for_script_id_ = script_index; |
| 7101 current_script_id_ = initial_script_index; |
7054 | 7102 |
7055 // Get offset for 1st library. | 7103 const Tag tag = PeekTag(); |
7056 SetOffset(reader_->size() - 4); | 7104 if (tag == kProcedure) { |
7057 intptr_t library_count = reader_->ReadUInt32(); | 7105 ProcedureHelper procedure_helper(this); |
7058 | 7106 procedure_helper.ReadUntilExcluding(ProcedureHelper::kEnd); |
7059 SetOffset(reader_->size() - 4 - 4 * library_count); | 7107 } else if (tag == kConstructor) { |
7060 intptr_t offset = reader_->ReadUInt32(); | 7108 ConstructorHelper constructor_helper(this); |
7061 | 7109 constructor_helper.ReadUntilExcluding(ConstructorHelper::kEnd); |
7062 SetOffset(offset); | 7110 } else if (tag == kFunctionNode) { |
7063 for (intptr_t i = 0; i < library_count; ++i) { | 7111 FunctionNodeHelper function_node_helper(this); |
7064 LibraryHelper library_helper(this); | 7112 function_node_helper.ReadUntilExcluding(FunctionNodeHelper::kEnd); |
7065 library_helper.ReadUntilExcluding(LibraryHelper::kEnd); | 7113 } else if (tag == kField) { |
| 7114 FieldHelper field_helper(this); |
| 7115 field_helper.ReadUntilExcluding(FieldHelper::kEnd); |
| 7116 } else { |
| 7117 UNREACHABLE(); |
7066 } | 7118 } |
7067 | 7119 |
7068 record_token_positions_into_ = NULL; | 7120 record_token_positions_into_ = NULL; |
7069 record_yield_positions_into_ = NULL; | 7121 record_yield_positions_into_ = NULL; |
7070 record_for_script_id_ = -1; | 7122 record_for_script_id_ = -1; |
7071 } | 7123 } |
7072 | 7124 |
7073 intptr_t StreamingFlowGraphBuilder::SourceTableSize() { | 7125 intptr_t StreamingFlowGraphBuilder::SourceTableSize() { |
7074 AlternativeReadingScope alt(reader_); | 7126 AlternativeReadingScope alt(reader_); |
7075 SetOffset(reader_->size() - 4); | 7127 SetOffset(reader_->size() - 4); |
(...skipping 14 matching lines...) Expand all Loading... |
7090 intptr_t end = -1; | 7142 intptr_t end = -1; |
7091 for (intptr_t i = 0; i < size; ++i) { | 7143 for (intptr_t i = 0; i < size; ++i) { |
7092 intptr_t offset = ReadUInt(); | 7144 intptr_t offset = ReadUInt(); |
7093 if (i == index - 1) { | 7145 if (i == index - 1) { |
7094 start = offset; | 7146 start = offset; |
7095 } else if (i == index) { | 7147 } else if (i == index) { |
7096 end = offset; | 7148 end = offset; |
7097 } | 7149 } |
7098 } | 7150 } |
7099 intptr_t end_offset = ReaderOffset(); | 7151 intptr_t end_offset = ReaderOffset(); |
7100 return H.DartString(reader_->buffer() + end_offset + start, end - start, | 7152 return H.DartString( |
7101 Heap::kOld); | 7153 reader_->CopyDataIntoZone(Z, end_offset + start, end - start), |
| 7154 end - start, Heap::kOld); |
7102 } | 7155 } |
7103 | 7156 |
7104 String& StreamingFlowGraphBuilder::GetSourceFor(intptr_t index) { | 7157 String& StreamingFlowGraphBuilder::GetSourceFor(intptr_t index) { |
7105 AlternativeReadingScope alt(reader_); | 7158 AlternativeReadingScope alt(reader_); |
7106 SetOffset(reader_->size() - 4); | 7159 SetOffset(reader_->size() - 4); |
7107 intptr_t library_count = reader_->ReadUInt32(); | 7160 intptr_t library_count = reader_->ReadUInt32(); |
7108 SetOffset(reader_->size() - 4 - 4 * library_count - 3 * 4); | 7161 SetOffset(reader_->size() - 4 - 4 * library_count - 3 * 4); |
7109 SetOffset(reader_->ReadUInt32()); // read source table offset. | 7162 SetOffset(reader_->ReadUInt32()); // read source table offset. |
7110 intptr_t size = ReadUInt(); // read source table size. | 7163 intptr_t size = ReadUInt(); // read source table size. |
7111 intptr_t uris_size = 0; | 7164 intptr_t uris_size = 0; |
7112 for (intptr_t i = 0; i < size; ++i) { | 7165 for (intptr_t i = 0; i < size; ++i) { |
7113 uris_size = ReadUInt(); | 7166 uris_size = ReadUInt(); |
7114 } | 7167 } |
7115 SkipBytes(uris_size); | 7168 SkipBytes(uris_size); |
7116 | 7169 |
7117 // Read the source code strings and line starts. | 7170 // Read the source code strings and line starts. |
7118 for (intptr_t i = 0; i < size; ++i) { | 7171 for (intptr_t i = 0; i < size; ++i) { |
7119 intptr_t length = ReadUInt(); | 7172 intptr_t length = ReadUInt(); |
7120 if (index == i) { | 7173 if (index == i) { |
7121 return H.DartString(reader_->buffer() + ReaderOffset(), length, | 7174 return H.DartString(reader_->CopyDataIntoZone(Z, ReaderOffset(), length), |
7122 Heap::kOld); | 7175 length, Heap::kOld); |
7123 } | 7176 } |
7124 SkipBytes(length); | 7177 SkipBytes(length); |
7125 intptr_t line_count = ReadUInt(); | 7178 intptr_t line_count = ReadUInt(); |
7126 for (intptr_t j = 0; j < line_count; ++j) { | 7179 for (intptr_t j = 0; j < line_count; ++j) { |
7127 ReadUInt(); | 7180 ReadUInt(); |
7128 } | 7181 } |
7129 } | 7182 } |
7130 | 7183 |
7131 return String::Handle(String::null()); | 7184 return String::Handle(String::null()); |
7132 } | 7185 } |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
7168 } | 7221 } |
7169 } | 7222 } |
7170 | 7223 |
7171 return Array::Handle(Array::null()); | 7224 return Array::Handle(Array::null()); |
7172 } | 7225 } |
7173 | 7226 |
7174 } // namespace kernel | 7227 } // namespace kernel |
7175 } // namespace dart | 7228 } // namespace dart |
7176 | 7229 |
7177 #endif // !defined(DART_PRECOMPILED_RUNTIME) | 7230 #endif // !defined(DART_PRECOMPILED_RUNTIME) |
OLD | NEW |