OLD | NEW |
1 //===- subzero/src/IceTargetLoweringX8664Traits.h - x86-64 traits -*- C++ -*-=// | 1 //===- subzero/src/IceTargetLoweringX8664Traits.h - x86-64 traits -*- C++ -*-=// |
2 // | 2 // |
3 // The Subzero Code Generator | 3 // The Subzero Code Generator |
4 // | 4 // |
5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
7 // | 7 // |
8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
9 /// | 9 /// |
10 /// \file | 10 /// \file |
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
64 using ByteRegister = ::Ice::RegX8664::ByteRegister; | 64 using ByteRegister = ::Ice::RegX8664::ByteRegister; |
65 using XmmRegister = ::Ice::RegX8664::XmmRegister; | 65 using XmmRegister = ::Ice::RegX8664::XmmRegister; |
66 | 66 |
67 using Cond = ::Ice::CondX8664; | 67 using Cond = ::Ice::CondX8664; |
68 | 68 |
69 using RegisterSet = ::Ice::RegX8664; | 69 using RegisterSet = ::Ice::RegX8664; |
70 static const SizeT StackPtr = RegX8664::Reg_rsp; | 70 static const SizeT StackPtr = RegX8664::Reg_rsp; |
71 static const SizeT FramePtr = RegX8664::Reg_rbp; | 71 static const SizeT FramePtr = RegX8664::Reg_rbp; |
72 static const GPRRegister Encoded_Reg_Accumulator = RegX8664::Encoded_Reg_eax; | 72 static const GPRRegister Encoded_Reg_Accumulator = RegX8664::Encoded_Reg_eax; |
73 static const GPRRegister Encoded_Reg_Counter = RegX8664::Encoded_Reg_ecx; | 73 static const GPRRegister Encoded_Reg_Counter = RegX8664::Encoded_Reg_ecx; |
74 static const FixupKind PcRelFixup = llvm::ELF::R_X86_64_PC32; | 74 static constexpr FixupKind FK_PcRel = llvm::ELF::R_X86_64_PC32; |
75 static const FixupKind RelFixup = llvm::ELF::R_X86_64_32; | 75 static constexpr FixupKind FK_Abs = llvm::ELF::R_X86_64_32; |
| 76 static constexpr FixupKind FK_Gotoff = llvm::ELF::R_X86_64_GOTOFF64; |
| 77 static constexpr FixupKind FK_GotPC = llvm::ELF::R_X86_64_GOTPC32; |
76 | 78 |
77 class Operand { | 79 class Operand { |
78 public: | 80 public: |
79 enum RexBits { | 81 enum RexBits { |
80 RexNone = 0x00, | 82 RexNone = 0x00, |
81 RexBase = 0x40, | 83 RexBase = 0x40, |
82 RexW = RexBase | (1 << 3), | 84 RexW = RexBase | (1 << 3), |
83 RexR = RexBase | (1 << 2), | 85 RexR = RexBase | (1 << 2), |
84 RexX = RexBase | (1 << 1), | 86 RexX = RexBase | (1 << 1), |
85 RexB = RexBase | (1 << 0), | 87 RexB = RexBase | (1 << 0), |
(...skipping 177 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
263 SetSIB(Scale, RegX8664::Encoded_Reg_esp, RegX8664::Encoded_Reg_ebp); | 265 SetSIB(Scale, RegX8664::Encoded_Reg_esp, RegX8664::Encoded_Reg_ebp); |
264 // Use the Offset in the displacement for now. If we decide to process | 266 // Use the Offset in the displacement for now. If we decide to process |
265 // fixups later, we'll need to patch up the emitted displacement. | 267 // fixups later, we'll need to patch up the emitted displacement. |
266 SetDisp32(Offset); | 268 SetDisp32(Offset); |
267 if (Fixup) | 269 if (Fixup) |
268 SetFixup(Fixup); | 270 SetFixup(Fixup); |
269 } | 271 } |
270 | 272 |
271 static Address ofConstPool(Assembler *Asm, const Constant *Imm) { | 273 static Address ofConstPool(Assembler *Asm, const Constant *Imm) { |
272 // TODO(jpp): ??? | 274 // TODO(jpp): ??? |
273 AssemblerFixup *Fixup = Asm->createFixup(RelFixup, Imm); | 275 AssemblerFixup *Fixup = Asm->createFixup(FK_Abs, Imm); |
274 const RelocOffsetT Offset = 4; | 276 const RelocOffsetT Offset = 4; |
275 return Address(Offset, Fixup); | 277 return Address(Offset, Fixup); |
276 } | 278 } |
277 }; | 279 }; |
278 | 280 |
279 //---------------------------------------------------------------------------- | 281 //---------------------------------------------------------------------------- |
280 // __ ______ __ __ ______ ______ __ __ __ ______ | 282 // __ ______ __ __ ______ ______ __ __ __ ______ |
281 // /\ \ /\ __ \/\ \ _ \ \/\ ___\/\ == \/\ \/\ "-.\ \/\ ___\ | 283 // /\ \ /\ __ \/\ \ _ \ \/\ ___\/\ == \/\ \/\ "-.\ \/\ ___\ |
282 // \ \ \___\ \ \/\ \ \ \/ ".\ \ \ __\\ \ __<\ \ \ \ \-. \ \ \__ \ | 284 // \ \ \___\ \ \/\ \ \ \/ ".\ \ \ __\\ \ __<\ \ \ \ \-. \ \ \__ \ |
283 // \ \_____\ \_____\ \__/".~\_\ \_____\ \_\ \_\ \_\ \_\\"\_\ \_____\ | 285 // \ \_____\ \_____\ \__/".~\_\ \_____\ \_\ \_\ \_\ \_\\"\_\ \_____\ |
(...skipping 489 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
773 class X86OperandMem : public X86Operand { | 775 class X86OperandMem : public X86Operand { |
774 X86OperandMem() = delete; | 776 X86OperandMem() = delete; |
775 X86OperandMem(const X86OperandMem &) = delete; | 777 X86OperandMem(const X86OperandMem &) = delete; |
776 X86OperandMem &operator=(const X86OperandMem &) = delete; | 778 X86OperandMem &operator=(const X86OperandMem &) = delete; |
777 | 779 |
778 public: | 780 public: |
779 enum SegmentRegisters { DefaultSegment = -1, SegReg_NUM }; | 781 enum SegmentRegisters { DefaultSegment = -1, SegReg_NUM }; |
780 static X86OperandMem * | 782 static X86OperandMem * |
781 create(Cfg *Func, Type Ty, Variable *Base, Constant *Offset, | 783 create(Cfg *Func, Type Ty, Variable *Base, Constant *Offset, |
782 Variable *Index = nullptr, uint16_t Shift = 0, | 784 Variable *Index = nullptr, uint16_t Shift = 0, |
783 SegmentRegisters SegmentRegister = DefaultSegment) { | 785 SegmentRegisters SegmentRegister = DefaultSegment, |
| 786 bool IsPIC = false) { |
784 assert(SegmentRegister == DefaultSegment); | 787 assert(SegmentRegister == DefaultSegment); |
785 (void)SegmentRegister; | 788 (void)SegmentRegister; |
786 return new (Func->allocate<X86OperandMem>()) | 789 return new (Func->allocate<X86OperandMem>()) |
787 X86OperandMem(Func, Ty, Base, Offset, Index, Shift); | 790 X86OperandMem(Func, Ty, Base, Offset, Index, Shift, IsPIC); |
788 } | 791 } |
789 Variable *getBase() const { return Base; } | 792 Variable *getBase() const { return Base; } |
790 Constant *getOffset() const { return Offset; } | 793 Constant *getOffset() const { return Offset; } |
791 Variable *getIndex() const { return Index; } | 794 Variable *getIndex() const { return Index; } |
792 uint16_t getShift() const { return Shift; } | 795 uint16_t getShift() const { return Shift; } |
793 SegmentRegisters getSegmentRegister() const { return DefaultSegment; } | 796 SegmentRegisters getSegmentRegister() const { return DefaultSegment; } |
794 void emitSegmentOverride(Assembler *) const {} | 797 void emitSegmentOverride(Assembler *) const {} |
| 798 void setIsPIC() { IsPIC = true; } |
| 799 bool getIsPIC() const { return IsPIC; } |
795 Address toAsmAddress(Assembler *Asm, | 800 Address toAsmAddress(Assembler *Asm, |
796 const Ice::TargetLowering *Target) const; | 801 const Ice::TargetLowering *Target) const; |
797 | 802 |
798 void emit(const Cfg *Func) const override; | 803 void emit(const Cfg *Func) const override; |
799 using X86Operand::dump; | 804 using X86Operand::dump; |
800 void dump(const Cfg *Func, Ostream &Str) const override; | 805 void dump(const Cfg *Func, Ostream &Str) const override; |
801 | 806 |
802 static bool classof(const Operand *Operand) { | 807 static bool classof(const Operand *Operand) { |
803 return Operand->getKind() == static_cast<OperandKind>(kMem); | 808 return Operand->getKind() == static_cast<OperandKind>(kMem); |
804 } | 809 } |
805 | 810 |
806 void setRandomized(bool R) { Randomized = R; } | 811 void setRandomized(bool R) { Randomized = R; } |
807 | 812 |
808 bool getRandomized() const { return Randomized; } | 813 bool getRandomized() const { return Randomized; } |
809 | 814 |
810 private: | 815 private: |
811 X86OperandMem(Cfg *Func, Type Ty, Variable *Base, Constant *Offset, | 816 X86OperandMem(Cfg *Func, Type Ty, Variable *Base, Constant *Offset, |
812 Variable *Index, uint16_t Shift); | 817 Variable *Index, uint16_t Shift, bool IsPIC); |
813 | 818 |
814 Variable *Base; | 819 Variable *Base; |
815 Constant *Offset; | 820 Constant *Offset; |
816 Variable *Index; | 821 Variable *Index; |
817 uint16_t Shift; | 822 uint16_t Shift; |
| 823 bool IsPIC; |
818 /// A flag to show if this memory operand is a randomized one. Randomized | 824 /// A flag to show if this memory operand is a randomized one. Randomized |
819 /// memory operands are generated in | 825 /// memory operands are generated in |
820 /// TargetX86Base::randomizeOrPoolImmediate() | 826 /// TargetX86Base::randomizeOrPoolImmediate() |
821 bool Randomized = false; | 827 bool Randomized = false; |
822 }; | 828 }; |
823 | 829 |
824 /// VariableSplit is a way to treat an f64 memory location as a pair of i32 | 830 /// VariableSplit is a way to treat an f64 memory location as a pair of i32 |
825 /// locations (Low and High). This is needed for some cases of the Bitcast | 831 /// locations (Low and High). This is needed for some cases of the Bitcast |
826 /// instruction. Since it's not possible for integer registers to access the | 832 /// instruction. Since it's not possible for integer registers to access the |
827 /// XMM registers and vice versa, the lowering forces the f64 to be spilled to | 833 /// XMM registers and vice versa, the lowering forces the f64 to be spilled to |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
917 | 923 |
918 } // end of namespace X86Internal | 924 } // end of namespace X86Internal |
919 | 925 |
920 namespace X8664 { | 926 namespace X8664 { |
921 using Traits = ::Ice::X86Internal::MachineTraits<TargetX8664>; | 927 using Traits = ::Ice::X86Internal::MachineTraits<TargetX8664>; |
922 } // end of namespace X8664 | 928 } // end of namespace X8664 |
923 | 929 |
924 } // end of namespace Ice | 930 } // end of namespace Ice |
925 | 931 |
926 #endif // SUBZERO_SRC_ICETARGETLOWERINGX8664TRAITS_H | 932 #endif // SUBZERO_SRC_ICETARGETLOWERINGX8664TRAITS_H |
OLD | NEW |