OLD | NEW |
1 //===- subzero/src/IceInstX86BaseImpl.h - Generic X86 instructions -*- C++ -*=// | 1 //===- subzero/src/IceInstX86BaseImpl.h - Generic X86 instructions -*- 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 720 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
731 } else { | 731 } else { |
732 Address SrcStackAddr = Target->stackVarToAsmOperand(SrcVar); | 732 Address SrcStackAddr = Target->stackVarToAsmOperand(SrcVar); |
733 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, SrcStackAddr); | 733 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, SrcStackAddr); |
734 } | 734 } |
735 } else if (const auto *Mem = llvm::dyn_cast<X86OperandMem>(Src)) { | 735 } else if (const auto *Mem = llvm::dyn_cast<X86OperandMem>(Src)) { |
736 Mem->emitSegmentOverride(Asm); | 736 Mem->emitSegmentOverride(Asm); |
737 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, | 737 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, |
738 Mem->toAsmAddress(Asm, Target, IsLea)); | 738 Mem->toAsmAddress(Asm, Target, IsLea)); |
739 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { | 739 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { |
740 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Imm->getValue())); | 740 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Imm->getValue())); |
| 741 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger64>(Src)) { |
| 742 assert(Traits::Is64Bit); |
| 743 assert(Utils::IsInt(32, Imm->getValue())); |
| 744 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Imm->getValue())); |
741 } else if (const auto *Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) { | 745 } else if (const auto *Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) { |
742 const auto FixupKind = (Reloc->getName().hasStdString() && | 746 const auto FixupKind = (Reloc->getName().hasStdString() && |
743 Reloc->getName().toString() == GlobalOffsetTable) | 747 Reloc->getName().toString() == GlobalOffsetTable) |
744 ? Traits::FK_GotPC | 748 ? Traits::FK_GotPC |
745 : Traits::TargetLowering::getAbsFixup(); | 749 : Traits::TargetLowering::getAbsFixup(); |
746 AssemblerFixup *Fixup = Asm->createFixup(FixupKind, Reloc); | 750 AssemblerFixup *Fixup = Asm->createFixup(FixupKind, Reloc); |
747 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Fixup)); | 751 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Fixup)); |
748 } else if (const auto *Split = llvm::dyn_cast<VariableSplit>(Src)) { | 752 } else if (const auto *Split = llvm::dyn_cast<VariableSplit>(Src)) { |
749 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, Split->toAsmAddress(Func)); | 753 (Asm->*(Emitter.GPRAddr))(Ty, VarReg, Split->toAsmAddress(Func)); |
750 } else { | 754 } else { |
751 llvm_unreachable("Unexpected operand type"); | 755 llvm_unreachable("Unexpected operand type"); |
752 } | 756 } |
753 } | 757 } |
754 | 758 |
755 template <typename TraitsType> | 759 template <typename TraitsType> |
756 void InstImpl<TraitsType>::emitIASAddrOpTyGPR(const Cfg *Func, Type Ty, | 760 void InstImpl<TraitsType>::emitIASAddrOpTyGPR(const Cfg *Func, Type Ty, |
757 const Address &Addr, | 761 const Address &Addr, |
758 const Operand *Src, | 762 const Operand *Src, |
759 const GPREmitterAddrOp &Emitter) { | 763 const GPREmitterAddrOp &Emitter) { |
760 Assembler *Asm = Func->getAssembler<Assembler>(); | 764 Assembler *Asm = Func->getAssembler<Assembler>(); |
761 // Src can only be Reg or AssemblerImmediate. | 765 // Src can only be Reg or AssemblerImmediate. |
762 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) { | 766 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) { |
763 assert(SrcVar->hasReg()); | 767 assert(SrcVar->hasReg()); |
764 GPRRegister SrcReg = Traits::getEncodedGPR(SrcVar->getRegNum()); | 768 GPRRegister SrcReg = Traits::getEncodedGPR(SrcVar->getRegNum()); |
765 (Asm->*(Emitter.AddrGPR))(Ty, Addr, SrcReg); | 769 (Asm->*(Emitter.AddrGPR))(Ty, Addr, SrcReg); |
766 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { | 770 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { |
767 (Asm->*(Emitter.AddrImm))(Ty, Addr, AssemblerImmediate(Imm->getValue())); | 771 (Asm->*(Emitter.AddrImm))(Ty, Addr, AssemblerImmediate(Imm->getValue())); |
| 772 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger64>(Src)) { |
| 773 assert(Traits::Is64Bit); |
| 774 assert(Utils::IsInt(32, Imm->getValue())); |
| 775 (Asm->*(Emitter.AddrImm))(Ty, Addr, AssemblerImmediate(Imm->getValue())); |
768 } else if (const auto *Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) { | 776 } else if (const auto *Reloc = llvm::dyn_cast<ConstantRelocatable>(Src)) { |
769 const auto FixupKind = (Reloc->getName().hasStdString() && | 777 const auto FixupKind = (Reloc->getName().hasStdString() && |
770 Reloc->getName().toString() == GlobalOffsetTable) | 778 Reloc->getName().toString() == GlobalOffsetTable) |
771 ? Traits::FK_GotPC | 779 ? Traits::FK_GotPC |
772 : Traits::TargetLowering::getAbsFixup(); | 780 : Traits::TargetLowering::getAbsFixup(); |
773 AssemblerFixup *Fixup = Asm->createFixup(FixupKind, Reloc); | 781 AssemblerFixup *Fixup = Asm->createFixup(FixupKind, Reloc); |
774 (Asm->*(Emitter.AddrImm))(Ty, Addr, AssemblerImmediate(Fixup)); | 782 (Asm->*(Emitter.AddrImm))(Ty, Addr, AssemblerImmediate(Fixup)); |
775 } else { | 783 } else { |
776 llvm_unreachable("Unexpected operand type"); | 784 llvm_unreachable("Unexpected operand type"); |
777 } | 785 } |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
809 assert(Var->hasReg()); | 817 assert(Var->hasReg()); |
810 // We cheat a little and use GPRRegister even for byte operations. | 818 // We cheat a little and use GPRRegister even for byte operations. |
811 GPRRegister VarReg = Traits::getEncodedGPR(Var->getRegNum()); | 819 GPRRegister VarReg = Traits::getEncodedGPR(Var->getRegNum()); |
812 // Src must be reg == ECX or an Imm8. This is asserted by the assembler. | 820 // Src must be reg == ECX or an Imm8. This is asserted by the assembler. |
813 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) { | 821 if (const auto *SrcVar = llvm::dyn_cast<Variable>(Src)) { |
814 assert(SrcVar->hasReg()); | 822 assert(SrcVar->hasReg()); |
815 GPRRegister SrcReg = Traits::getEncodedGPR(SrcVar->getRegNum()); | 823 GPRRegister SrcReg = Traits::getEncodedGPR(SrcVar->getRegNum()); |
816 (Asm->*(Emitter.GPRGPR))(Ty, VarReg, SrcReg); | 824 (Asm->*(Emitter.GPRGPR))(Ty, VarReg, SrcReg); |
817 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { | 825 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger32>(Src)) { |
818 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Imm->getValue())); | 826 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Imm->getValue())); |
| 827 } else if (const auto *Imm = llvm::dyn_cast<ConstantInteger64>(Src)) { |
| 828 assert(Traits::Is64Bit); |
| 829 assert(Utils::IsInt(32, Imm->getValue())); |
| 830 (Asm->*(Emitter.GPRImm))(Ty, VarReg, AssemblerImmediate(Imm->getValue())); |
819 } else { | 831 } else { |
820 llvm_unreachable("Unexpected operand type"); | 832 llvm_unreachable("Unexpected operand type"); |
821 } | 833 } |
822 } | 834 } |
823 | 835 |
824 template <typename TraitsType> | 836 template <typename TraitsType> |
825 void InstImpl<TraitsType>::emitIASGPRShiftDouble( | 837 void InstImpl<TraitsType>::emitIASGPRShiftDouble( |
826 const Cfg *Func, const Variable *Dest, const Operand *Src1Op, | 838 const Cfg *Func, const Variable *Dest, const Operand *Src1Op, |
827 const Operand *Src2Op, const GPREmitterShiftD &Emitter) { | 839 const Operand *Src2Op, const GPREmitterShiftD &Emitter) { |
828 Assembler *Asm = Func->getAssembler<Assembler>(); | 840 Assembler *Asm = Func->getAssembler<Assembler>(); |
(...skipping 1206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2035 template <typename TraitsType> | 2047 template <typename TraitsType> |
2036 void InstImpl<TraitsType>::InstX86Mov::emit(const Cfg *Func) const { | 2048 void InstImpl<TraitsType>::InstX86Mov::emit(const Cfg *Func) const { |
2037 if (!BuildDefs::dump()) | 2049 if (!BuildDefs::dump()) |
2038 return; | 2050 return; |
2039 Ostream &Str = Func->getContext()->getStrEmit(); | 2051 Ostream &Str = Func->getContext()->getStrEmit(); |
2040 assert(this->getSrcSize() == 1); | 2052 assert(this->getSrcSize() == 1); |
2041 Operand *Src = this->getSrc(0); | 2053 Operand *Src = this->getSrc(0); |
2042 Type SrcTy = Src->getType(); | 2054 Type SrcTy = Src->getType(); |
2043 Type DestTy = this->getDest()->getType(); | 2055 Type DestTy = this->getDest()->getType(); |
2044 if (Traits::Is64Bit && DestTy == IceType_i64 && | 2056 if (Traits::Is64Bit && DestTy == IceType_i64 && |
2045 llvm::isa<ConstantInteger64>(Src)) { | 2057 llvm::isa<ConstantInteger64>(Src) && |
| 2058 !Utils::IsInt(32, llvm::cast<ConstantInteger64>(Src)->getValue())) { |
2046 Str << "\t" | 2059 Str << "\t" |
2047 "movabs" | 2060 "movabs" |
2048 "\t"; | 2061 "\t"; |
2049 } else { | 2062 } else { |
2050 Str << "\t" | 2063 Str << "\t" |
2051 "mov" << (!isScalarFloatingType(DestTy) | 2064 "mov" << (!isScalarFloatingType(DestTy) |
2052 ? this->getWidthString(DestTy) | 2065 ? this->getWidthString(DestTy) |
2053 : Traits::TypeAttributes[DestTy].SdSsString) << "\t"; | 2066 : Traits::TypeAttributes[DestTy].SdSsString) << "\t"; |
2054 } | 2067 } |
2055 // For an integer truncation operation, src is wider than dest. In this case, | 2068 // For an integer truncation operation, src is wider than dest. In this case, |
(...skipping 869 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2925 return; | 2938 return; |
2926 Ostream &Str = Func->getContext()->getStrDump(); | 2939 Ostream &Str = Func->getContext()->getStrDump(); |
2927 Str << "IACA_END"; | 2940 Str << "IACA_END"; |
2928 } | 2941 } |
2929 | 2942 |
2930 } // end of namespace X86NAMESPACE | 2943 } // end of namespace X86NAMESPACE |
2931 | 2944 |
2932 } // end of namespace Ice | 2945 } // end of namespace Ice |
2933 | 2946 |
2934 #endif // SUBZERO_SRC_ICEINSTX86BASEIMPL_H | 2947 #endif // SUBZERO_SRC_ICEINSTX86BASEIMPL_H |
OLD | NEW |