1 //===--------------------- PredicateExpander.cpp --------------------------===// 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 /// \file 10 /// Functionalities used by the Tablegen backends to expand machine predicates. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "PredicateExpander.h" 15 16 namespace llvm { 17 18 void PredicateExpander::expandTrue(formatted_raw_ostream &OS) { OS << "true"; } 19 void PredicateExpander::expandFalse(formatted_raw_ostream &OS) { 20 OS << "false"; 21 } 22 23 void PredicateExpander::expandCheckImmOperand(formatted_raw_ostream &OS, 24 int OpIndex, int ImmVal) { 25 OS << "MI" << (isByRef() ? "." : "->") << "getOperand(" << OpIndex 26 << ").getImm() " << (shouldNegate() ? "!= " : "== ") << ImmVal; 27 } 28 29 void PredicateExpander::expandCheckImmOperand(formatted_raw_ostream &OS, 30 int OpIndex, StringRef ImmVal) { 31 OS << "MI" << (isByRef() ? "." : "->") << "getOperand(" << OpIndex 32 << ").getImm() " << (shouldNegate() ? "!= " : "== ") << ImmVal; 33 } 34 35 void PredicateExpander::expandCheckRegOperand(formatted_raw_ostream &OS, 36 int OpIndex, const Record *Reg) { 37 assert(Reg->isSubClassOf("Register") && "Expected a register Record!"); 38 39 OS << "MI" << (isByRef() ? "." : "->") << "getOperand(" << OpIndex 40 << ").getReg() " << (shouldNegate() ? "!= " : "== "); 41 const StringRef Str = Reg->getValueAsString("Namespace"); 42 if (!Str.empty()) 43 OS << Str << "::"; 44 OS << Reg->getName(); 45 } 46 47 void PredicateExpander::expandCheckInvalidRegOperand(formatted_raw_ostream &OS, 48 int OpIndex) { 49 OS << "MI" << (isByRef() ? "." : "->") << "getOperand(" << OpIndex 50 << ").getReg() " << (shouldNegate() ? "!= " : "== ") << "0"; 51 } 52 53 void PredicateExpander::expandCheckSameRegOperand(formatted_raw_ostream &OS, 54 int First, int Second) { 55 OS << "MI" << (isByRef() ? "." : "->") << "getOperand(" << First 56 << ").getReg() " << (shouldNegate() ? "!=" : "==") << " MI" 57 << (isByRef() ? "." : "->") << "getOperand(" << Second << ").getReg()"; 58 } 59 60 void PredicateExpander::expandCheckNumOperands(formatted_raw_ostream &OS, 61 int NumOps) { 62 OS << "MI" << (isByRef() ? "." : "->") << "getNumOperands() " 63 << (shouldNegate() ? "!= " : "== ") << NumOps; 64 } 65 66 void PredicateExpander::expandCheckOpcode(formatted_raw_ostream &OS, 67 const Record *Inst) { 68 OS << "MI" << (isByRef() ? "." : "->") << "getOpcode() " 69 << (shouldNegate() ? "!= " : "== ") << Inst->getValueAsString("Namespace") 70 << "::" << Inst->getName(); 71 } 72 73 void PredicateExpander::expandCheckOpcode(formatted_raw_ostream &OS, 74 const RecVec &Opcodes) { 75 assert(!Opcodes.empty() && "Expected at least one opcode to check!"); 76 bool First = true; 77 78 if (Opcodes.size() == 1) { 79 OS << "( "; 80 expandCheckOpcode(OS, Opcodes[0]); 81 OS << " )"; 82 return; 83 } 84 85 OS << '('; 86 increaseIndentLevel(); 87 for (const Record *Rec : Opcodes) { 88 OS << '\n'; 89 OS.PadToColumn(getIndentLevel() * 2); 90 if (!First) 91 OS << (shouldNegate() ? "&& " : "|| "); 92 93 expandCheckOpcode(OS, Rec); 94 First = false; 95 } 96 97 OS << '\n'; 98 decreaseIndentLevel(); 99 OS.PadToColumn(getIndentLevel() * 2); 100 OS << ')'; 101 } 102 103 void PredicateExpander::expandCheckPseudo(formatted_raw_ostream &OS, 104 const RecVec &Opcodes) { 105 if (shouldExpandForMC()) 106 expandFalse(OS); 107 else 108 expandCheckOpcode(OS, Opcodes); 109 } 110 111 void PredicateExpander::expandPredicateSequence(formatted_raw_ostream &OS, 112 const RecVec &Sequence, 113 bool IsCheckAll) { 114 assert(!Sequence.empty() && "Found an invalid empty predicate set!"); 115 if (Sequence.size() == 1) 116 return expandPredicate(OS, Sequence[0]); 117 118 // Okay, there is more than one predicate in the set. 119 bool First = true; 120 OS << (shouldNegate() ? "!(" : "("); 121 increaseIndentLevel(); 122 123 bool OldValue = shouldNegate(); 124 setNegatePredicate(false); 125 for (const Record *Rec : Sequence) { 126 OS << '\n'; 127 OS.PadToColumn(getIndentLevel() * 2); 128 if (!First) 129 OS << (IsCheckAll ? "&& " : "|| "); 130 expandPredicate(OS, Rec); 131 First = false; 132 } 133 OS << '\n'; 134 decreaseIndentLevel(); 135 OS.PadToColumn(getIndentLevel() * 2); 136 OS << ')'; 137 setNegatePredicate(OldValue); 138 } 139 140 void PredicateExpander::expandTIIFunctionCall(formatted_raw_ostream &OS, 141 StringRef TargetName, 142 StringRef MethodName) { 143 OS << (shouldNegate() ? "!" : ""); 144 if (shouldExpandForMC()) 145 OS << TargetName << "_MC::"; 146 else 147 OS << TargetName << "Gen" 148 << "InstrInfo::"; 149 OS << MethodName << (isByRef() ? "(MI)" : "(*MI)"); 150 } 151 152 void PredicateExpander::expandCheckIsRegOperand(formatted_raw_ostream &OS, 153 int OpIndex) { 154 OS << (shouldNegate() ? "!" : "") << "MI" << (isByRef() ? "." : "->") 155 << "getOperand(" << OpIndex << ").isReg() "; 156 } 157 158 void PredicateExpander::expandCheckIsImmOperand(formatted_raw_ostream &OS, 159 int OpIndex) { 160 OS << (shouldNegate() ? "!" : "") << "MI" << (isByRef() ? "." : "->") 161 << "getOperand(" << OpIndex << ").isImm() "; 162 } 163 164 void PredicateExpander::expandCheckFunctionPredicate(formatted_raw_ostream &OS, 165 StringRef MCInstFn, 166 StringRef MachineInstrFn) { 167 OS << (shouldExpandForMC() ? MCInstFn : MachineInstrFn) 168 << (isByRef() ? "(MI)" : "(*MI)"); 169 } 170 171 void PredicateExpander::expandCheckNonPortable(formatted_raw_ostream &OS, 172 StringRef Code) { 173 if (shouldExpandForMC()) 174 return expandFalse(OS); 175 176 OS << '(' << Code << ')'; 177 } 178 179 void PredicateExpander::expandPredicate(formatted_raw_ostream &OS, 180 const Record *Rec) { 181 OS.flush(); 182 unsigned ColNum = getIndentLevel() * 2; 183 if (OS.getColumn() < ColNum) 184 OS.PadToColumn(ColNum); 185 186 if (Rec->isSubClassOf("MCTrue")) { 187 if (shouldNegate()) 188 return expandFalse(OS); 189 return expandTrue(OS); 190 } 191 192 if (Rec->isSubClassOf("MCFalse")) { 193 if (shouldNegate()) 194 return expandTrue(OS); 195 return expandFalse(OS); 196 } 197 198 if (Rec->isSubClassOf("CheckNot")) { 199 flipNegatePredicate(); 200 expandPredicate(OS, Rec->getValueAsDef("Pred")); 201 flipNegatePredicate(); 202 return; 203 } 204 205 if (Rec->isSubClassOf("CheckIsRegOperand")) 206 return expandCheckIsRegOperand(OS, Rec->getValueAsInt("OpIndex")); 207 208 if (Rec->isSubClassOf("CheckIsImmOperand")) 209 return expandCheckIsImmOperand(OS, Rec->getValueAsInt("OpIndex")); 210 211 if (Rec->isSubClassOf("CheckRegOperand")) 212 return expandCheckRegOperand(OS, Rec->getValueAsInt("OpIndex"), 213 Rec->getValueAsDef("Reg")); 214 215 if (Rec->isSubClassOf("CheckInvalidRegOperand")) 216 return expandCheckInvalidRegOperand(OS, Rec->getValueAsInt("OpIndex")); 217 218 if (Rec->isSubClassOf("CheckImmOperand")) 219 return expandCheckImmOperand(OS, Rec->getValueAsInt("OpIndex"), 220 Rec->getValueAsInt("ImmVal")); 221 222 if (Rec->isSubClassOf("CheckImmOperand_s")) 223 return expandCheckImmOperand(OS, Rec->getValueAsInt("OpIndex"), 224 Rec->getValueAsString("ImmVal")); 225 226 if (Rec->isSubClassOf("CheckSameRegOperand")) 227 return expandCheckSameRegOperand(OS, Rec->getValueAsInt("FirstIndex"), 228 Rec->getValueAsInt("SecondIndex")); 229 230 if (Rec->isSubClassOf("CheckNumOperands")) 231 return expandCheckNumOperands(OS, Rec->getValueAsInt("NumOps")); 232 233 if (Rec->isSubClassOf("CheckPseudo")) 234 return expandCheckPseudo(OS, Rec->getValueAsListOfDefs("ValidOpcodes")); 235 236 if (Rec->isSubClassOf("CheckOpcode")) 237 return expandCheckOpcode(OS, Rec->getValueAsListOfDefs("ValidOpcodes")); 238 239 if (Rec->isSubClassOf("CheckAll")) 240 return expandPredicateSequence(OS, Rec->getValueAsListOfDefs("Predicates"), 241 /* AllOf */ true); 242 243 if (Rec->isSubClassOf("CheckAny")) 244 return expandPredicateSequence(OS, Rec->getValueAsListOfDefs("Predicates"), 245 /* AllOf */ false); 246 247 if (Rec->isSubClassOf("CheckFunctionPredicate")) 248 return expandCheckFunctionPredicate( 249 OS, Rec->getValueAsString("MCInstFnName"), 250 Rec->getValueAsString("MachineInstrFnName")); 251 252 if (Rec->isSubClassOf("CheckNonPortable")) 253 return expandCheckNonPortable(OS, Rec->getValueAsString("CodeBlock")); 254 255 if (Rec->isSubClassOf("TIIPredicate")) 256 return expandTIIFunctionCall(OS, Rec->getValueAsString("TargetName"), 257 Rec->getValueAsString("FunctionName")); 258 259 llvm_unreachable("No known rules to expand this MCInstPredicate"); 260 } 261 262 } // namespace llvm 263