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

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

Issue 2469703002: Implement instance field guards for kernel-based FlowGraphBuilder (Closed)
Patch Set: update status file Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « runtime/vm/kernel_to_il.h ('k') | tests/language/language_kernel.status » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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
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
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
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
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
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
OLDNEW
« no previous file with comments | « runtime/vm/kernel_to_il.h ('k') | tests/language/language_kernel.status » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698