| OLD | NEW |
| 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include <map> | 5 #include <map> |
| 6 #include <set> | 6 #include <set> |
| 7 #include <string> | 7 #include <string> |
| 8 | 8 |
| 9 #include "vm/kernel_to_il.h" | 9 #include "vm/kernel_to_il.h" |
| 10 | 10 |
| (...skipping 2350 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2361 Fragment FlowGraphBuilder::StoreInstanceField(const dart::Field& field) { | 2361 Fragment FlowGraphBuilder::StoreInstanceField(const dart::Field& field) { |
| 2362 Value* value = Pop(); | 2362 Value* value = Pop(); |
| 2363 // TODO(27590): Omit store barrier when possible (e.g., storing | 2363 // TODO(27590): Omit store barrier when possible (e.g., storing |
| 2364 // some constants). | 2364 // some constants). |
| 2365 StoreInstanceFieldInstr* store = new (Z) StoreInstanceFieldInstr( | 2365 StoreInstanceFieldInstr* store = new (Z) StoreInstanceFieldInstr( |
| 2366 field, Pop(), value, kEmitStoreBarrier, TokenPosition::kNoSource); | 2366 field, Pop(), value, kEmitStoreBarrier, TokenPosition::kNoSource); |
| 2367 return Fragment(store); | 2367 return Fragment(store); |
| 2368 } | 2368 } |
| 2369 | 2369 |
| 2370 | 2370 |
| 2371 Fragment FlowGraphBuilder::StoreInstanceFieldGuarded(const dart::Field& field) { |
| 2372 Fragment instructions; |
| 2373 if (FLAG_use_field_guards) { |
| 2374 LocalVariable* store_expression = MakeTemporary(); |
| 2375 instructions += LoadLocal(store_expression); |
| 2376 instructions += GuardFieldClass(field, Thread::Current()->GetNextDeoptId()); |
| 2377 instructions += LoadLocal(store_expression); |
| 2378 instructions += |
| 2379 GuardFieldLength(field, Thread::Current()->GetNextDeoptId()); |
| 2380 } |
| 2381 instructions += StoreInstanceField(field); |
| 2382 return instructions; |
| 2383 } |
| 2384 |
| 2385 |
| 2371 Fragment FlowGraphBuilder::StoreInstanceField(intptr_t offset) { | 2386 Fragment FlowGraphBuilder::StoreInstanceField(intptr_t offset) { |
| 2372 Value* value = Pop(); | 2387 Value* value = Pop(); |
| 2373 StoreInstanceFieldInstr* store = new (Z) StoreInstanceFieldInstr( | 2388 StoreInstanceFieldInstr* store = new (Z) StoreInstanceFieldInstr( |
| 2374 offset, Pop(), value, kEmitStoreBarrier, TokenPosition::kNoSource); | 2389 offset, Pop(), value, kEmitStoreBarrier, TokenPosition::kNoSource); |
| 2375 return Fragment(store); | 2390 return Fragment(store); |
| 2376 } | 2391 } |
| 2377 | 2392 |
| 2378 | 2393 |
| 2379 Fragment FlowGraphBuilder::StoreLocal(LocalVariable* variable) { | 2394 Fragment FlowGraphBuilder::StoreLocal(LocalVariable* variable) { |
| 2380 Fragment instructions; | 2395 Fragment instructions; |
| (...skipping 711 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3092 | 3107 |
| 3093 bool is_setter = function.IsImplicitSetterFunction(); | 3108 bool is_setter = function.IsImplicitSetterFunction(); |
| 3094 bool is_method = !function.IsStaticFunction(); | 3109 bool is_method = !function.IsStaticFunction(); |
| 3095 dart::Field& field = | 3110 dart::Field& field = |
| 3096 dart::Field::ZoneHandle(Z, H.LookupFieldByKernelField(kernel_field)); | 3111 dart::Field::ZoneHandle(Z, H.LookupFieldByKernelField(kernel_field)); |
| 3097 | 3112 |
| 3098 TargetEntryInstr* normal_entry = BuildTargetEntry(); | 3113 TargetEntryInstr* normal_entry = BuildTargetEntry(); |
| 3099 graph_entry_ = new (Z) | 3114 graph_entry_ = new (Z) |
| 3100 GraphEntryInstr(*parsed_function_, normal_entry, Compiler::kNoOSRDeoptId); | 3115 GraphEntryInstr(*parsed_function_, normal_entry, Compiler::kNoOSRDeoptId); |
| 3101 | 3116 |
| 3102 // TODO(27590): Add support for FLAG_use_field_guards. | |
| 3103 Fragment body(normal_entry); | 3117 Fragment body(normal_entry); |
| 3104 if (is_setter) { | 3118 if (is_setter) { |
| 3105 if (is_method) { | 3119 if (is_method) { |
| 3106 body += LoadLocal(scopes_->this_variable); | 3120 body += LoadLocal(scopes_->this_variable); |
| 3107 body += LoadLocal(setter_value); | 3121 body += LoadLocal(setter_value); |
| 3108 body += StoreInstanceField(field); | 3122 body += StoreInstanceFieldGuarded(field); |
| 3109 } else { | 3123 } else { |
| 3110 body += LoadLocal(setter_value); | 3124 body += LoadLocal(setter_value); |
| 3111 body += StoreStaticField(field); | 3125 body += StoreStaticField(field); |
| 3112 } | 3126 } |
| 3113 body += NullConstant(); | 3127 body += NullConstant(); |
| 3114 } else if (is_method) { | 3128 } else if (is_method) { |
| 3115 body += LoadLocal(scopes_->this_variable); | 3129 body += LoadLocal(scopes_->this_variable); |
| 3116 body += LoadField(field); | 3130 body += LoadField(field); |
| 3117 } else if (field.is_const()) { | 3131 } else if (field.is_const()) { |
| 3118 // If the parser needs to know the value of an uninitialized constant field | 3132 // If the parser needs to know the value of an uninitialized constant field |
| (...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3186 // The context is on top of the operand stack. Store `this`. The context | 3200 // The context is on top of the operand stack. Store `this`. The context |
| 3187 // doesn't need a parent pointer because it doesn't close over anything | 3201 // doesn't need a parent pointer because it doesn't close over anything |
| 3188 // else. | 3202 // else. |
| 3189 fragment += LoadLocal(scopes_->this_variable); | 3203 fragment += LoadLocal(scopes_->this_variable); |
| 3190 fragment += StoreInstanceField(Context::variable_offset(0)); | 3204 fragment += StoreInstanceField(Context::variable_offset(0)); |
| 3191 | 3205 |
| 3192 return fragment; | 3206 return fragment; |
| 3193 } | 3207 } |
| 3194 | 3208 |
| 3195 | 3209 |
| 3210 Fragment FlowGraphBuilder::GuardFieldLength(const dart::Field& field, |
| 3211 intptr_t deopt_id) { |
| 3212 return Fragment(new (Z) GuardFieldLengthInstr(Pop(), field, deopt_id)); |
| 3213 } |
| 3214 |
| 3215 |
| 3216 Fragment FlowGraphBuilder::GuardFieldClass(const dart::Field& field, |
| 3217 intptr_t deopt_id) { |
| 3218 return Fragment(new (Z) GuardFieldClassInstr(Pop(), field, deopt_id)); |
| 3219 } |
| 3220 |
| 3221 |
| 3196 FlowGraph* FlowGraphBuilder::BuildGraphOfMethodExtractor( | 3222 FlowGraph* FlowGraphBuilder::BuildGraphOfMethodExtractor( |
| 3197 const Function& method) { | 3223 const Function& method) { |
| 3198 // A method extractor is the implicit getter for a method. | 3224 // A method extractor is the implicit getter for a method. |
| 3199 const Function& function = | 3225 const Function& function = |
| 3200 Function::ZoneHandle(Z, method.extracted_method_closure()); | 3226 Function::ZoneHandle(Z, method.extracted_method_closure()); |
| 3201 | 3227 |
| 3202 TargetEntryInstr* normal_entry = BuildTargetEntry(); | 3228 TargetEntryInstr* normal_entry = BuildTargetEntry(); |
| 3203 graph_entry_ = new (Z) | 3229 graph_entry_ = new (Z) |
| 3204 GraphEntryInstr(*parsed_function_, normal_entry, Compiler::kNoOSRDeoptId); | 3230 GraphEntryInstr(*parsed_function_, normal_entry, Compiler::kNoOSRDeoptId); |
| 3205 Fragment body(normal_entry); | 3231 Fragment body(normal_entry); |
| (...skipping 302 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3508 // var x = (expr); | 3534 // var x = (expr); |
| 3509 // } | 3535 // } |
| 3510 for (intptr_t i = 0; i < kernel_klass->fields().length(); i++) { | 3536 for (intptr_t i = 0; i < kernel_klass->fields().length(); i++) { |
| 3511 Field* kernel_field = kernel_klass->fields()[i]; | 3537 Field* kernel_field = kernel_klass->fields()[i]; |
| 3512 Expression* init = kernel_field->initializer(); | 3538 Expression* init = kernel_field->initializer(); |
| 3513 if (!kernel_field->IsStatic() && init != NULL) { | 3539 if (!kernel_field->IsStatic() && init != NULL) { |
| 3514 dart::Field& field = | 3540 dart::Field& field = |
| 3515 dart::Field::ZoneHandle(Z, H.LookupFieldByKernelField(kernel_field)); | 3541 dart::Field::ZoneHandle(Z, H.LookupFieldByKernelField(kernel_field)); |
| 3516 | 3542 |
| 3517 EnterScope(kernel_field); | 3543 EnterScope(kernel_field); |
| 3518 // TODO(27590): Support FLAG_use_field_guards. | |
| 3519 instructions += LoadLocal(scopes_->this_variable); | 3544 instructions += LoadLocal(scopes_->this_variable); |
| 3520 instructions += TranslateExpression(init); | 3545 instructions += TranslateExpression(init); |
| 3521 instructions += StoreInstanceField(field); | 3546 instructions += StoreInstanceFieldGuarded(field); |
| 3522 ExitScope(kernel_field); | 3547 ExitScope(kernel_field); |
| 3523 } | 3548 } |
| 3524 } | 3549 } |
| 3525 | 3550 |
| 3526 // These to come from: | 3551 // These to come from: |
| 3527 // class A { | 3552 // class A { |
| 3528 // var x; | 3553 // var x; |
| 3529 // var y; | 3554 // var y; |
| 3530 // A(this.x) : super(expr), y = (expr); | 3555 // A(this.x) : super(expr), y = (expr); |
| 3531 // } | 3556 // } |
| 3532 for (intptr_t i = 0; i < initializers->length(); i++) { | 3557 for (intptr_t i = 0; i < initializers->length(); i++) { |
| 3533 Initializer* initializer = (*initializers)[i]; | 3558 Initializer* initializer = (*initializers)[i]; |
| 3534 if (initializer->IsFieldInitializer()) { | 3559 if (initializer->IsFieldInitializer()) { |
| 3535 FieldInitializer* init = FieldInitializer::Cast(initializer); | 3560 FieldInitializer* init = FieldInitializer::Cast(initializer); |
| 3536 dart::Field& field = | 3561 dart::Field& field = |
| 3537 dart::Field::ZoneHandle(Z, H.LookupFieldByKernelField(init->field())); | 3562 dart::Field::ZoneHandle(Z, H.LookupFieldByKernelField(init->field())); |
| 3538 | 3563 |
| 3539 // TODO(27590): Support FLAG_use_field_guards. | |
| 3540 instructions += LoadLocal(scopes_->this_variable); | 3564 instructions += LoadLocal(scopes_->this_variable); |
| 3541 instructions += TranslateExpression(init->value()); | 3565 instructions += TranslateExpression(init->value()); |
| 3542 instructions += StoreInstanceField(field); | 3566 instructions += StoreInstanceFieldGuarded(field); |
| 3543 } else if (initializer->IsSuperInitializer()) { | 3567 } else if (initializer->IsSuperInitializer()) { |
| 3544 SuperInitializer* init = SuperInitializer::Cast(initializer); | 3568 SuperInitializer* init = SuperInitializer::Cast(initializer); |
| 3545 | 3569 |
| 3546 instructions += LoadLocal(scopes_->this_variable); | 3570 instructions += LoadLocal(scopes_->this_variable); |
| 3547 instructions += PushArgument(); | 3571 instructions += PushArgument(); |
| 3548 | 3572 |
| 3549 ASSERT(init->arguments()->types().length() == 0); | 3573 ASSERT(init->arguments()->types().length() == 0); |
| 3550 Array& argument_names = Array::ZoneHandle(Z); | 3574 Array& argument_names = Array::ZoneHandle(Z); |
| 3551 instructions += TranslateArguments(init->arguments(), &argument_names); | 3575 instructions += TranslateArguments(init->arguments(), &argument_names); |
| 3552 | 3576 |
| (...skipping 2025 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5578 instructions += LoadLocal(closure); | 5602 instructions += LoadLocal(closure); |
| 5579 instructions += LoadLocal(parsed_function_->current_context_var()); | 5603 instructions += LoadLocal(parsed_function_->current_context_var()); |
| 5580 instructions += StoreInstanceField(Closure::context_offset()); | 5604 instructions += StoreInstanceField(Closure::context_offset()); |
| 5581 | 5605 |
| 5582 return instructions; | 5606 return instructions; |
| 5583 } | 5607 } |
| 5584 | 5608 |
| 5585 | 5609 |
| 5586 } // namespace kernel | 5610 } // namespace kernel |
| 5587 } // namespace dart | 5611 } // namespace dart |
| OLD | NEW |