OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 #ifndef V8_COMPILER_INSTRUCTION_H_ | 5 #ifndef V8_COMPILER_INSTRUCTION_H_ |
6 #define V8_COMPILER_INSTRUCTION_H_ | 6 #define V8_COMPILER_INSTRUCTION_H_ |
7 | 7 |
8 #include <deque> | 8 #include <deque> |
9 #include <iosfwd> | 9 #include <iosfwd> |
10 #include <map> | 10 #include <map> |
11 #include <set> | 11 #include <set> |
12 | 12 |
13 #include "src/compiler/common-operator.h" | 13 #include "src/compiler/common-operator.h" |
14 #include "src/compiler/frame.h" | 14 #include "src/compiler/frame.h" |
15 #include "src/compiler/instruction-codes.h" | 15 #include "src/compiler/instruction-codes.h" |
16 #include "src/compiler/opcodes.h" | 16 #include "src/compiler/opcodes.h" |
17 #include "src/compiler/register-configuration.h" | 17 #include "src/compiler/register-configuration.h" |
18 #include "src/compiler/schedule.h" | |
19 #include "src/compiler/source-position.h" | 18 #include "src/compiler/source-position.h" |
20 #include "src/zone-allocator.h" | 19 #include "src/zone-allocator.h" |
21 | 20 |
22 namespace v8 { | 21 namespace v8 { |
23 namespace internal { | 22 namespace internal { |
24 namespace compiler { | 23 namespace compiler { |
25 | 24 |
| 25 class Schedule; |
| 26 |
26 // A couple of reserved opcodes are used for internal use. | 27 // A couple of reserved opcodes are used for internal use. |
27 const InstructionCode kGapInstruction = -1; | 28 const InstructionCode kGapInstruction = -1; |
28 const InstructionCode kSourcePositionInstruction = -2; | 29 const InstructionCode kSourcePositionInstruction = -2; |
29 | 30 |
30 #define INSTRUCTION_OPERAND_LIST(V) \ | 31 #define INSTRUCTION_OPERAND_LIST(V) \ |
31 V(Constant, CONSTANT) \ | 32 V(Constant, CONSTANT) \ |
32 V(Immediate, IMMEDIATE) \ | 33 V(Immediate, IMMEDIATE) \ |
33 V(StackSlot, STACK_SLOT) \ | 34 V(StackSlot, STACK_SLOT) \ |
34 V(DoubleStackSlot, DOUBLE_STACK_SLOT) \ | 35 V(DoubleStackSlot, DOUBLE_STACK_SLOT) \ |
35 V(Register, REGISTER) \ | 36 V(Register, REGISTER) \ |
(...skipping 648 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
684 : Instruction(kSourcePositionInstruction), | 685 : Instruction(kSourcePositionInstruction), |
685 source_position_(source_position) { | 686 source_position_(source_position) { |
686 DCHECK(!source_position_.IsInvalid()); | 687 DCHECK(!source_position_.IsInvalid()); |
687 DCHECK(!source_position_.IsUnknown()); | 688 DCHECK(!source_position_.IsUnknown()); |
688 } | 689 } |
689 | 690 |
690 SourcePosition source_position_; | 691 SourcePosition source_position_; |
691 }; | 692 }; |
692 | 693 |
693 | 694 |
| 695 class RpoNumber FINAL { |
| 696 public: |
| 697 static const int kInvalidRpoNumber = -1; |
| 698 int ToInt() const { |
| 699 DCHECK(IsValid()); |
| 700 return index_; |
| 701 } |
| 702 size_t ToSize() const { |
| 703 DCHECK(IsValid()); |
| 704 return static_cast<size_t>(index_); |
| 705 } |
| 706 bool IsValid() const { return index_ >= 0; } |
| 707 static RpoNumber FromInt(int index) { return RpoNumber(index); } |
| 708 static RpoNumber Invalid() { return RpoNumber(kInvalidRpoNumber); } |
| 709 |
| 710 bool IsNext(const RpoNumber other) const { |
| 711 DCHECK(IsValid()); |
| 712 return other.index_ == this->index_ + 1; |
| 713 } |
| 714 |
| 715 bool operator==(RpoNumber other) const { |
| 716 return this->index_ == other.index_; |
| 717 } |
| 718 |
| 719 private: |
| 720 explicit RpoNumber(int32_t index) : index_(index) {} |
| 721 int32_t index_; |
| 722 }; |
| 723 |
| 724 |
| 725 std::ostream& operator<<(std::ostream&, const RpoNumber&); |
| 726 |
| 727 |
694 class Constant FINAL { | 728 class Constant FINAL { |
695 public: | 729 public: |
696 enum Type { | 730 enum Type { |
697 kInt32, | 731 kInt32, |
698 kInt64, | 732 kInt64, |
699 kFloat32, | 733 kFloat32, |
700 kFloat64, | 734 kFloat64, |
701 kExternalReference, | 735 kExternalReference, |
702 kHeapObject, | 736 kHeapObject, |
703 kRpoNumber | 737 kRpoNumber |
704 }; | 738 }; |
705 | 739 |
706 explicit Constant(int32_t v) : type_(kInt32), value_(v) {} | 740 explicit Constant(int32_t v) : type_(kInt32), value_(v) {} |
707 explicit Constant(int64_t v) : type_(kInt64), value_(v) {} | 741 explicit Constant(int64_t v) : type_(kInt64), value_(v) {} |
708 explicit Constant(float v) : type_(kFloat32), value_(bit_cast<int32_t>(v)) {} | 742 explicit Constant(float v) : type_(kFloat32), value_(bit_cast<int32_t>(v)) {} |
709 explicit Constant(double v) : type_(kFloat64), value_(bit_cast<int64_t>(v)) {} | 743 explicit Constant(double v) : type_(kFloat64), value_(bit_cast<int64_t>(v)) {} |
710 explicit Constant(ExternalReference ref) | 744 explicit Constant(ExternalReference ref) |
711 : type_(kExternalReference), value_(bit_cast<intptr_t>(ref)) {} | 745 : type_(kExternalReference), value_(bit_cast<intptr_t>(ref)) {} |
712 explicit Constant(Handle<HeapObject> obj) | 746 explicit Constant(Handle<HeapObject> obj) |
713 : type_(kHeapObject), value_(bit_cast<intptr_t>(obj)) {} | 747 : type_(kHeapObject), value_(bit_cast<intptr_t>(obj)) {} |
714 explicit Constant(BasicBlock::RpoNumber rpo) | 748 explicit Constant(RpoNumber rpo) : type_(kRpoNumber), value_(rpo.ToInt()) {} |
715 : type_(kRpoNumber), value_(rpo.ToInt()) {} | |
716 | 749 |
717 Type type() const { return type_; } | 750 Type type() const { return type_; } |
718 | 751 |
719 int32_t ToInt32() const { | 752 int32_t ToInt32() const { |
720 DCHECK(type() == kInt32 || type() == kInt64); | 753 DCHECK(type() == kInt32 || type() == kInt64); |
721 const int32_t value = static_cast<int32_t>(value_); | 754 const int32_t value = static_cast<int32_t>(value_); |
722 DCHECK_EQ(value_, static_cast<int64_t>(value)); | 755 DCHECK_EQ(value_, static_cast<int64_t>(value)); |
723 return value; | 756 return value; |
724 } | 757 } |
725 | 758 |
(...skipping 12 matching lines...) Expand all Loading... |
738 if (type() == kInt32) return ToInt32(); | 771 if (type() == kInt32) return ToInt32(); |
739 DCHECK_EQ(kFloat64, type()); | 772 DCHECK_EQ(kFloat64, type()); |
740 return bit_cast<double>(value_); | 773 return bit_cast<double>(value_); |
741 } | 774 } |
742 | 775 |
743 ExternalReference ToExternalReference() const { | 776 ExternalReference ToExternalReference() const { |
744 DCHECK_EQ(kExternalReference, type()); | 777 DCHECK_EQ(kExternalReference, type()); |
745 return bit_cast<ExternalReference>(static_cast<intptr_t>(value_)); | 778 return bit_cast<ExternalReference>(static_cast<intptr_t>(value_)); |
746 } | 779 } |
747 | 780 |
748 BasicBlock::RpoNumber ToRpoNumber() const { | 781 RpoNumber ToRpoNumber() const { |
749 DCHECK_EQ(kRpoNumber, type()); | 782 DCHECK_EQ(kRpoNumber, type()); |
750 return BasicBlock::RpoNumber::FromInt(static_cast<int>(value_)); | 783 return RpoNumber::FromInt(static_cast<int>(value_)); |
751 } | 784 } |
752 | 785 |
753 Handle<HeapObject> ToHeapObject() const { | 786 Handle<HeapObject> ToHeapObject() const { |
754 DCHECK_EQ(kHeapObject, type()); | 787 DCHECK_EQ(kHeapObject, type()); |
755 return bit_cast<Handle<HeapObject> >(static_cast<intptr_t>(value_)); | 788 return bit_cast<Handle<HeapObject> >(static_cast<intptr_t>(value_)); |
756 } | 789 } |
757 | 790 |
758 private: | 791 private: |
759 Type type_; | 792 Type type_; |
760 int64_t value_; | 793 int64_t value_; |
(...skipping 63 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
824 const int virtual_register_; | 857 const int virtual_register_; |
825 InstructionOperand output_; | 858 InstructionOperand output_; |
826 IntVector operands_; | 859 IntVector operands_; |
827 Inputs inputs_; | 860 Inputs inputs_; |
828 }; | 861 }; |
829 | 862 |
830 | 863 |
831 // Analogue of BasicBlock for Instructions instead of Nodes. | 864 // Analogue of BasicBlock for Instructions instead of Nodes. |
832 class InstructionBlock FINAL : public ZoneObject { | 865 class InstructionBlock FINAL : public ZoneObject { |
833 public: | 866 public: |
834 InstructionBlock(Zone* zone, BasicBlock::Id id, | 867 InstructionBlock(Zone* zone, RpoNumber rpo_number, RpoNumber loop_header, |
835 BasicBlock::RpoNumber rpo_number, | 868 RpoNumber loop_end, bool deferred); |
836 BasicBlock::RpoNumber loop_header, | |
837 BasicBlock::RpoNumber loop_end, bool deferred); | |
838 | 869 |
839 // Instruction indexes (used by the register allocator). | 870 // Instruction indexes (used by the register allocator). |
840 int first_instruction_index() const { | 871 int first_instruction_index() const { |
841 DCHECK(code_start_ >= 0); | 872 DCHECK(code_start_ >= 0); |
842 DCHECK(code_end_ > 0); | 873 DCHECK(code_end_ > 0); |
843 DCHECK(code_end_ >= code_start_); | 874 DCHECK(code_end_ >= code_start_); |
844 return code_start_; | 875 return code_start_; |
845 } | 876 } |
846 int last_instruction_index() const { | 877 int last_instruction_index() const { |
847 DCHECK(code_start_ >= 0); | 878 DCHECK(code_start_ >= 0); |
848 DCHECK(code_end_ > 0); | 879 DCHECK(code_end_ > 0); |
849 DCHECK(code_end_ >= code_start_); | 880 DCHECK(code_end_ >= code_start_); |
850 return code_end_ - 1; | 881 return code_end_ - 1; |
851 } | 882 } |
852 | 883 |
853 int32_t code_start() const { return code_start_; } | 884 int32_t code_start() const { return code_start_; } |
854 void set_code_start(int32_t start) { code_start_ = start; } | 885 void set_code_start(int32_t start) { code_start_ = start; } |
855 | 886 |
856 int32_t code_end() const { return code_end_; } | 887 int32_t code_end() const { return code_end_; } |
857 void set_code_end(int32_t end) { code_end_ = end; } | 888 void set_code_end(int32_t end) { code_end_ = end; } |
858 | 889 |
859 bool IsDeferred() const { return deferred_; } | 890 bool IsDeferred() const { return deferred_; } |
860 | 891 |
861 BasicBlock::Id id() const { return id_; } | 892 RpoNumber ao_number() const { return ao_number_; } |
862 BasicBlock::RpoNumber ao_number() const { return ao_number_; } | 893 RpoNumber rpo_number() const { return rpo_number_; } |
863 BasicBlock::RpoNumber rpo_number() const { return rpo_number_; } | 894 RpoNumber loop_header() const { return loop_header_; } |
864 BasicBlock::RpoNumber loop_header() const { return loop_header_; } | 895 RpoNumber loop_end() const { |
865 BasicBlock::RpoNumber loop_end() const { | |
866 DCHECK(IsLoopHeader()); | 896 DCHECK(IsLoopHeader()); |
867 return loop_end_; | 897 return loop_end_; |
868 } | 898 } |
869 inline bool IsLoopHeader() const { return loop_end_.IsValid(); } | 899 inline bool IsLoopHeader() const { return loop_end_.IsValid(); } |
870 | 900 |
871 typedef ZoneVector<BasicBlock::RpoNumber> Predecessors; | 901 typedef ZoneVector<RpoNumber> Predecessors; |
872 Predecessors& predecessors() { return predecessors_; } | 902 Predecessors& predecessors() { return predecessors_; } |
873 const Predecessors& predecessors() const { return predecessors_; } | 903 const Predecessors& predecessors() const { return predecessors_; } |
874 size_t PredecessorCount() const { return predecessors_.size(); } | 904 size_t PredecessorCount() const { return predecessors_.size(); } |
875 size_t PredecessorIndexOf(BasicBlock::RpoNumber rpo_number) const; | 905 size_t PredecessorIndexOf(RpoNumber rpo_number) const; |
876 | 906 |
877 typedef ZoneVector<BasicBlock::RpoNumber> Successors; | 907 typedef ZoneVector<RpoNumber> Successors; |
878 Successors& successors() { return successors_; } | 908 Successors& successors() { return successors_; } |
879 const Successors& successors() const { return successors_; } | 909 const Successors& successors() const { return successors_; } |
880 size_t SuccessorCount() const { return successors_.size(); } | 910 size_t SuccessorCount() const { return successors_.size(); } |
881 | 911 |
882 typedef ZoneVector<PhiInstruction*> PhiInstructions; | 912 typedef ZoneVector<PhiInstruction*> PhiInstructions; |
883 const PhiInstructions& phis() const { return phis_; } | 913 const PhiInstructions& phis() const { return phis_; } |
884 void AddPhi(PhiInstruction* phi) { phis_.push_back(phi); } | 914 void AddPhi(PhiInstruction* phi) { phis_.push_back(phi); } |
885 | 915 |
886 void set_ao_number(BasicBlock::RpoNumber ao_number) { | 916 void set_ao_number(RpoNumber ao_number) { ao_number_ = ao_number; } |
887 ao_number_ = ao_number; | |
888 } | |
889 | 917 |
890 private: | 918 private: |
891 Successors successors_; | 919 Successors successors_; |
892 Predecessors predecessors_; | 920 Predecessors predecessors_; |
893 PhiInstructions phis_; | 921 PhiInstructions phis_; |
894 const BasicBlock::Id id_; | 922 RpoNumber ao_number_; // Assembly order number. |
895 BasicBlock::RpoNumber ao_number_; // Assembly order number. | 923 const RpoNumber rpo_number_; |
896 const BasicBlock::RpoNumber rpo_number_; | 924 const RpoNumber loop_header_; |
897 const BasicBlock::RpoNumber loop_header_; | 925 const RpoNumber loop_end_; |
898 const BasicBlock::RpoNumber loop_end_; | |
899 int32_t code_start_; // start index of arch-specific code. | 926 int32_t code_start_; // start index of arch-specific code. |
900 int32_t code_end_; // end index of arch-specific code. | 927 int32_t code_end_; // end index of arch-specific code. |
901 const bool deferred_; // Block contains deferred code. | 928 const bool deferred_; // Block contains deferred code. |
902 }; | 929 }; |
903 | 930 |
904 typedef ZoneDeque<Constant> ConstantDeque; | 931 typedef ZoneDeque<Constant> ConstantDeque; |
905 typedef std::map<int, Constant, std::less<int>, | 932 typedef std::map<int, Constant, std::less<int>, |
906 zone_allocator<std::pair<int, Constant> > > ConstantMap; | 933 zone_allocator<std::pair<int, Constant> > > ConstantMap; |
907 | 934 |
908 typedef ZoneDeque<Instruction*> InstructionDeque; | 935 typedef ZoneDeque<Instruction*> InstructionDeque; |
(...skipping 21 matching lines...) Expand all Loading... |
930 int VirtualRegisterCount() const { return next_virtual_register_; } | 957 int VirtualRegisterCount() const { return next_virtual_register_; } |
931 | 958 |
932 const InstructionBlocks& instruction_blocks() const { | 959 const InstructionBlocks& instruction_blocks() const { |
933 return *instruction_blocks_; | 960 return *instruction_blocks_; |
934 } | 961 } |
935 | 962 |
936 int InstructionBlockCount() const { | 963 int InstructionBlockCount() const { |
937 return static_cast<int>(instruction_blocks_->size()); | 964 return static_cast<int>(instruction_blocks_->size()); |
938 } | 965 } |
939 | 966 |
940 InstructionBlock* InstructionBlockAt(BasicBlock::RpoNumber rpo_number) { | 967 InstructionBlock* InstructionBlockAt(RpoNumber rpo_number) { |
941 return instruction_blocks_->at(rpo_number.ToSize()); | 968 return instruction_blocks_->at(rpo_number.ToSize()); |
942 } | 969 } |
943 | 970 |
944 int LastLoopInstructionIndex(const InstructionBlock* block) { | 971 int LastLoopInstructionIndex(const InstructionBlock* block) { |
945 return instruction_blocks_->at(block->loop_end().ToSize() - 1) | 972 return instruction_blocks_->at(block->loop_end().ToSize() - 1) |
946 ->last_instruction_index(); | 973 ->last_instruction_index(); |
947 } | 974 } |
948 | 975 |
949 const InstructionBlock* InstructionBlockAt( | 976 const InstructionBlock* InstructionBlockAt(RpoNumber rpo_number) const { |
950 BasicBlock::RpoNumber rpo_number) const { | |
951 return instruction_blocks_->at(rpo_number.ToSize()); | 977 return instruction_blocks_->at(rpo_number.ToSize()); |
952 } | 978 } |
953 | 979 |
954 const InstructionBlock* GetInstructionBlock(int instruction_index) const; | 980 const InstructionBlock* GetInstructionBlock(int instruction_index) const; |
955 | 981 |
956 bool IsReference(int virtual_register) const; | 982 bool IsReference(int virtual_register) const; |
957 bool IsDouble(int virtual_register) const; | 983 bool IsDouble(int virtual_register) const; |
958 | 984 |
959 void MarkAsReference(int virtual_register); | 985 void MarkAsReference(int virtual_register); |
960 void MarkAsDouble(int virtual_register); | 986 void MarkAsDouble(int virtual_register); |
961 | 987 |
962 void AddGapMove(int index, InstructionOperand* from, InstructionOperand* to); | 988 void AddGapMove(int index, InstructionOperand* from, InstructionOperand* to); |
963 | 989 |
964 GapInstruction* GetBlockStart(BasicBlock::RpoNumber rpo) const; | 990 GapInstruction* GetBlockStart(RpoNumber rpo) const; |
965 | 991 |
966 typedef InstructionDeque::const_iterator const_iterator; | 992 typedef InstructionDeque::const_iterator const_iterator; |
967 const_iterator begin() const { return instructions_.begin(); } | 993 const_iterator begin() const { return instructions_.begin(); } |
968 const_iterator end() const { return instructions_.end(); } | 994 const_iterator end() const { return instructions_.end(); } |
969 const InstructionDeque& instructions() const { return instructions_; } | 995 const InstructionDeque& instructions() const { return instructions_; } |
970 | 996 |
971 GapInstruction* GapAt(int index) const { | 997 GapInstruction* GapAt(int index) const { |
972 return GapInstruction::cast(InstructionAt(index)); | 998 return GapInstruction::cast(InstructionAt(index)); |
973 } | 999 } |
974 bool IsGapAt(int index) const { return InstructionAt(index)->IsGapMoves(); } | 1000 bool IsGapAt(int index) const { return InstructionAt(index)->IsGapMoves(); } |
975 Instruction* InstructionAt(int index) const { | 1001 Instruction* InstructionAt(int index) const { |
976 DCHECK(index >= 0); | 1002 DCHECK(index >= 0); |
977 DCHECK(index < static_cast<int>(instructions_.size())); | 1003 DCHECK(index < static_cast<int>(instructions_.size())); |
978 return instructions_[index]; | 1004 return instructions_[index]; |
979 } | 1005 } |
980 | 1006 |
981 Isolate* isolate() const { return isolate_; } | 1007 Isolate* isolate() const { return isolate_; } |
982 const PointerMapDeque* pointer_maps() const { return &pointer_maps_; } | 1008 const PointerMapDeque* pointer_maps() const { return &pointer_maps_; } |
983 Zone* zone() const { return zone_; } | 1009 Zone* zone() const { return zone_; } |
984 | 1010 |
985 // Used by the instruction selector while adding instructions. | 1011 // Used by the instruction selector while adding instructions. |
986 int AddInstruction(Instruction* instr); | 1012 int AddInstruction(Instruction* instr); |
987 void StartBlock(BasicBlock::RpoNumber rpo); | 1013 void StartBlock(RpoNumber rpo); |
988 void EndBlock(BasicBlock::RpoNumber rpo); | 1014 void EndBlock(RpoNumber rpo); |
989 | 1015 |
990 int AddConstant(int virtual_register, Constant constant) { | 1016 int AddConstant(int virtual_register, Constant constant) { |
991 // TODO(titzer): allow RPO numbers as constants? | 1017 // TODO(titzer): allow RPO numbers as constants? |
992 DCHECK(constant.type() != Constant::kRpoNumber); | 1018 DCHECK(constant.type() != Constant::kRpoNumber); |
993 DCHECK(virtual_register >= 0 && virtual_register < next_virtual_register_); | 1019 DCHECK(virtual_register >= 0 && virtual_register < next_virtual_register_); |
994 DCHECK(constants_.find(virtual_register) == constants_.end()); | 1020 DCHECK(constants_.find(virtual_register) == constants_.end()); |
995 constants_.insert(std::make_pair(virtual_register, constant)); | 1021 constants_.insert(std::make_pair(virtual_register, constant)); |
996 return virtual_register; | 1022 return virtual_register; |
997 } | 1023 } |
998 Constant GetConstant(int virtual_register) const { | 1024 Constant GetConstant(int virtual_register) const { |
(...skipping 24 matching lines...) Expand all Loading... |
1023 | 1049 |
1024 private: | 1050 private: |
1025 explicit StateId(int id) : id_(id) {} | 1051 explicit StateId(int id) : id_(id) {} |
1026 int id_; | 1052 int id_; |
1027 }; | 1053 }; |
1028 | 1054 |
1029 StateId AddFrameStateDescriptor(FrameStateDescriptor* descriptor); | 1055 StateId AddFrameStateDescriptor(FrameStateDescriptor* descriptor); |
1030 FrameStateDescriptor* GetFrameStateDescriptor(StateId deoptimization_id); | 1056 FrameStateDescriptor* GetFrameStateDescriptor(StateId deoptimization_id); |
1031 int GetFrameStateDescriptorCount(); | 1057 int GetFrameStateDescriptorCount(); |
1032 | 1058 |
1033 BasicBlock::RpoNumber InputRpo(Instruction* instr, size_t index) { | 1059 RpoNumber InputRpo(Instruction* instr, size_t index) { |
1034 InstructionOperand* operand = instr->InputAt(index); | 1060 InstructionOperand* operand = instr->InputAt(index); |
1035 Constant constant = operand->IsImmediate() ? GetImmediate(operand->index()) | 1061 Constant constant = operand->IsImmediate() ? GetImmediate(operand->index()) |
1036 : GetConstant(operand->index()); | 1062 : GetConstant(operand->index()); |
1037 return constant.ToRpoNumber(); | 1063 return constant.ToRpoNumber(); |
1038 } | 1064 } |
1039 | 1065 |
1040 private: | 1066 private: |
1041 friend std::ostream& operator<<(std::ostream& os, | 1067 friend std::ostream& operator<<(std::ostream& os, |
1042 const PrintableInstructionSequence& code); | 1068 const PrintableInstructionSequence& code); |
1043 | 1069 |
(...skipping 23 matching lines...) Expand all Loading... |
1067 | 1093 |
1068 | 1094 |
1069 std::ostream& operator<<(std::ostream& os, | 1095 std::ostream& operator<<(std::ostream& os, |
1070 const PrintableInstructionSequence& code); | 1096 const PrintableInstructionSequence& code); |
1071 | 1097 |
1072 } // namespace compiler | 1098 } // namespace compiler |
1073 } // namespace internal | 1099 } // namespace internal |
1074 } // namespace v8 | 1100 } // namespace v8 |
1075 | 1101 |
1076 #endif // V8_COMPILER_INSTRUCTION_H_ | 1102 #endif // V8_COMPILER_INSTRUCTION_H_ |
OLD | NEW |