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

Side by Side Diff: src/ic/accessor-assembler.cc

Issue 2598543003: [runtime][ic] Constant field tracking support. (Closed)
Patch Set: Created 3 years, 11 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
OLDNEW
1 // Copyright 2016 the V8 project authors. All rights reserved. 1 // Copyright 2016 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/ic/accessor-assembler.h" 5 #include "src/ic/accessor-assembler.h"
6 6
7 #include "src/code-factory.h" 7 #include "src/code-factory.h"
8 #include "src/code-stubs.h" 8 #include "src/code-stubs.h"
9 #include "src/ic/handler-configuration.h" 9 #include "src/ic/handler-configuration.h"
10 #include "src/ic/stub-cache.h" 10 #include "src/ic/stub-cache.h"
(...skipping 612 matching lines...) Expand 10 before | Expand all | Expand 10 after
623 Node* handler_kind = DecodeWord<StoreHandler::KindBits>(handler_word); 623 Node* handler_kind = DecodeWord<StoreHandler::KindBits>(handler_word);
624 if (transition) { 624 if (transition) {
625 CSA_ASSERT( 625 CSA_ASSERT(
626 this, 626 this,
627 Word32Or( 627 Word32Or(
628 WordEqual(handler_kind, 628 WordEqual(handler_kind,
629 IntPtrConstant(StoreHandler::kTransitionToField)), 629 IntPtrConstant(StoreHandler::kTransitionToField)),
630 WordEqual(handler_kind, 630 WordEqual(handler_kind,
631 IntPtrConstant(StoreHandler::kTransitionToConstant)))); 631 IntPtrConstant(StoreHandler::kTransitionToConstant))));
632 } else { 632 } else {
633 CSA_ASSERT(this, WordEqual(handler_kind, 633 if (FLAG_track_constant_fields) {
634 IntPtrConstant(StoreHandler::kStoreField))); 634 CSA_ASSERT(
635 this,
636 Word32Or(WordEqual(handler_kind,
637 IntPtrConstant(StoreHandler::kStoreField)),
638 WordEqual(handler_kind,
639 IntPtrConstant(StoreHandler::kStoreConstField))));
640 } else {
641 CSA_ASSERT(this, WordEqual(handler_kind,
642 IntPtrConstant(StoreHandler::kStoreField)));
643 }
635 } 644 }
636 #endif 645 #endif
637 646
638 Node* field_representation = 647 Node* field_representation =
639 DecodeWord<StoreHandler::FieldRepresentationBits>(handler_word); 648 DecodeWord<StoreHandler::FieldRepresentationBits>(handler_word);
640 649
641 Label if_smi_field(this), if_double_field(this), if_heap_object_field(this), 650 Label if_smi_field(this), if_double_field(this), if_heap_object_field(this),
642 if_tagged_field(this); 651 if_tagged_field(this);
643 652
644 GotoIf(WordEqual(field_representation, IntPtrConstant(StoreHandler::kTagged)), 653 GotoIf(WordEqual(field_representation, IntPtrConstant(StoreHandler::kTagged)),
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
691 Node* prepared_value = PrepareValueForStore( 700 Node* prepared_value = PrepareValueForStore(
692 handler_word, holder, representation, transition, value, miss); 701 handler_word, holder, representation, transition, value, miss);
693 702
694 Label if_inobject(this), if_out_of_object(this); 703 Label if_inobject(this), if_out_of_object(this);
695 Branch(IsSetWord<StoreHandler::IsInobjectBits>(handler_word), &if_inobject, 704 Branch(IsSetWord<StoreHandler::IsInobjectBits>(handler_word), &if_inobject,
696 &if_out_of_object); 705 &if_out_of_object);
697 706
698 Bind(&if_inobject); 707 Bind(&if_inobject);
699 { 708 {
700 StoreNamedField(handler_word, holder, true, representation, prepared_value, 709 StoreNamedField(handler_word, holder, true, representation, prepared_value,
701 transition_to_field); 710 transition_to_field, miss);
702 if (transition_to_field) { 711 if (transition_to_field) {
703 StoreMap(holder, transition); 712 StoreMap(holder, transition);
704 } 713 }
705 Return(value); 714 Return(value);
706 } 715 }
707 716
708 Bind(&if_out_of_object); 717 Bind(&if_out_of_object);
709 { 718 {
710 if (transition_to_field) { 719 if (transition_to_field) {
711 Label storage_extended(this); 720 Label storage_extended(this);
712 GotoUnless(IsSetWord<StoreHandler::ExtendStorageBits>(handler_word), 721 GotoUnless(IsSetWord<StoreHandler::ExtendStorageBits>(handler_word),
713 &storage_extended); 722 &storage_extended);
714 Comment("[ Extend storage"); 723 Comment("[ Extend storage");
715 ExtendPropertiesBackingStore(holder); 724 ExtendPropertiesBackingStore(holder);
716 Comment("] Extend storage"); 725 Comment("] Extend storage");
717 Goto(&storage_extended); 726 Goto(&storage_extended);
718 727
719 Bind(&storage_extended); 728 Bind(&storage_extended);
720 } 729 }
721 730
722 StoreNamedField(handler_word, holder, false, representation, prepared_value, 731 StoreNamedField(handler_word, holder, false, representation, prepared_value,
723 transition_to_field); 732 transition_to_field, miss);
724 if (transition_to_field) { 733 if (transition_to_field) {
725 StoreMap(holder, transition); 734 StoreMap(holder, transition);
726 } 735 }
727 Return(value); 736 Return(value);
728 } 737 }
729 } 738 }
730 739
731 Node* AccessorAssembler::PrepareValueForStore(Node* handler_word, Node* holder, 740 Node* AccessorAssembler::PrepareValueForStore(Node* handler_word, Node* holder,
732 Representation representation, 741 Representation representation,
733 Node* transition, Node* value, 742 Node* transition, Node* value,
734 Label* bailout) { 743 Label* bailout) {
735 if (representation.IsDouble()) { 744 if (representation.IsDouble()) {
736 value = TryTaggedToFloat64(value, bailout); 745 value = TryTaggedToFloat64(value, bailout);
737 746
738 } else if (representation.IsHeapObject()) { 747 } else if (representation.IsHeapObject()) {
739 GotoIf(TaggedIsSmi(value), bailout); 748 GotoIf(TaggedIsSmi(value), bailout);
749
750 Label done(this);
751 if (FLAG_track_constant_fields && !transition) {
752 // Skip field type check in favor of constant value check when storing
753 // to constant field.
754 GotoIf(WordEqual(DecodeWord<StoreHandler::KindBits>(handler_word),
755 IntPtrConstant(StoreHandler::kStoreConstField)),
756 &done);
757 }
740 Node* value_index_in_descriptor = 758 Node* value_index_in_descriptor =
741 DecodeWord<StoreHandler::DescriptorValueIndexBits>(handler_word); 759 DecodeWord<StoreHandler::DescriptorValueIndexBits>(handler_word);
742 Node* descriptors = 760 Node* descriptors =
743 LoadMapDescriptors(transition ? transition : LoadMap(holder)); 761 LoadMapDescriptors(transition ? transition : LoadMap(holder));
744 Node* maybe_field_type = 762 Node* maybe_field_type =
745 LoadFixedArrayElement(descriptors, value_index_in_descriptor); 763 LoadFixedArrayElement(descriptors, value_index_in_descriptor);
746 764
747 Label done(this);
748 GotoIf(TaggedIsSmi(maybe_field_type), &done); 765 GotoIf(TaggedIsSmi(maybe_field_type), &done);
749 // Check that value type matches the field type. 766 // Check that value type matches the field type.
750 { 767 {
751 Node* field_type = LoadWeakCellValue(maybe_field_type, bailout); 768 Node* field_type = LoadWeakCellValue(maybe_field_type, bailout);
752 Branch(WordEqual(LoadMap(value), field_type), &done, bailout); 769 Branch(WordEqual(LoadMap(value), field_type), &done, bailout);
753 } 770 }
754 Bind(&done); 771 Bind(&done);
755 772
756 } else if (representation.IsSmi()) { 773 } else if (representation.IsSmi()) {
757 GotoUnless(TaggedIsSmi(value), bailout); 774 GotoUnless(TaggedIsSmi(value), bailout);
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
794 // the write barrier. 811 // the write barrier.
795 CopyFixedArrayElements(kind, properties, new_properties, length, 812 CopyFixedArrayElements(kind, properties, new_properties, length,
796 SKIP_WRITE_BARRIER, mode); 813 SKIP_WRITE_BARRIER, mode);
797 814
798 StoreObjectField(object, JSObject::kPropertiesOffset, new_properties); 815 StoreObjectField(object, JSObject::kPropertiesOffset, new_properties);
799 } 816 }
800 817
801 void AccessorAssembler::StoreNamedField(Node* handler_word, Node* object, 818 void AccessorAssembler::StoreNamedField(Node* handler_word, Node* object,
802 bool is_inobject, 819 bool is_inobject,
803 Representation representation, 820 Representation representation,
804 Node* value, bool transition_to_field) { 821 Node* value, bool transition_to_field,
822 Label* bailout) {
805 bool store_value_as_double = representation.IsDouble(); 823 bool store_value_as_double = representation.IsDouble();
806 Node* property_storage = object; 824 Node* property_storage = object;
807 if (!is_inobject) { 825 if (!is_inobject) {
808 property_storage = LoadProperties(object); 826 property_storage = LoadProperties(object);
809 } 827 }
810 828
811 Node* offset = DecodeWord<StoreHandler::FieldOffsetBits>(handler_word); 829 Node* offset = DecodeWord<StoreHandler::FieldOffsetBits>(handler_word);
812 if (representation.IsDouble()) { 830 if (representation.IsDouble()) {
813 if (!FLAG_unbox_double_fields || !is_inobject) { 831 if (!FLAG_unbox_double_fields || !is_inobject) {
814 if (transition_to_field) { 832 if (transition_to_field) {
815 Node* heap_number = AllocateHeapNumberWithValue(value, MUTABLE); 833 Node* heap_number = AllocateHeapNumberWithValue(value, MUTABLE);
816 // Store the new mutable heap number into the object. 834 // Store the new mutable heap number into the object.
817 value = heap_number; 835 value = heap_number;
818 store_value_as_double = false; 836 store_value_as_double = false;
819 } else { 837 } else {
820 // Load the heap number. 838 // Load the heap number.
821 property_storage = LoadObjectField(property_storage, offset); 839 property_storage = LoadObjectField(property_storage, offset);
822 // Store the double value into it. 840 // Store the double value into it.
823 offset = IntPtrConstant(HeapNumber::kValueOffset); 841 offset = IntPtrConstant(HeapNumber::kValueOffset);
824 } 842 }
825 } 843 }
826 } 844 }
827 845
846 // Do constant value check if necessary.
847 if (FLAG_track_constant_fields && !transition_to_field) {
848 Label done(this);
849 GotoUnless(WordEqual(DecodeWord<StoreHandler::KindBits>(handler_word),
850 IntPtrConstant(StoreHandler::kStoreConstField)),
851 &done);
852 {
853 if (store_value_as_double) {
854 Node* current_value =
855 LoadObjectField(property_storage, offset, MachineType::Float64());
856 GotoUnless(Float64Equal(current_value, value), bailout);
857 } else {
858 Node* current_value = LoadObjectField(property_storage, offset);
859 GotoUnless(WordEqual(current_value, value), bailout);
860 }
861 Goto(&done);
862 }
863 Bind(&done);
864 }
865
866 // Do the store.
828 if (store_value_as_double) { 867 if (store_value_as_double) {
829 StoreObjectFieldNoWriteBarrier(property_storage, offset, value, 868 StoreObjectFieldNoWriteBarrier(property_storage, offset, value,
830 MachineRepresentation::kFloat64); 869 MachineRepresentation::kFloat64);
831 } else if (representation.IsSmi()) { 870 } else if (representation.IsSmi()) {
832 StoreObjectFieldNoWriteBarrier(property_storage, offset, value); 871 StoreObjectFieldNoWriteBarrier(property_storage, offset, value);
833 } else { 872 } else {
834 StoreObjectField(property_storage, offset, value); 873 StoreObjectField(property_storage, offset, value);
835 } 874 }
836 } 875 }
837 876
(...skipping 1045 matching lines...) Expand 10 before | Expand all | Expand 10 after
1883 Node* slot = Parameter(Descriptor::kSlot); 1922 Node* slot = Parameter(Descriptor::kSlot);
1884 Node* context = Parameter(Descriptor::kContext); 1923 Node* context = Parameter(Descriptor::kContext);
1885 Node* vector = LoadTypeFeedbackVectorForStub(); 1924 Node* vector = LoadTypeFeedbackVectorForStub();
1886 1925
1887 StoreICParameters p(context, receiver, name, value, slot, vector); 1926 StoreICParameters p(context, receiver, name, value, slot, vector);
1888 KeyedStoreIC(&p, language_mode); 1927 KeyedStoreIC(&p, language_mode);
1889 } 1928 }
1890 1929
1891 } // namespace internal 1930 } // namespace internal
1892 } // namespace v8 1931 } // namespace v8
OLDNEW
« no previous file with comments | « src/ic/accessor-assembler.h ('k') | src/ic/handler-configuration.h » ('j') | src/lookup.cc » ('J')

Powered by Google App Engine
This is Rietveld 408576698