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

Side by Side Diff: src/hydrogen.cc

Issue 10802038: Add dependency to HLoadKeyed* instructions to prevent invalid hoisting (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Fix nits Created 8 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 4350 matching lines...) Expand 10 before | Expand all | Expand 10 after
4361 current_block()->Finish(compare_index); 4361 current_block()->Finish(compare_index);
4362 4362
4363 set_current_block(loop_successor); 4363 set_current_block(loop_successor);
4364 Drop(5); 4364 Drop(5);
4365 4365
4366 set_current_block(loop_body); 4366 set_current_block(loop_body);
4367 4367
4368 HValue* key = AddInstruction( 4368 HValue* key = AddInstruction(
4369 new(zone()) HLoadKeyedFastElement( 4369 new(zone()) HLoadKeyedFastElement(
4370 environment()->ExpressionStackAt(2), // Enum cache. 4370 environment()->ExpressionStackAt(2), // Enum cache.
4371 environment()->ExpressionStackAt(0))); // Iteration index. 4371 environment()->ExpressionStackAt(0), // Iteration index.
4372 environment()->ExpressionStackAt(0)));
4372 4373
4373 // Check if the expected map still matches that of the enumerable. 4374 // Check if the expected map still matches that of the enumerable.
4374 // If not just deoptimize. 4375 // If not just deoptimize.
4375 AddInstruction(new(zone()) HCheckMapValue( 4376 AddInstruction(new(zone()) HCheckMapValue(
4376 environment()->ExpressionStackAt(4), 4377 environment()->ExpressionStackAt(4),
4377 environment()->ExpressionStackAt(3))); 4378 environment()->ExpressionStackAt(3)));
4378 4379
4379 Bind(each_var, key); 4380 Bind(each_var, key);
4380 4381
4381 BreakAndContinueInfo break_info(stmt, 5); 4382 BreakAndContinueInfo break_info(stmt, 5);
(...skipping 1319 matching lines...) Expand 10 before | Expand all | Expand 10 after
5701 HValue* key) { 5702 HValue* key) {
5702 HValue* context = environment()->LookupContext(); 5703 HValue* context = environment()->LookupContext();
5703 return new(zone()) HLoadKeyedGeneric(context, object, key); 5704 return new(zone()) HLoadKeyedGeneric(context, object, key);
5704 } 5705 }
5705 5706
5706 5707
5707 HInstruction* HGraphBuilder::BuildExternalArrayElementAccess( 5708 HInstruction* HGraphBuilder::BuildExternalArrayElementAccess(
5708 HValue* external_elements, 5709 HValue* external_elements,
5709 HValue* checked_key, 5710 HValue* checked_key,
5710 HValue* val, 5711 HValue* val,
5712 HValue* dependency,
5711 ElementsKind elements_kind, 5713 ElementsKind elements_kind,
5712 bool is_store) { 5714 bool is_store) {
5713 if (is_store) { 5715 if (is_store) {
5714 ASSERT(val != NULL); 5716 ASSERT(val != NULL);
5715 switch (elements_kind) { 5717 switch (elements_kind) {
5716 case EXTERNAL_PIXEL_ELEMENTS: { 5718 case EXTERNAL_PIXEL_ELEMENTS: {
5717 val = AddInstruction(new(zone()) HClampToUint8(val)); 5719 val = AddInstruction(new(zone()) HClampToUint8(val));
5718 break; 5720 break;
5719 } 5721 }
5720 case EXTERNAL_BYTE_ELEMENTS: 5722 case EXTERNAL_BYTE_ELEMENTS:
(...skipping 23 matching lines...) Expand all
5744 case DICTIONARY_ELEMENTS: 5746 case DICTIONARY_ELEMENTS:
5745 case NON_STRICT_ARGUMENTS_ELEMENTS: 5747 case NON_STRICT_ARGUMENTS_ELEMENTS:
5746 UNREACHABLE(); 5748 UNREACHABLE();
5747 break; 5749 break;
5748 } 5750 }
5749 return new(zone()) HStoreKeyedSpecializedArrayElement( 5751 return new(zone()) HStoreKeyedSpecializedArrayElement(
5750 external_elements, checked_key, val, elements_kind); 5752 external_elements, checked_key, val, elements_kind);
5751 } else { 5753 } else {
5752 ASSERT(val == NULL); 5754 ASSERT(val == NULL);
5753 return new(zone()) HLoadKeyedSpecializedArrayElement( 5755 return new(zone()) HLoadKeyedSpecializedArrayElement(
5754 external_elements, checked_key, elements_kind); 5756 external_elements, checked_key, dependency, elements_kind);
5755 } 5757 }
5756 } 5758 }
5757 5759
5758 5760
5759 HInstruction* HGraphBuilder::BuildFastElementAccess(HValue* elements, 5761 HInstruction* HGraphBuilder::BuildFastElementAccess(HValue* elements,
5760 HValue* checked_key, 5762 HValue* checked_key,
5761 HValue* val, 5763 HValue* val,
5764 HValue* load_dependency,
5762 ElementsKind elements_kind, 5765 ElementsKind elements_kind,
5763 bool is_store) { 5766 bool is_store) {
5764 if (is_store) { 5767 if (is_store) {
5765 ASSERT(val != NULL); 5768 ASSERT(val != NULL);
5766 switch (elements_kind) { 5769 switch (elements_kind) {
5767 case FAST_DOUBLE_ELEMENTS: 5770 case FAST_DOUBLE_ELEMENTS:
5768 case FAST_HOLEY_DOUBLE_ELEMENTS: 5771 case FAST_HOLEY_DOUBLE_ELEMENTS:
5769 return new(zone()) HStoreKeyedFastDoubleElement( 5772 return new(zone()) HStoreKeyedFastDoubleElement(
5770 elements, checked_key, val); 5773 elements, checked_key, val);
5771 case FAST_SMI_ELEMENTS: 5774 case FAST_SMI_ELEMENTS:
5772 case FAST_HOLEY_SMI_ELEMENTS: 5775 case FAST_HOLEY_SMI_ELEMENTS:
5773 // Smi-only arrays need a smi check. 5776 // Smi-only arrays need a smi check.
5774 AddInstruction(new(zone()) HCheckSmi(val)); 5777 AddInstruction(new(zone()) HCheckSmi(val));
5775 // Fall through. 5778 // Fall through.
5776 case FAST_ELEMENTS: 5779 case FAST_ELEMENTS:
5777 case FAST_HOLEY_ELEMENTS: 5780 case FAST_HOLEY_ELEMENTS:
5778 return new(zone()) HStoreKeyedFastElement( 5781 return new(zone()) HStoreKeyedFastElement(
5779 elements, checked_key, val, elements_kind); 5782 elements, checked_key, val, elements_kind);
5780 default: 5783 default:
5781 UNREACHABLE(); 5784 UNREACHABLE();
5782 return NULL; 5785 return NULL;
5783 } 5786 }
5784 } 5787 }
5785 // It's an element load (!is_store). 5788 // It's an element load (!is_store).
5786 HoleCheckMode mode = IsFastPackedElementsKind(elements_kind) ? 5789 HoleCheckMode mode = IsFastPackedElementsKind(elements_kind) ?
5787 OMIT_HOLE_CHECK : 5790 OMIT_HOLE_CHECK :
5788 PERFORM_HOLE_CHECK; 5791 PERFORM_HOLE_CHECK;
5789 if (IsFastDoubleElementsKind(elements_kind)) { 5792 if (IsFastDoubleElementsKind(elements_kind)) {
5790 return new(zone()) HLoadKeyedFastDoubleElement(elements, checked_key, mode); 5793 return new(zone()) HLoadKeyedFastDoubleElement(elements, checked_key,
5794 load_dependency, mode);
5791 } else { // Smi or Object elements. 5795 } else { // Smi or Object elements.
5792 return new(zone()) HLoadKeyedFastElement(elements, checked_key, 5796 return new(zone()) HLoadKeyedFastElement(elements, checked_key,
5793 elements_kind); 5797 load_dependency, elements_kind);
5794 } 5798 }
5795 } 5799 }
5796 5800
5797 5801
5798 HInstruction* HGraphBuilder::BuildMonomorphicElementAccess(HValue* object, 5802 HInstruction* HGraphBuilder::BuildMonomorphicElementAccess(HValue* object,
5799 HValue* key, 5803 HValue* key,
5800 HValue* val, 5804 HValue* val,
5801 HValue* dependency, 5805 HValue* dependency,
5802 Handle<Map> map, 5806 Handle<Map> map,
5803 bool is_store) { 5807 bool is_store) {
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
5840 } 5844 }
5841 HInstruction* length = NULL; 5845 HInstruction* length = NULL;
5842 HInstruction* checked_key = NULL; 5846 HInstruction* checked_key = NULL;
5843 if (map->has_external_array_elements()) { 5847 if (map->has_external_array_elements()) {
5844 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements)); 5848 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements));
5845 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length, 5849 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length,
5846 ALLOW_SMI_KEY)); 5850 ALLOW_SMI_KEY));
5847 HLoadExternalArrayPointer* external_elements = 5851 HLoadExternalArrayPointer* external_elements =
5848 new(zone()) HLoadExternalArrayPointer(elements); 5852 new(zone()) HLoadExternalArrayPointer(elements);
5849 AddInstruction(external_elements); 5853 AddInstruction(external_elements);
5850 return BuildExternalArrayElementAccess(external_elements, checked_key, 5854 return BuildExternalArrayElementAccess(
5851 val, map->elements_kind(), is_store); 5855 external_elements, checked_key, val, mapcheck,
5856 map->elements_kind(), is_store);
5852 } 5857 }
5853 ASSERT(fast_smi_only_elements || 5858 ASSERT(fast_smi_only_elements ||
5854 fast_elements || 5859 fast_elements ||
5855 map->has_fast_double_elements()); 5860 map->has_fast_double_elements());
5856 if (map->instance_type() == JS_ARRAY_TYPE) { 5861 if (map->instance_type() == JS_ARRAY_TYPE) {
5857 length = AddInstruction(new(zone()) HJSArrayLength(object, mapcheck, 5862 length = AddInstruction(new(zone()) HJSArrayLength(object, mapcheck,
5858 HType::Smi())); 5863 HType::Smi()));
5859 } else { 5864 } else {
5860 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements)); 5865 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements));
5861 } 5866 }
5862 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length)); 5867 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length));
5863 return BuildFastElementAccess(elements, checked_key, val, 5868 return BuildFastElementAccess(elements, checked_key, val, mapcheck,
5864 map->elements_kind(), is_store); 5869 map->elements_kind(), is_store);
5865 } 5870 }
5866 5871
5867 5872
5868 HInstruction* HGraphBuilder::TryBuildConsolidatedElementLoad( 5873 HInstruction* HGraphBuilder::TryBuildConsolidatedElementLoad(
5869 HValue* object, 5874 HValue* object,
5870 HValue* key, 5875 HValue* key,
5871 HValue* val, 5876 HValue* val,
5872 SmallMapList* maps) { 5877 SmallMapList* maps) {
5873 // For polymorphic loads of similar elements kinds (i.e. all tagged or all 5878 // For polymorphic loads of similar elements kinds (i.e. all tagged or all
(...skipping 200 matching lines...) Expand 10 before | Expand all | Expand 10 after
6074 typecheck->SetSuccessorAt(1, if_fastobject); 6079 typecheck->SetSuccessorAt(1, if_fastobject);
6075 current_block()->Finish(typecheck); 6080 current_block()->Finish(typecheck);
6076 6081
6077 set_current_block(if_jsarray); 6082 set_current_block(if_jsarray);
6078 HInstruction* length; 6083 HInstruction* length;
6079 length = AddInstruction(new(zone()) HJSArrayLength(object, typecheck, 6084 length = AddInstruction(new(zone()) HJSArrayLength(object, typecheck,
6080 HType::Smi())); 6085 HType::Smi()));
6081 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length, 6086 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length,
6082 ALLOW_SMI_KEY)); 6087 ALLOW_SMI_KEY));
6083 access = AddInstruction(BuildFastElementAccess( 6088 access = AddInstruction(BuildFastElementAccess(
6084 elements, checked_key, val, elements_kind, is_store)); 6089 elements, checked_key, val, elements_kind_branch,
6090 elements_kind, is_store));
6085 if (!is_store) { 6091 if (!is_store) {
6086 Push(access); 6092 Push(access);
6087 } 6093 }
6088 6094
6089 *has_side_effects |= access->HasObservableSideEffects(); 6095 *has_side_effects |= access->HasObservableSideEffects();
6090 if (position != -1) { 6096 if (position != -1) {
6091 access->set_position(position); 6097 access->set_position(position);
6092 } 6098 }
6093 if_jsarray->Goto(join); 6099 if_jsarray->Goto(join);
6094 6100
6095 set_current_block(if_fastobject); 6101 set_current_block(if_fastobject);
6096 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements)); 6102 length = AddInstruction(new(zone()) HFixedArrayBaseLength(elements));
6097 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length, 6103 checked_key = AddInstruction(new(zone()) HBoundsCheck(key, length,
6098 ALLOW_SMI_KEY)); 6104 ALLOW_SMI_KEY));
6099 access = AddInstruction(BuildFastElementAccess( 6105 access = AddInstruction(BuildFastElementAccess(
6100 elements, checked_key, val, elements_kind, is_store)); 6106 elements, checked_key, val, elements_kind_branch,
6107 elements_kind, is_store));
6101 } else if (elements_kind == DICTIONARY_ELEMENTS) { 6108 } else if (elements_kind == DICTIONARY_ELEMENTS) {
6102 if (is_store) { 6109 if (is_store) {
6103 access = AddInstruction(BuildStoreKeyedGeneric(object, key, val)); 6110 access = AddInstruction(BuildStoreKeyedGeneric(object, key, val));
6104 } else { 6111 } else {
6105 access = AddInstruction(BuildLoadKeyedGeneric(object, key)); 6112 access = AddInstruction(BuildLoadKeyedGeneric(object, key));
6106 } 6113 }
6107 } else { // External array elements. 6114 } else { // External array elements.
6108 access = AddInstruction(BuildExternalArrayElementAccess( 6115 access = AddInstruction(BuildExternalArrayElementAccess(
6109 external_elements, checked_key, val, elements_kind, is_store)); 6116 external_elements, checked_key, val, elements_kind_branch,
6117 elements_kind, is_store));
6110 } 6118 }
6111 *has_side_effects |= access->HasObservableSideEffects(); 6119 *has_side_effects |= access->HasObservableSideEffects();
6112 if (position != RelocInfo::kNoPosition) access->set_position(position); 6120 if (position != RelocInfo::kNoPosition) access->set_position(position);
6113 if (!is_store) { 6121 if (!is_store) {
6114 Push(access); 6122 Push(access);
6115 } 6123 }
6116 current_block()->Goto(join); 6124 current_block()->Goto(join);
6117 set_current_block(if_false); 6125 set_current_block(if_false);
6118 } 6126 }
6119 } 6127 }
(...skipping 3455 matching lines...) Expand 10 before | Expand all | Expand 10 after
9575 } 9583 }
9576 } 9584 }
9577 9585
9578 #ifdef DEBUG 9586 #ifdef DEBUG
9579 if (graph_ != NULL) graph_->Verify(false); // No full verify. 9587 if (graph_ != NULL) graph_->Verify(false); // No full verify.
9580 if (allocator_ != NULL) allocator_->Verify(); 9588 if (allocator_ != NULL) allocator_->Verify();
9581 #endif 9589 #endif
9582 } 9590 }
9583 9591
9584 } } // namespace v8::internal 9592 } } // namespace v8::internal
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698