| OLD | NEW |
| 1 //===- subzero/src/IceInstX8632.cpp - X86-32 instruction implementation ---===// | 1 //===- subzero/src/IceInstX8632.cpp - X86-32 instruction implementation ---===// |
| 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 // This file implements the InstX8632 and OperandX8632 classes, | 10 // This file implements the InstX8632 and OperandX8632 classes, |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 43 } TypeX8632Attributes[] = { | 43 } TypeX8632Attributes[] = { |
| 44 #define X(tag, cvt, sdss, width) \ | 44 #define X(tag, cvt, sdss, width) \ |
| 45 { cvt, "" sdss, width } \ | 45 { cvt, "" sdss, width } \ |
| 46 , | 46 , |
| 47 ICETYPEX8632_TABLE | 47 ICETYPEX8632_TABLE |
| 48 #undef X | 48 #undef X |
| 49 }; | 49 }; |
| 50 const size_t TypeX8632AttributesSize = | 50 const size_t TypeX8632AttributesSize = |
| 51 llvm::array_lengthof(TypeX8632Attributes); | 51 llvm::array_lengthof(TypeX8632Attributes); |
| 52 | 52 |
| 53 const char *InstX8632SegmentRegNames[] = { |
| 54 #define X(val, name) \ |
| 55 name, |
| 56 SEG_REGX8632_TABLE |
| 57 #undef X |
| 58 }; |
| 59 const size_t InstX8632SegmentRegNamesSize = |
| 60 llvm::array_lengthof(InstX8632SegmentRegNames); |
| 61 |
| 53 } // end of anonymous namespace | 62 } // end of anonymous namespace |
| 54 | 63 |
| 55 const char *InstX8632::getWidthString(Type Ty) { | 64 const char *InstX8632::getWidthString(Type Ty) { |
| 56 return TypeX8632Attributes[Ty].WidthString; | 65 return TypeX8632Attributes[Ty].WidthString; |
| 57 } | 66 } |
| 58 | 67 |
| 59 OperandX8632Mem::OperandX8632Mem(Cfg *Func, Type Ty, Variable *Base, | 68 OperandX8632Mem::OperandX8632Mem(Cfg *Func, Type Ty, Variable *Base, |
| 60 Constant *Offset, Variable *Index, | 69 Constant *Offset, Variable *Index, |
| 61 uint32_t Shift) | 70 uint16_t Shift, SegmentRegisters SegmentReg) |
| 62 : OperandX8632(kMem, Ty), Base(Base), Offset(Offset), Index(Index), | 71 : OperandX8632(kMem, Ty), Base(Base), Offset(Offset), Index(Index), |
| 63 Shift(Shift) { | 72 Shift(Shift), SegmentReg(SegmentReg) { |
| 64 assert(Shift <= 3); | 73 assert(Shift <= 3); |
| 65 Vars = NULL; | 74 Vars = NULL; |
| 66 NumVars = 0; | 75 NumVars = 0; |
| 67 if (Base) | 76 if (Base) |
| 68 ++NumVars; | 77 ++NumVars; |
| 69 if (Index) | 78 if (Index) |
| 70 ++NumVars; | 79 ++NumVars; |
| 71 if (NumVars) { | 80 if (NumVars) { |
| 72 Vars = Func->allocateArrayOf<Variable *>(NumVars); | 81 Vars = Func->allocateArrayOf<Variable *>(NumVars); |
| 73 SizeT I = 0; | 82 SizeT I = 0; |
| (...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 141 addSource(Src0); | 150 addSource(Src0); |
| 142 addSource(Src1); | 151 addSource(Src1); |
| 143 } | 152 } |
| 144 | 153 |
| 145 InstX8632Ucomiss::InstX8632Ucomiss(Cfg *Func, Operand *Src0, Operand *Src1) | 154 InstX8632Ucomiss::InstX8632Ucomiss(Cfg *Func, Operand *Src0, Operand *Src1) |
| 146 : InstX8632(Func, InstX8632::Ucomiss, 2, NULL) { | 155 : InstX8632(Func, InstX8632::Ucomiss, 2, NULL) { |
| 147 addSource(Src0); | 156 addSource(Src0); |
| 148 addSource(Src1); | 157 addSource(Src1); |
| 149 } | 158 } |
| 150 | 159 |
| 160 InstX8632UD2::InstX8632UD2(Cfg *Func) |
| 161 : InstX8632(Func, InstX8632::UD2, 0, NULL) {} |
| 162 |
| 151 InstX8632Test::InstX8632Test(Cfg *Func, Operand *Src1, Operand *Src2) | 163 InstX8632Test::InstX8632Test(Cfg *Func, Operand *Src1, Operand *Src2) |
| 152 : InstX8632(Func, InstX8632::Test, 2, NULL) { | 164 : InstX8632(Func, InstX8632::Test, 2, NULL) { |
| 153 addSource(Src1); | 165 addSource(Src1); |
| 154 addSource(Src2); | 166 addSource(Src2); |
| 155 } | 167 } |
| 156 | 168 |
| 157 InstX8632Store::InstX8632Store(Cfg *Func, Operand *Value, OperandX8632 *Mem) | 169 InstX8632Store::InstX8632Store(Cfg *Func, Operand *Value, OperandX8632 *Mem) |
| 158 : InstX8632(Func, InstX8632::Store, 2, NULL) { | 170 : InstX8632(Func, InstX8632::Store, 2, NULL) { |
| 159 addSource(Value); | 171 addSource(Value); |
| 160 addSource(Mem); | 172 addSource(Mem); |
| (...skipping 357 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 518 getSrc(1)->emit(Func); | 530 getSrc(1)->emit(Func); |
| 519 Str << "\n"; | 531 Str << "\n"; |
| 520 } | 532 } |
| 521 | 533 |
| 522 void InstX8632Ucomiss::dump(const Cfg *Func) const { | 534 void InstX8632Ucomiss::dump(const Cfg *Func) const { |
| 523 Ostream &Str = Func->getContext()->getStrDump(); | 535 Ostream &Str = Func->getContext()->getStrDump(); |
| 524 Str << "ucomiss." << getSrc(0)->getType() << " "; | 536 Str << "ucomiss." << getSrc(0)->getType() << " "; |
| 525 dumpSources(Func); | 537 dumpSources(Func); |
| 526 } | 538 } |
| 527 | 539 |
| 540 void InstX8632UD2::emit(const Cfg *Func) const { |
| 541 Ostream &Str = Func->getContext()->getStrEmit(); |
| 542 assert(getSrcSize() == 0); |
| 543 Str << "\tud2\n"; |
| 544 } |
| 545 |
| 546 void InstX8632UD2::dump(const Cfg *Func) const { |
| 547 Ostream &Str = Func->getContext()->getStrDump(); |
| 548 Str << "ud2\n"; |
| 549 } |
| 550 |
| 528 void InstX8632Test::emit(const Cfg *Func) const { | 551 void InstX8632Test::emit(const Cfg *Func) const { |
| 529 Ostream &Str = Func->getContext()->getStrEmit(); | 552 Ostream &Str = Func->getContext()->getStrEmit(); |
| 530 assert(getSrcSize() == 2); | 553 assert(getSrcSize() == 2); |
| 531 Str << "\ttest\t"; | 554 Str << "\ttest\t"; |
| 532 getSrc(0)->emit(Func); | 555 getSrc(0)->emit(Func); |
| 533 Str << ", "; | 556 Str << ", "; |
| 534 getSrc(1)->emit(Func); | 557 getSrc(1)->emit(Func); |
| 535 Str << "\n"; | 558 Str << "\n"; |
| 536 } | 559 } |
| 537 | 560 |
| (...skipping 213 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 751 } | 774 } |
| 752 | 775 |
| 753 void OperandX8632::dump(const Cfg *Func) const { | 776 void OperandX8632::dump(const Cfg *Func) const { |
| 754 Ostream &Str = Func->getContext()->getStrDump(); | 777 Ostream &Str = Func->getContext()->getStrDump(); |
| 755 Str << "<OperandX8632>"; | 778 Str << "<OperandX8632>"; |
| 756 } | 779 } |
| 757 | 780 |
| 758 void OperandX8632Mem::emit(const Cfg *Func) const { | 781 void OperandX8632Mem::emit(const Cfg *Func) const { |
| 759 Ostream &Str = Func->getContext()->getStrEmit(); | 782 Ostream &Str = Func->getContext()->getStrEmit(); |
| 760 Str << TypeX8632Attributes[getType()].WidthString << " "; | 783 Str << TypeX8632Attributes[getType()].WidthString << " "; |
| 784 if (SegmentReg != DefaultSegment) { |
| 785 assert(SegmentReg >= 0 && |
| 786 static_cast<size_t>(SegmentReg) < InstX8632SegmentRegNamesSize); |
| 787 Str << InstX8632SegmentRegNames[SegmentReg] << ":"; |
| 788 } |
| 761 // TODO: The following is an almost verbatim paste of dump(). | 789 // TODO: The following is an almost verbatim paste of dump(). |
| 762 bool Dumped = false; | 790 bool Dumped = false; |
| 763 Str << "["; | 791 Str << "["; |
| 764 if (Base) { | 792 if (Base) { |
| 765 Base->emit(Func); | 793 Base->emit(Func); |
| 766 Dumped = true; | 794 Dumped = true; |
| 767 } | 795 } |
| 768 if (Index) { | 796 if (Index) { |
| 769 assert(Base); | 797 assert(Base); |
| 770 Str << "+"; | 798 Str << "+"; |
| 771 if (Shift > 0) | 799 if (Shift > 0) |
| 772 Str << (1u << Shift) << "*"; | 800 Str << (1u << Shift) << "*"; |
| 773 Index->emit(Func); | 801 Index->emit(Func); |
| 774 Dumped = true; | 802 Dumped = true; |
| 775 } | 803 } |
| 776 // Pretty-print the Offset. | 804 // Pretty-print the Offset. |
| 777 bool OffsetIsZero = false; | 805 bool OffsetIsZero = false; |
| 778 bool OffsetIsNegative = false; | 806 bool OffsetIsNegative = false; |
| 779 if (Offset == NULL) { | 807 if (Offset == NULL) { |
| 780 OffsetIsZero = true; | 808 OffsetIsZero = true; |
| 781 } else if (ConstantInteger *CI = llvm::dyn_cast<ConstantInteger>(Offset)) { | 809 } else if (ConstantInteger *CI = llvm::dyn_cast<ConstantInteger>(Offset)) { |
| 782 OffsetIsZero = (CI->getValue() == 0); | 810 OffsetIsZero = (CI->getValue() == 0); |
| 783 OffsetIsNegative = (static_cast<int64_t>(CI->getValue()) < 0); | 811 OffsetIsNegative = (static_cast<int64_t>(CI->getValue()) < 0); |
| 784 } | 812 } |
| 785 if (!OffsetIsZero) { // Suppress if Offset is known to be 0 | 813 if (Dumped) { |
| 786 if (Dumped) { | 814 if (!OffsetIsZero) { // Suppress if Offset is known to be 0 |
| 787 if (!OffsetIsNegative) // Suppress if Offset is known to be negative | 815 if (!OffsetIsNegative) // Suppress if Offset is known to be negative |
| 788 Str << "+"; | 816 Str << "+"; |
| 817 Offset->emit(Func); |
| 789 } | 818 } |
| 819 } else { |
| 820 // There is only the offset. |
| 790 Offset->emit(Func); | 821 Offset->emit(Func); |
| 791 } | 822 } |
| 792 Str << "]"; | 823 Str << "]"; |
| 793 } | 824 } |
| 794 | 825 |
| 795 void OperandX8632Mem::dump(const Cfg *Func) const { | 826 void OperandX8632Mem::dump(const Cfg *Func) const { |
| 796 Ostream &Str = Func->getContext()->getStrDump(); | 827 Ostream &Str = Func->getContext()->getStrDump(); |
| 828 if (SegmentReg != DefaultSegment) { |
| 829 assert(SegmentReg >= 0 && |
| 830 static_cast<size_t>(SegmentReg) < InstX8632SegmentRegNamesSize); |
| 831 Str << InstX8632SegmentRegNames[SegmentReg] << ":"; |
| 832 } |
| 797 bool Dumped = false; | 833 bool Dumped = false; |
| 798 Str << "["; | 834 Str << "["; |
| 799 if (Base) { | 835 if (Base) { |
| 800 Base->dump(Func); | 836 Base->dump(Func); |
| 801 Dumped = true; | 837 Dumped = true; |
| 802 } | 838 } |
| 803 if (Index) { | 839 if (Index) { |
| 804 assert(Base); | 840 assert(Base); |
| 805 Str << "+"; | 841 Str << "+"; |
| 806 if (Shift > 0) | 842 if (Shift > 0) |
| 807 Str << (1u << Shift) << "*"; | 843 Str << (1u << Shift) << "*"; |
| 808 Index->dump(Func); | 844 Index->dump(Func); |
| 809 Dumped = true; | 845 Dumped = true; |
| 810 } | 846 } |
| 811 // Pretty-print the Offset. | 847 // Pretty-print the Offset. |
| 812 bool OffsetIsZero = false; | 848 bool OffsetIsZero = false; |
| 813 bool OffsetIsNegative = false; | 849 bool OffsetIsNegative = false; |
| 814 if (Offset == NULL) { | 850 if (Offset == NULL) { |
| 815 OffsetIsZero = true; | 851 OffsetIsZero = true; |
| 816 } else if (ConstantInteger *CI = llvm::dyn_cast<ConstantInteger>(Offset)) { | 852 } else if (ConstantInteger *CI = llvm::dyn_cast<ConstantInteger>(Offset)) { |
| 817 OffsetIsZero = (CI->getValue() == 0); | 853 OffsetIsZero = (CI->getValue() == 0); |
| 818 OffsetIsNegative = (static_cast<int64_t>(CI->getValue()) < 0); | 854 OffsetIsNegative = (static_cast<int64_t>(CI->getValue()) < 0); |
| 819 } | 855 } |
| 820 if (!OffsetIsZero) { // Suppress if Offset is known to be 0 | 856 if (Dumped) { |
| 821 if (Dumped) { | 857 if (!OffsetIsZero) { // Suppress if Offset is known to be 0 |
| 822 if (!OffsetIsNegative) // Suppress if Offset is known to be negative | 858 if (!OffsetIsNegative) // Suppress if Offset is known to be negative |
| 823 Str << "+"; | 859 Str << "+"; |
| 860 Offset->dump(Func); |
| 824 } | 861 } |
| 862 } else { |
| 863 // There is only the offset. |
| 825 Offset->dump(Func); | 864 Offset->dump(Func); |
| 826 } | 865 } |
| 827 Str << "]"; | 866 Str << "]"; |
| 828 } | 867 } |
| 829 | 868 |
| 830 void VariableSplit::emit(const Cfg *Func) const { | 869 void VariableSplit::emit(const Cfg *Func) const { |
| 831 Ostream &Str = Func->getContext()->getStrEmit(); | 870 Ostream &Str = Func->getContext()->getStrEmit(); |
| 832 assert(Var->getLocalUseNode() == NULL || | 871 assert(Var->getLocalUseNode() == NULL || |
| 833 Var->getLocalUseNode() == Func->getCurrentNode()); | 872 Var->getLocalUseNode() == Func->getCurrentNode()); |
| 834 assert(!Var->hasReg()); | 873 assert(!Var->hasReg()); |
| (...skipping 25 matching lines...) Expand all Loading... |
| 860 default: | 899 default: |
| 861 Str << "???"; | 900 Str << "???"; |
| 862 break; | 901 break; |
| 863 } | 902 } |
| 864 Str << "("; | 903 Str << "("; |
| 865 Var->dump(Func); | 904 Var->dump(Func); |
| 866 Str << ")"; | 905 Str << ")"; |
| 867 } | 906 } |
| 868 | 907 |
| 869 } // end of namespace Ice | 908 } // end of namespace Ice |
| OLD | NEW |