1 //===-- MipsABIFlagsSection.h - Mips ELF ABI Flags Section -----*- C++ -*--===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 10 #ifndef LLVM_LIB_TARGET_MIPS_MCTARGETDESC_MIPSABIFLAGSSECTION_H 11 #define LLVM_LIB_TARGET_MIPS_MCTARGETDESC_MIPSABIFLAGSSECTION_H 12 13 #include "llvm/MC/MCStreamer.h" 14 #include "llvm/Support/ErrorHandling.h" 15 #include "llvm/Support/MipsABIFlags.h" 16 17 namespace llvm { 18 19 class MCStreamer; 20 21 struct MipsABIFlagsSection { 22 // Internal representation of the fp_abi related values used in .module. 23 enum class FpABIKind { ANY, XX, S32, S64, SOFT }; 24 25 // Version of flags structure. 26 uint16_t Version; 27 // The level of the ISA: 1-5, 32, 64. 28 uint8_t ISALevel; 29 // The revision of ISA: 0 for MIPS V and below, 1-n otherwise. 30 uint8_t ISARevision; 31 // The size of general purpose registers. 32 Mips::AFL_REG GPRSize; 33 // The size of co-processor 1 registers. 34 Mips::AFL_REG CPR1Size; 35 // The size of co-processor 2 registers. 36 Mips::AFL_REG CPR2Size; 37 // Processor-specific extension. 38 uint32_t ISAExtensionSet; 39 // Mask of ASEs used. 40 uint32_t ASESet; 41 42 bool OddSPReg; 43 44 bool Is32BitABI; 45 46 protected: 47 // The floating-point ABI. 48 FpABIKind FpABI; 49 50 public: MipsABIFlagsSectionMipsABIFlagsSection51 MipsABIFlagsSection() 52 : Version(0), ISALevel(0), ISARevision(0), GPRSize(Mips::AFL_REG_NONE), 53 CPR1Size(Mips::AFL_REG_NONE), CPR2Size(Mips::AFL_REG_NONE), 54 ISAExtensionSet(0), ASESet(0), OddSPReg(false), Is32BitABI(false), 55 FpABI(FpABIKind::ANY) {} 56 getVersionValueMipsABIFlagsSection57 uint16_t getVersionValue() { return (uint16_t)Version; } getISALevelValueMipsABIFlagsSection58 uint8_t getISALevelValue() { return (uint8_t)ISALevel; } getISARevisionValueMipsABIFlagsSection59 uint8_t getISARevisionValue() { return (uint8_t)ISARevision; } getGPRSizeValueMipsABIFlagsSection60 uint8_t getGPRSizeValue() { return (uint8_t)GPRSize; } 61 uint8_t getCPR1SizeValue(); getCPR2SizeValueMipsABIFlagsSection62 uint8_t getCPR2SizeValue() { return (uint8_t)CPR2Size; } 63 uint8_t getFpABIValue(); getISAExtensionSetValueMipsABIFlagsSection64 uint32_t getISAExtensionSetValue() { return (uint32_t)ISAExtensionSet; } getASESetValueMipsABIFlagsSection65 uint32_t getASESetValue() { return (uint32_t)ASESet; } 66 getFlags1ValueMipsABIFlagsSection67 uint32_t getFlags1Value() { 68 uint32_t Value = 0; 69 70 if (OddSPReg) 71 Value |= (uint32_t)Mips::AFL_FLAGS1_ODDSPREG; 72 73 return Value; 74 } 75 getFlags2ValueMipsABIFlagsSection76 uint32_t getFlags2Value() { return 0; } 77 getFpABIMipsABIFlagsSection78 FpABIKind getFpABI() { return FpABI; } setFpABIMipsABIFlagsSection79 void setFpABI(FpABIKind Value, bool IsABI32Bit) { 80 FpABI = Value; 81 Is32BitABI = IsABI32Bit; 82 } 83 StringRef getFpABIString(FpABIKind Value); 84 85 template <class PredicateLibrary> setISALevelAndRevisionFromPredicatesMipsABIFlagsSection86 void setISALevelAndRevisionFromPredicates(const PredicateLibrary &P) { 87 if (P.hasMips64()) { 88 ISALevel = 64; 89 if (P.hasMips64r6()) 90 ISARevision = 6; 91 else if (P.hasMips64r5()) 92 ISARevision = 5; 93 else if (P.hasMips64r3()) 94 ISARevision = 3; 95 else if (P.hasMips64r2()) 96 ISARevision = 2; 97 else 98 ISARevision = 1; 99 } else if (P.hasMips32()) { 100 ISALevel = 32; 101 if (P.hasMips32r6()) 102 ISARevision = 6; 103 else if (P.hasMips32r5()) 104 ISARevision = 5; 105 else if (P.hasMips32r3()) 106 ISARevision = 3; 107 else if (P.hasMips32r2()) 108 ISARevision = 2; 109 else 110 ISARevision = 1; 111 } else { 112 ISARevision = 0; 113 if (P.hasMips5()) 114 ISALevel = 5; 115 else if (P.hasMips4()) 116 ISALevel = 4; 117 else if (P.hasMips3()) 118 ISALevel = 3; 119 else if (P.hasMips2()) 120 ISALevel = 2; 121 else if (P.hasMips1()) 122 ISALevel = 1; 123 else 124 llvm_unreachable("Unknown ISA level!"); 125 } 126 } 127 128 template <class PredicateLibrary> setGPRSizeFromPredicatesMipsABIFlagsSection129 void setGPRSizeFromPredicates(const PredicateLibrary &P) { 130 GPRSize = P.isGP64bit() ? Mips::AFL_REG_64 : Mips::AFL_REG_32; 131 } 132 133 template <class PredicateLibrary> setCPR1SizeFromPredicatesMipsABIFlagsSection134 void setCPR1SizeFromPredicates(const PredicateLibrary &P) { 135 if (P.useSoftFloat()) 136 CPR1Size = Mips::AFL_REG_NONE; 137 else if (P.hasMSA()) 138 CPR1Size = Mips::AFL_REG_128; 139 else 140 CPR1Size = P.isFP64bit() ? Mips::AFL_REG_64 : Mips::AFL_REG_32; 141 } 142 143 template <class PredicateLibrary> setASESetFromPredicatesMipsABIFlagsSection144 void setASESetFromPredicates(const PredicateLibrary &P) { 145 ASESet = 0; 146 if (P.hasDSP()) 147 ASESet |= Mips::AFL_ASE_DSP; 148 if (P.hasDSPR2()) 149 ASESet |= Mips::AFL_ASE_DSPR2; 150 if (P.hasMSA()) 151 ASESet |= Mips::AFL_ASE_MSA; 152 if (P.inMicroMipsMode()) 153 ASESet |= Mips::AFL_ASE_MICROMIPS; 154 if (P.inMips16Mode()) 155 ASESet |= Mips::AFL_ASE_MIPS16; 156 } 157 158 template <class PredicateLibrary> setFpAbiFromPredicatesMipsABIFlagsSection159 void setFpAbiFromPredicates(const PredicateLibrary &P) { 160 Is32BitABI = P.isABI_O32(); 161 162 FpABI = FpABIKind::ANY; 163 if (P.useSoftFloat()) 164 FpABI = FpABIKind::SOFT; 165 else if (P.isABI_N32() || P.isABI_N64()) 166 FpABI = FpABIKind::S64; 167 else if (P.isABI_O32()) { 168 if (P.isABI_FPXX()) 169 FpABI = FpABIKind::XX; 170 else if (P.isFP64bit()) 171 FpABI = FpABIKind::S64; 172 else 173 FpABI = FpABIKind::S32; 174 } 175 } 176 177 template <class PredicateLibrary> setAllFromPredicatesMipsABIFlagsSection178 void setAllFromPredicates(const PredicateLibrary &P) { 179 setISALevelAndRevisionFromPredicates(P); 180 setGPRSizeFromPredicates(P); 181 setCPR1SizeFromPredicates(P); 182 setASESetFromPredicates(P); 183 setFpAbiFromPredicates(P); 184 OddSPReg = P.useOddSPReg(); 185 } 186 }; 187 188 MCStreamer &operator<<(MCStreamer &OS, MipsABIFlagsSection &ABIFlagsSection); 189 } 190 191 #endif 192