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

Side by Side Diff: src/compiler/js-native-context-specialization.cc

Issue 2066223002: [turbofan] Introduce CheckHole and CheckHoleNaN operators. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Address comments. Blacklist test Created 4 years, 6 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
« no previous file with comments | « src/compiler/effect-control-linearizer.cc ('k') | src/compiler/opcodes.h » ('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 2015 the V8 project authors. All rights reserved. 1 // Copyright 2015 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/compiler/js-native-context-specialization.h" 5 #include "src/compiler/js-native-context-specialization.h"
6 6
7 #include "src/accessors.h" 7 #include "src/accessors.h"
8 #include "src/code-factory.h" 8 #include "src/code-factory.h"
9 #include "src/compilation-dependencies.h" 9 #include "src/compilation-dependencies.h"
10 #include "src/compiler/access-builder.h" 10 #include "src/compiler/access-builder.h"
(...skipping 634 matching lines...) Expand 10 before | Expand all | Expand 10 after
645 this_effect = this_effects.front(); 645 this_effect = this_effects.front();
646 } else { 646 } else {
647 this_control = 647 this_control =
648 graph()->NewNode(common()->Merge(this_control_count), 648 graph()->NewNode(common()->Merge(this_control_count),
649 this_control_count, &this_controls.front()); 649 this_control_count, &this_controls.front());
650 this_effects.push_back(this_control); 650 this_effects.push_back(this_control);
651 this_effect = 651 this_effect =
652 graph()->NewNode(common()->EffectPhi(this_control_count), 652 graph()->NewNode(common()->EffectPhi(this_control_count),
653 this_control_count + 1, &this_effects.front()); 653 this_control_count + 1, &this_effects.front());
654 } 654 }
655
656 // TODO(turbofan): The effect/control linearization will not find a
657 // FrameState after the StoreField or Call that is generated for the
658 // elements kind transition above. This is because those operators
659 // don't have the kNoWrite flag on it, even though they are not
660 // observable by JavaScript.
661 this_effect = graph()->NewNode(common()->Checkpoint(), frame_state,
662 this_effect, this_control);
655 } 663 }
656 664
657 // Certain stores need a prototype chain check because shape changes 665 // Certain stores need a prototype chain check because shape changes
658 // could allow callbacks on elements in the prototype chain that are 666 // could allow callbacks on elements in the prototype chain that are
659 // not compatible with (monomorphic) keyed stores. 667 // not compatible with (monomorphic) keyed stores.
660 Handle<JSObject> holder; 668 Handle<JSObject> holder;
661 if (access_info.holder().ToHandle(&holder)) { 669 if (access_info.holder().ToHandle(&holder)) {
662 AssumePrototypesStable(receiver_type, native_context, holder); 670 AssumePrototypesStable(receiver_type, native_context, holder);
663 } 671 }
664 672
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after
755 } 763 }
756 // Perform the actual backing store access. 764 // Perform the actual backing store access.
757 this_value = this_effect = graph()->NewNode( 765 this_value = this_effect = graph()->NewNode(
758 simplified()->LoadElement(element_access), this_elements, this_index, 766 simplified()->LoadElement(element_access), this_elements, this_index,
759 this_effect, this_control); 767 this_effect, this_control);
760 // Handle loading from holey backing stores correctly, by either mapping 768 // Handle loading from holey backing stores correctly, by either mapping
761 // the hole to undefined if possible, or deoptimizing otherwise. 769 // the hole to undefined if possible, or deoptimizing otherwise.
762 if (elements_kind == FAST_HOLEY_ELEMENTS || 770 if (elements_kind == FAST_HOLEY_ELEMENTS ||
763 elements_kind == FAST_HOLEY_SMI_ELEMENTS) { 771 elements_kind == FAST_HOLEY_SMI_ELEMENTS) {
764 // Perform the hole check on the result. 772 // Perform the hole check on the result.
765 Node* check = 773 CheckTaggedHoleMode mode = CheckTaggedHoleMode::kNeverReturnHole;
766 graph()->NewNode(simplified()->ReferenceEqual(element_access.type),
767 this_value, jsgraph()->TheHoleConstant());
768 // Check if we are allowed to turn the hole into undefined. 774 // Check if we are allowed to turn the hole into undefined.
769 Type* initial_holey_array_type = Type::Class( 775 Type* initial_holey_array_type = Type::Class(
770 handle(isolate()->get_initial_js_array_map(elements_kind)), 776 handle(isolate()->get_initial_js_array_map(elements_kind)),
771 graph()->zone()); 777 graph()->zone());
772 if (receiver_type->NowIs(initial_holey_array_type) && 778 if (receiver_type->NowIs(initial_holey_array_type) &&
773 isolate()->IsFastArrayConstructorPrototypeChainIntact()) { 779 isolate()->IsFastArrayConstructorPrototypeChainIntact()) {
774 Node* branch = graph()->NewNode(common()->Branch(BranchHint::kFalse),
775 check, this_control);
776 Node* if_true = graph()->NewNode(common()->IfTrue(), branch);
777 Node* if_false = graph()->NewNode(common()->IfFalse(), branch);
778 // Add a code dependency on the array protector cell. 780 // Add a code dependency on the array protector cell.
779 AssumePrototypesStable(receiver_type, native_context, 781 AssumePrototypesStable(receiver_type, native_context,
780 isolate()->initial_object_prototype()); 782 isolate()->initial_object_prototype());
781 dependencies()->AssumePropertyCell(factory()->array_protector()); 783 dependencies()->AssumePropertyCell(factory()->array_protector());
782 // Turn the hole into undefined. 784 // Turn the hole into undefined.
783 this_control = 785 mode = CheckTaggedHoleMode::kConvertHoleToUndefined;
784 graph()->NewNode(common()->Merge(2), if_true, if_false);
785 this_value = graph()->NewNode(
786 common()->Phi(MachineRepresentation::kTagged, 2),
787 jsgraph()->UndefinedConstant(), this_value, this_control);
788 element_type =
789 Type::Union(element_type, Type::Undefined(), graph()->zone());
790 } else {
791 // Deoptimize in case of the hole.
792 this_control = this_effect =
793 graph()->NewNode(common()->DeoptimizeIf(), check, frame_state,
794 this_effect, this_control);
795 } 786 }
796 // Rename the result to represent the actual type (not polluted by the 787 this_value = this_effect =
797 // hole). 788 graph()->NewNode(simplified()->CheckTaggedHole(mode), this_value,
798 this_value = graph()->NewNode(simplified()->TypeGuard(element_type), 789 this_effect, this_control);
799 this_value, this_control);
800 } else if (elements_kind == FAST_HOLEY_DOUBLE_ELEMENTS) { 790 } else if (elements_kind == FAST_HOLEY_DOUBLE_ELEMENTS) {
791 // Perform the hole check on the result.
792 CheckFloat64HoleMode mode = CheckFloat64HoleMode::kNeverReturnHole;
801 // Check if we are allowed to return the hole directly. 793 // Check if we are allowed to return the hole directly.
802 Type* initial_holey_array_type = Type::Class( 794 Type* initial_holey_array_type = Type::Class(
803 handle(isolate()->get_initial_js_array_map(elements_kind)), 795 handle(isolate()->get_initial_js_array_map(elements_kind)),
804 graph()->zone()); 796 graph()->zone());
805 if (receiver_type->NowIs(initial_holey_array_type) && 797 if (receiver_type->NowIs(initial_holey_array_type) &&
806 isolate()->IsFastArrayConstructorPrototypeChainIntact()) { 798 isolate()->IsFastArrayConstructorPrototypeChainIntact()) {
807 // Add a code dependency on the array protector cell. 799 // Add a code dependency on the array protector cell.
808 AssumePrototypesStable(receiver_type, native_context, 800 AssumePrototypesStable(receiver_type, native_context,
809 isolate()->initial_object_prototype()); 801 isolate()->initial_object_prototype());
810 dependencies()->AssumePropertyCell(factory()->array_protector()); 802 dependencies()->AssumePropertyCell(factory()->array_protector());
811 // Turn the hole into undefined. 803 // Return the signaling NaN hole directly if all uses are truncating.
812 this_value = graph()->NewNode(simplified()->NumberConvertHoleNaN(), 804 mode = CheckFloat64HoleMode::kAllowReturnHole;
813 this_value);
814 } else {
815 // Perform the hole check on the result.
816 Node* check =
817 graph()->NewNode(simplified()->NumberIsHoleNaN(), this_value);
818 // Deoptimize in case of the hole.
819 this_control = this_effect =
820 graph()->NewNode(common()->DeoptimizeIf(), check, frame_state,
821 this_effect, this_control);
822 } 805 }
806 this_value = this_effect =
807 graph()->NewNode(simplified()->CheckFloat64Hole(mode), this_value,
808 this_effect, this_control);
823 } 809 }
824 } else { 810 } else {
825 DCHECK_EQ(AccessMode::kStore, access_mode); 811 DCHECK_EQ(AccessMode::kStore, access_mode);
826 if (IsFastSmiElementsKind(elements_kind)) { 812 if (IsFastSmiElementsKind(elements_kind)) {
827 Node* check = graph()->NewNode(simplified()->ObjectIsSmi(), this_value); 813 Node* check = graph()->NewNode(simplified()->ObjectIsSmi(), this_value);
828 this_control = this_effect = 814 this_control = this_effect =
829 graph()->NewNode(common()->DeoptimizeUnless(), check, frame_state, 815 graph()->NewNode(common()->DeoptimizeUnless(), check, frame_state,
830 this_effect, this_control); 816 this_effect, this_control);
831 this_value = graph()->NewNode(simplified()->TypeGuard(type_cache_.kSmi), 817 this_value = graph()->NewNode(simplified()->TypeGuard(type_cache_.kSmi),
832 this_value, this_control); 818 this_value, this_control);
(...skipping 297 matching lines...) Expand 10 before | Expand all | Expand 10 after
1130 } 1116 }
1131 1117
1132 1118
1133 SimplifiedOperatorBuilder* JSNativeContextSpecialization::simplified() const { 1119 SimplifiedOperatorBuilder* JSNativeContextSpecialization::simplified() const {
1134 return jsgraph()->simplified(); 1120 return jsgraph()->simplified();
1135 } 1121 }
1136 1122
1137 } // namespace compiler 1123 } // namespace compiler
1138 } // namespace internal 1124 } // namespace internal
1139 } // namespace v8 1125 } // namespace v8
OLDNEW
« no previous file with comments | « src/compiler/effect-control-linearizer.cc ('k') | src/compiler/opcodes.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698