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

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

Issue 23584002: Replace guarded list length field loads with constants (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 7 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « no previous file | runtime/vm/intermediate_language.cc » ('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) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/flow_graph_optimizer.h" 5 #include "vm/flow_graph_optimizer.h"
6 6
7 #include "vm/bit_vector.h" 7 #include "vm/bit_vector.h"
8 #include "vm/cha.h" 8 #include "vm/cha.h"
9 #include "vm/dart_entry.h" 9 #include "vm/dart_entry.h"
10 #include "vm/flow_graph_builder.h" 10 #include "vm/flow_graph_builder.h"
(...skipping 752 matching lines...) Expand 10 before | Expand all | Expand 10 after
763 Definition** array, 763 Definition** array,
764 Definition** index) { 764 Definition** index) {
765 // Insert class check and index smi checks and attach a copy of the 765 // Insert class check and index smi checks and attach a copy of the
766 // original environment because the operation can still deoptimize. 766 // original environment because the operation can still deoptimize.
767 AddReceiverCheck(call); 767 AddReceiverCheck(call);
768 InsertBefore(call, 768 InsertBefore(call,
769 new CheckSmiInstr(new Value(*index), call->deopt_id()), 769 new CheckSmiInstr(new Value(*index), call->deopt_id()),
770 call->env(), 770 call->env(),
771 Definition::kEffect); 771 Definition::kEffect);
772 772
773 bool emit_bounds_check = true; 773 // Insert array length load and bounds check.
774 // Get the field for the array. 774 const bool is_immutable =
775 const Field* field = NULL; 775 CheckArrayBoundInstr::IsFixedLengthArrayType(class_id);
776 if ((*array)->IsLoadField()) { 776 LoadFieldInstr* length =
777 LoadFieldInstr* load_field_instr = (*array)->AsLoadField(); 777 new LoadFieldInstr(new Value(*array),
778 field = load_field_instr->field(); 778 CheckArrayBoundInstr::LengthOffsetFor(class_id),
779 } 779 Type::ZoneHandle(Type::SmiType()),
780 // Extract the guarded array length. 780 is_immutable);
781 intptr_t guarded_array_length = -1; 781 length->set_result_cid(kSmiCid);
782 if (field != NULL) { 782 length->set_recognized_kind(
783 if (field->guarded_list_length() >= 0) { 783 LoadFieldInstr::RecognizedKindFromArrayCid(class_id));
784 guarded_array_length = field->guarded_list_length(); 784 InsertBefore(call, length, NULL, Definition::kValue);
785 } 785 InsertBefore(call,
786 } 786 new CheckArrayBoundInstr(new Value(length),
787 Definition* i = *index; 787 new Value(*index),
788 // Check if we can skip emitting the bounds check. 788 call->deopt_id()),
789 if (i->IsConstant() && guarded_array_length >= 0) { 789 call->env(),
790 ConstantInstr* constant = i->AsConstant(); 790 Definition::kEffect);
791 ASSERT(constant != NULL);
792 intptr_t ci = Smi::Cast(constant->value()).Value();
793 if (ci < guarded_array_length) {
794 emit_bounds_check = false;
795 }
796 }
797
798 if (emit_bounds_check) {
799 // Insert array length load and bounds check.
800 const bool is_immutable =
801 CheckArrayBoundInstr::IsFixedLengthArrayType(class_id);
802 LoadFieldInstr* length =
803 new LoadFieldInstr(new Value(*array),
804 CheckArrayBoundInstr::LengthOffsetFor(class_id),
805 Type::ZoneHandle(Type::SmiType()),
806 is_immutable);
807 length->set_result_cid(kSmiCid);
808 length->set_recognized_kind(
809 LoadFieldInstr::RecognizedKindFromArrayCid(class_id));
810 InsertBefore(call, length, NULL, Definition::kValue);
811 InsertBefore(call,
812 new CheckArrayBoundInstr(new Value(length),
813 new Value(*index),
814 call->deopt_id()),
815 call->env(),
816 Definition::kEffect);
817 }
818 791
819 792
820 if (class_id == kGrowableObjectArrayCid) { 793 if (class_id == kGrowableObjectArrayCid) {
821 // Insert data elements load. 794 // Insert data elements load.
822 LoadFieldInstr* elements = 795 LoadFieldInstr* elements =
823 new LoadFieldInstr(new Value(*array), 796 new LoadFieldInstr(new Value(*array),
824 GrowableObjectArray::data_offset(), 797 GrowableObjectArray::data_offset(),
825 Type::ZoneHandle(Type::DynamicType())); 798 Type::ZoneHandle(Type::DynamicType()));
826 elements->set_result_cid(kArrayCid); 799 elements->set_result_cid(kArrayCid);
827 InsertBefore(call, elements, NULL, Definition::kValue); 800 InsertBefore(call, elements, NULL, Definition::kValue);
(...skipping 6682 matching lines...) Expand 10 before | Expand all | Expand 10 after
7510 } 7483 }
7511 7484
7512 // Insert materializations at environment uses. 7485 // Insert materializations at environment uses.
7513 for (intptr_t i = 0; i < exits.length(); i++) { 7486 for (intptr_t i = 0; i < exits.length(); i++) {
7514 CreateMaterializationAt(exits[i], alloc, alloc->cls(), *fields); 7487 CreateMaterializationAt(exits[i], alloc, alloc->cls(), *fields);
7515 } 7488 }
7516 } 7489 }
7517 7490
7518 7491
7519 } // namespace dart 7492 } // namespace dart
OLDNEW
« no previous file with comments | « no previous file | runtime/vm/intermediate_language.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698