18#include "MipsGenInstrInfo.inc" 19 20using namespace llvm; 21 22MipsInstrInfo::MipsInstrInfo(MipsTargetMachine &tm) 23 : TargetInstrInfoImpl(MipsInsts, array_lengthof(MipsInsts)), 24 TM(tm), RI(*TM.getSubtargetImpl(), *this) {} 25 26static bool isZeroImm(const MachineOperand &op) { 27 return op.isImm() && op.getImm() == 0; 28} 29 30/// Return true if the instruction is a register to register move and 31/// leave the source and dest operands in the passed parameters. 32bool MipsInstrInfo:: 33isMoveInstr(const MachineInstr &MI, unsigned &SrcReg, unsigned &DstReg, 34 unsigned &SrcSubIdx, unsigned &DstSubIdx) const 35{ 36 SrcSubIdx = DstSubIdx = 0; // No sub-registers. 37 38 // addu $dst, $src, $zero || addu $dst, $zero, $src 39 // or $dst, $src, $zero || or $dst, $zero, $src 40 if ((MI.getOpcode() == Mips::ADDu) || (MI.getOpcode() == Mips::OR)) { 41 if (MI.getOperand(1).getReg() == Mips::ZERO) { 42 DstReg = MI.getOperand(0).getReg(); 43 SrcReg = MI.getOperand(2).getReg(); 44 return true; 45 } else if (MI.getOperand(2).getReg() == Mips::ZERO) { 46 DstReg = MI.getOperand(0).getReg(); 47 SrcReg = MI.getOperand(1).getReg(); 48 return true; 49 } 50 } 51 52 // mov $fpDst, $fpSrc 53 // mfc $gpDst, $fpSrc 54 // mtc $fpDst, $gpSrc 55 if (MI.getOpcode() == Mips::FMOV_S32 || 56 MI.getOpcode() == Mips::FMOV_D32 || 57 MI.getOpcode() == Mips::MFC1 || 58 MI.getOpcode() == Mips::MTC1 || 59 MI.getOpcode() == Mips::MOVCCRToCCR) { 60 DstReg = MI.getOperand(0).getReg(); 61 SrcReg = MI.getOperand(1).getReg(); 62 return true; 63 } 64 65 // addiu $dst, $src, 0 66 if (MI.getOpcode() == Mips::ADDiu) { 67 if ((MI.getOperand(1).isReg()) && (isZeroImm(MI.getOperand(2)))) { 68 DstReg = MI.getOperand(0).getReg(); 69 SrcReg = MI.getOperand(1).getReg(); 70 return true; 71 } 72 } 73 74 return false; 75} 76 77/// isLoadFromStackSlot - If the specified machine instruction is a direct 78/// load from a stack slot, return the virtual or physical register number of 79/// the destination along with the FrameIndex of the loaded stack slot. If 80/// not, return 0. This predicate must return 0 if the instruction has 81/// any side effects other than loading from the stack slot. 82unsigned MipsInstrInfo:: 83isLoadFromStackSlot(const MachineInstr *MI, int &FrameIndex) const 84{ 85 if ((MI->getOpcode() == Mips::LW) || (MI->getOpcode() == Mips::LWC1) || 86 (MI->getOpcode() == Mips::LDC1)) { 87 if ((MI->getOperand(2).isFI()) && // is a stack slot 88 (MI->getOperand(1).isImm()) && // the imm is zero 89 (isZeroImm(MI->getOperand(1)))) { 90 FrameIndex = MI->getOperand(2).getIndex(); 91 return MI->getOperand(0).getReg(); 92 } 93 } 94 95 return 0; 96} 97 98/// isStoreToStackSlot - If the specified machine instruction is a direct 99/// store to a stack slot, return the virtual or physical register number of 100/// the source reg along with the FrameIndex of the loaded stack slot. If 101/// not, return 0. This predicate must return 0 if the instruction has 102/// any side effects other than storing to the stack slot. 103unsigned MipsInstrInfo:: 104isStoreToStackSlot(const MachineInstr *MI, int &FrameIndex) const 105{ 106 if ((MI->getOpcode() == Mips::SW) || (MI->getOpcode() == Mips::SWC1) || 107 (MI->getOpcode() == Mips::SDC1)) { 108 if ((MI->getOperand(2).isFI()) && // is a stack slot 109 (MI->getOperand(1).isImm()) && // the imm is zero 110 (isZeroImm(MI->getOperand(1)))) { 111 FrameIndex = MI->getOperand(2).getIndex(); 112 return MI->getOperand(0).getReg(); 113 } 114 } 115 return 0; 116} 117 118/// insertNoop - If data hazard condition is found insert the target nop 119/// instruction. 120void MipsInstrInfo:: 121insertNoop(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI) const 122{ 123 DebugLoc DL = DebugLoc::getUnknownLoc(); 124 if (MI != MBB.end()) DL = MI->getDebugLoc(); 125 BuildMI(MBB, MI, DL, get(Mips::NOP)); 126} 127 128bool MipsInstrInfo:: 129copyRegToReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 130 unsigned DestReg, unsigned SrcReg, 131 const TargetRegisterClass *DestRC, 132 const TargetRegisterClass *SrcRC) const { 133 DebugLoc DL = DebugLoc::getUnknownLoc(); 134 if (I != MBB.end()) DL = I->getDebugLoc(); 135 136 if (DestRC != SrcRC) { 137 138 // Copy to/from FCR31 condition register 139 if ((DestRC == Mips::CPURegsRegisterClass) && 140 (SrcRC == Mips::CCRRegisterClass)) 141 BuildMI(MBB, I, DL, get(Mips::CFC1), DestReg).addReg(SrcReg); 142 else if ((DestRC == Mips::CCRRegisterClass) && 143 (SrcRC == Mips::CPURegsRegisterClass)) 144 BuildMI(MBB, I, DL, get(Mips::CTC1), DestReg).addReg(SrcReg); 145 146 // Moves between coprocessors and cpu 147 else if ((DestRC == Mips::CPURegsRegisterClass) && 148 (SrcRC == Mips::FGR32RegisterClass)) 149 BuildMI(MBB, I, DL, get(Mips::MFC1), DestReg).addReg(SrcReg); 150 else if ((DestRC == Mips::FGR32RegisterClass) && 151 (SrcRC == Mips::CPURegsRegisterClass)) 152 BuildMI(MBB, I, DL, get(Mips::MTC1), DestReg).addReg(SrcReg); 153 154 // Move from/to Hi/Lo registers 155 else if ((DestRC == Mips::HILORegisterClass) && 156 (SrcRC == Mips::CPURegsRegisterClass)) { 157 unsigned Opc = (DestReg == Mips::HI) ? Mips::MTHI : Mips::MTLO; 158 BuildMI(MBB, I, DL, get(Opc), DestReg); 159 } else if ((SrcRC == Mips::HILORegisterClass) && 160 (DestRC == Mips::CPURegsRegisterClass)) { 161 unsigned Opc = (SrcReg == Mips::HI) ? Mips::MFHI : Mips::MFLO; 162 BuildMI(MBB, I, DL, get(Opc), DestReg); 163 164 // Can't copy this register 165 } else 166 return false; 167 168 return true; 169 } 170 171 if (DestRC == Mips::CPURegsRegisterClass) 172 BuildMI(MBB, I, DL, get(Mips::ADDu), DestReg).addReg(Mips::ZERO) 173 .addReg(SrcReg); 174 else if (DestRC == Mips::FGR32RegisterClass) 175 BuildMI(MBB, I, DL, get(Mips::FMOV_S32), DestReg).addReg(SrcReg); 176 else if (DestRC == Mips::AFGR64RegisterClass) 177 BuildMI(MBB, I, DL, get(Mips::FMOV_D32), DestReg).addReg(SrcReg); 178 else if (DestRC == Mips::CCRRegisterClass) 179 BuildMI(MBB, I, DL, get(Mips::MOVCCRToCCR), DestReg).addReg(SrcReg); 180 else 181 // Can't copy this register 182 return false; 183 184 return true; 185} 186 187void MipsInstrInfo:: 188storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 189 unsigned SrcReg, bool isKill, int FI, 190 const TargetRegisterClass *RC) const { 191 unsigned Opc; 192 193 DebugLoc DL = DebugLoc::getUnknownLoc(); 194 if (I != MBB.end()) DL = I->getDebugLoc(); 195 196 if (RC == Mips::CPURegsRegisterClass) 197 Opc = Mips::SW; 198 else if (RC == Mips::FGR32RegisterClass) 199 Opc = Mips::SWC1; 200 else { 201 assert(RC == Mips::AFGR64RegisterClass); 202 Opc = Mips::SDC1; 203 } 204 205 BuildMI(MBB, I, DL, get(Opc)).addReg(SrcReg, getKillRegState(isKill)) 206 .addImm(0).addFrameIndex(FI); 207} 208 209void MipsInstrInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, 210 bool isKill, SmallVectorImpl<MachineOperand> &Addr, 211 const TargetRegisterClass *RC, SmallVectorImpl<MachineInstr*> &NewMIs) const 212{ 213 unsigned Opc; 214 if (RC == Mips::CPURegsRegisterClass) 215 Opc = Mips::SW; 216 else if (RC == Mips::FGR32RegisterClass) 217 Opc = Mips::SWC1; 218 else { 219 assert(RC == Mips::AFGR64RegisterClass); 220 Opc = Mips::SDC1; 221 } 222 223 DebugLoc DL = DebugLoc::getUnknownLoc(); 224 MachineInstrBuilder MIB = BuildMI(MF, DL, get(Opc)) 225 .addReg(SrcReg, getKillRegState(isKill)); 226 for (unsigned i = 0, e = Addr.size(); i != e; ++i) 227 MIB.addOperand(Addr[i]); 228 NewMIs.push_back(MIB); 229 return; 230} 231 232void MipsInstrInfo:: 233loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 234 unsigned DestReg, int FI, 235 const TargetRegisterClass *RC) const 236{ 237 unsigned Opc; 238 if (RC == Mips::CPURegsRegisterClass) 239 Opc = Mips::LW; 240 else if (RC == Mips::FGR32RegisterClass) 241 Opc = Mips::LWC1; 242 else { 243 assert(RC == Mips::AFGR64RegisterClass); 244 Opc = Mips::LDC1; 245 } 246 247 DebugLoc DL = DebugLoc::getUnknownLoc(); 248 if (I != MBB.end()) DL = I->getDebugLoc(); 249 BuildMI(MBB, I, DL, get(Opc), DestReg).addImm(0).addFrameIndex(FI); 250} 251 252void MipsInstrInfo::loadRegFromAddr(MachineFunction &MF, unsigned DestReg, 253 SmallVectorImpl<MachineOperand> &Addr, 254 const TargetRegisterClass *RC, 255 SmallVectorImpl<MachineInstr*> &NewMIs) const { 256 unsigned Opc; 257 if (RC == Mips::CPURegsRegisterClass) 258 Opc = Mips::LW; 259 else if (RC == Mips::FGR32RegisterClass) 260 Opc = Mips::LWC1; 261 else { 262 assert(RC == Mips::AFGR64RegisterClass); 263 Opc = Mips::LDC1; 264 } 265 266 DebugLoc DL = DebugLoc::getUnknownLoc(); 267 MachineInstrBuilder MIB = BuildMI(MF, DL, get(Opc), DestReg); 268 for (unsigned i = 0, e = Addr.size(); i != e; ++i) 269 MIB.addOperand(Addr[i]); 270 NewMIs.push_back(MIB); 271 return; 272} 273 274MachineInstr *MipsInstrInfo:: 275foldMemoryOperandImpl(MachineFunction &MF, 276 MachineInstr* MI, 277 const SmallVectorImpl<unsigned> &Ops, int FI) const 278{ 279 if (Ops.size() != 1) return NULL; 280 281 MachineInstr *NewMI = NULL; 282 283 switch (MI->getOpcode()) { 284 case Mips::ADDu: 285 if ((MI->getOperand(0).isReg()) && 286 (MI->getOperand(1).isReg()) && 287 (MI->getOperand(1).getReg() == Mips::ZERO) && 288 (MI->getOperand(2).isReg())) { 289 if (Ops[0] == 0) { // COPY -> STORE 290 unsigned SrcReg = MI->getOperand(2).getReg(); 291 bool isKill = MI->getOperand(2).isKill(); 292 NewMI = BuildMI(MF, MI->getDebugLoc(), get(Mips::SW)) 293 .addReg(SrcReg, getKillRegState(isKill)) 294 .addImm(0).addFrameIndex(FI); 295 } else { // COPY -> LOAD 296 unsigned DstReg = MI->getOperand(0).getReg(); 297 bool isDead = MI->getOperand(0).isDead(); 298 NewMI = BuildMI(MF, MI->getDebugLoc(), get(Mips::LW)) 299 .addReg(DstReg, RegState::Define | getDeadRegState(isDead)) 300 .addImm(0).addFrameIndex(FI); 301 } 302 } 303 break; 304 case Mips::FMOV_S32: 305 case Mips::FMOV_D32: 306 if ((MI->getOperand(0).isReg()) && 307 (MI->getOperand(1).isReg())) { 308 const TargetRegisterClass 309 *RC = RI.getRegClass(MI->getOperand(0).getReg()); 310 unsigned StoreOpc, LoadOpc; 311 312 if (RC == Mips::FGR32RegisterClass) { 313 LoadOpc = Mips::LWC1; StoreOpc = Mips::SWC1; 314 } else { 315 assert(RC == Mips::AFGR64RegisterClass); 316 LoadOpc = Mips::LDC1; StoreOpc = Mips::SDC1; 317 } 318 319 if (Ops[0] == 0) { // COPY -> STORE 320 unsigned SrcReg = MI->getOperand(1).getReg(); 321 bool isKill = MI->getOperand(1).isKill(); 322 NewMI = BuildMI(MF, MI->getDebugLoc(), get(StoreOpc)) 323 .addReg(SrcReg, getKillRegState(isKill)) 324 .addImm(0).addFrameIndex(FI) ; 325 } else { // COPY -> LOAD 326 unsigned DstReg = MI->getOperand(0).getReg(); 327 bool isDead = MI->getOperand(0).isDead(); 328 NewMI = BuildMI(MF, MI->getDebugLoc(), get(LoadOpc)) 329 .addReg(DstReg, RegState::Define | getDeadRegState(isDead)) 330 .addImm(0).addFrameIndex(FI); 331 } 332 } 333 break; 334 } 335 336 return NewMI; 337} 338 339//===----------------------------------------------------------------------===// 340// Branch Analysis 341//===----------------------------------------------------------------------===// 342 343/// GetCondFromBranchOpc - Return the Mips CC that matches 344/// the correspondent Branch instruction opcode. 345static Mips::CondCode GetCondFromBranchOpc(unsigned BrOpc) 346{ 347 switch (BrOpc) { 348 default: return Mips::COND_INVALID; 349 case Mips::BEQ : return Mips::COND_E; 350 case Mips::BNE : return Mips::COND_NE; 351 case Mips::BGTZ : return Mips::COND_GZ; 352 case Mips::BGEZ : return Mips::COND_GEZ; 353 case Mips::BLTZ : return Mips::COND_LZ; 354 case Mips::BLEZ : return Mips::COND_LEZ; 355 356 // We dont do fp branch analysis yet! 357 case Mips::BC1T : 358 case Mips::BC1F : return Mips::COND_INVALID; 359 } 360} 361 362/// GetCondBranchFromCond - Return the Branch instruction 363/// opcode that matches the cc. 364unsigned Mips::GetCondBranchFromCond(Mips::CondCode CC) 365{ 366 switch (CC) { 367 default: assert(0 && "Illegal condition code!"); 368 case Mips::COND_E : return Mips::BEQ; 369 case Mips::COND_NE : return Mips::BNE; 370 case Mips::COND_GZ : return Mips::BGTZ; 371 case Mips::COND_GEZ : return Mips::BGEZ; 372 case Mips::COND_LZ : return Mips::BLTZ; 373 case Mips::COND_LEZ : return Mips::BLEZ; 374 375 case Mips::FCOND_F: 376 case Mips::FCOND_UN: 377 case Mips::FCOND_EQ: 378 case Mips::FCOND_UEQ: 379 case Mips::FCOND_OLT: 380 case Mips::FCOND_ULT: 381 case Mips::FCOND_OLE: 382 case Mips::FCOND_ULE: 383 case Mips::FCOND_SF: 384 case Mips::FCOND_NGLE: 385 case Mips::FCOND_SEQ: 386 case Mips::FCOND_NGL: 387 case Mips::FCOND_LT: 388 case Mips::FCOND_NGE: 389 case Mips::FCOND_LE: 390 case Mips::FCOND_NGT: return Mips::BC1T; 391 392 case Mips::FCOND_T: 393 case Mips::FCOND_OR: 394 case Mips::FCOND_NEQ: 395 case Mips::FCOND_OGL: 396 case Mips::FCOND_UGE: 397 case Mips::FCOND_OGE: 398 case Mips::FCOND_UGT: 399 case Mips::FCOND_OGT: 400 case Mips::FCOND_ST: 401 case Mips::FCOND_GLE: 402 case Mips::FCOND_SNE: 403 case Mips::FCOND_GL: 404 case Mips::FCOND_NLT: 405 case Mips::FCOND_GE: 406 case Mips::FCOND_NLE: 407 case Mips::FCOND_GT: return Mips::BC1F; 408 } 409} 410 411/// GetOppositeBranchCondition - Return the inverse of the specified 412/// condition, e.g. turning COND_E to COND_NE. 413Mips::CondCode Mips::GetOppositeBranchCondition(Mips::CondCode CC) 414{ 415 switch (CC) { 416 default: assert(0 && "Illegal condition code!"); 417 case Mips::COND_E : return Mips::COND_NE; 418 case Mips::COND_NE : return Mips::COND_E; 419 case Mips::COND_GZ : return Mips::COND_LEZ; 420 case Mips::COND_GEZ : return Mips::COND_LZ; 421 case Mips::COND_LZ : return Mips::COND_GEZ; 422 case Mips::COND_LEZ : return Mips::COND_GZ; 423 case Mips::FCOND_F : return Mips::FCOND_T; 424 case Mips::FCOND_UN : return Mips::FCOND_OR; 425 case Mips::FCOND_EQ : return Mips::FCOND_NEQ; 426 case Mips::FCOND_UEQ: return Mips::FCOND_OGL; 427 case Mips::FCOND_OLT: return Mips::FCOND_UGE; 428 case Mips::FCOND_ULT: return Mips::FCOND_OGE; 429 case Mips::FCOND_OLE: return Mips::FCOND_UGT; 430 case Mips::FCOND_ULE: return Mips::FCOND_OGT; 431 case Mips::FCOND_SF: return Mips::FCOND_ST; 432 case Mips::FCOND_NGLE:return Mips::FCOND_GLE; 433 case Mips::FCOND_SEQ: return Mips::FCOND_SNE; 434 case Mips::FCOND_NGL: return Mips::FCOND_GL; 435 case Mips::FCOND_LT: return Mips::FCOND_NLT; 436 case Mips::FCOND_NGE: return Mips::FCOND_GE; 437 case Mips::FCOND_LE: return Mips::FCOND_NLE; 438 case Mips::FCOND_NGT: return Mips::FCOND_GT; 439 } 440} 441 442bool MipsInstrInfo::AnalyzeBranch(MachineBasicBlock &MBB, 443 MachineBasicBlock *&TBB, 444 MachineBasicBlock *&FBB, 445 SmallVectorImpl<MachineOperand> &Cond, 446 bool AllowModify) const 447{ 448 // If the block has no terminators, it just falls into the block after it. 449 MachineBasicBlock::iterator I = MBB.end(); 450 if (I == MBB.begin() || !isUnpredicatedTerminator(--I)) 451 return false; 452 453 // Get the last instruction in the block. 454 MachineInstr *LastInst = I; 455 456 // If there is only one terminator instruction, process it. 457 unsigned LastOpc = LastInst->getOpcode(); 458 if (I == MBB.begin() || !isUnpredicatedTerminator(--I)) { 459 if (!LastInst->getDesc().isBranch()) 460 return true; 461 462 // Unconditional branch 463 if (LastOpc == Mips::J) { 464 TBB = LastInst->getOperand(0).getMBB(); 465 return false; 466 } 467 468 Mips::CondCode BranchCode = GetCondFromBranchOpc(LastInst->getOpcode()); 469 if (BranchCode == Mips::COND_INVALID) 470 return true; // Can't handle indirect branch. 471 472 // Conditional branch 473 // Block ends with fall-through condbranch. 474 if (LastOpc != Mips::COND_INVALID) { 475 int LastNumOp = LastInst->getNumOperands(); 476 477 TBB = LastInst->getOperand(LastNumOp-1).getMBB(); 478 Cond.push_back(MachineOperand::CreateImm(BranchCode)); 479 480 for (int i=0; i<LastNumOp-1; i++) { 481 Cond.push_back(LastInst->getOperand(i)); 482 } 483 484 return false; 485 } 486 } 487 488 // Get the instruction before it if it is a terminator. 489 MachineInstr *SecondLastInst = I; 490 491 // If there are three terminators, we don't know what sort of block this is. 492 if (SecondLastInst && I != MBB.begin() && isUnpredicatedTerminator(--I)) 493 return true; 494 495 // If the block ends with Mips::J and a Mips::BNE/Mips::BEQ, handle it. 496 unsigned SecondLastOpc = SecondLastInst->getOpcode(); 497 Mips::CondCode BranchCode = GetCondFromBranchOpc(SecondLastOpc); 498 499 if (BranchCode != Mips::COND_INVALID && LastOpc == Mips::J) { 500 int SecondNumOp = SecondLastInst->getNumOperands(); 501 502 TBB = SecondLastInst->getOperand(SecondNumOp-1).getMBB(); 503 Cond.push_back(MachineOperand::CreateImm(BranchCode)); 504 505 for (int i=0; i<SecondNumOp-1; i++) { 506 Cond.push_back(SecondLastInst->getOperand(i)); 507 } 508 509 FBB = LastInst->getOperand(0).getMBB(); 510 return false; 511 } 512 513 // If the block ends with two unconditional branches, handle it. The last 514 // one is not executed, so remove it. 515 if ((SecondLastOpc == Mips::J) && (LastOpc == Mips::J)) { 516 TBB = SecondLastInst->getOperand(0).getMBB(); 517 I = LastInst; 518 if (AllowModify) 519 I->eraseFromParent(); 520 return false; 521 } 522 523 // Otherwise, can't handle this. 524 return true; 525} 526 527unsigned MipsInstrInfo:: 528InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, 529 MachineBasicBlock *FBB, 530 const SmallVectorImpl<MachineOperand> &Cond) const { 531 // FIXME this should probably have a DebugLoc argument 532 DebugLoc dl = DebugLoc::getUnknownLoc(); 533 // Shouldn't be a fall through. 534 assert(TBB && "InsertBranch must not be told to insert a fallthrough"); 535 assert((Cond.size() == 3 || Cond.size() == 2 || Cond.size() == 0) && 536 "Mips branch conditions can have two|three components!"); 537 538 if (FBB == 0) { // One way branch. 539 if (Cond.empty()) { 540 // Unconditional branch? 541 BuildMI(&MBB, dl, get(Mips::J)).addMBB(TBB); 542 } else { 543 // Conditional branch. 544 unsigned Opc = GetCondBranchFromCond((Mips::CondCode)Cond[0].getImm()); 545 const TargetInstrDesc &TID = get(Opc); 546 547 if (TID.getNumOperands() == 3) 548 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()) 549 .addReg(Cond[2].getReg()) 550 .addMBB(TBB); 551 else 552 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()) 553 .addMBB(TBB); 554 555 } 556 return 1; 557 } 558 559 // Two-way Conditional branch. 560 unsigned Opc = GetCondBranchFromCond((Mips::CondCode)Cond[0].getImm()); 561 const TargetInstrDesc &TID = get(Opc); 562 563 if (TID.getNumOperands() == 3) 564 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()).addReg(Cond[2].getReg()) 565 .addMBB(TBB); 566 else 567 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()).addMBB(TBB); 568 569 BuildMI(&MBB, dl, get(Mips::J)).addMBB(FBB); 570 return 2; 571} 572 573unsigned MipsInstrInfo:: 574RemoveBranch(MachineBasicBlock &MBB) const 575{ 576 MachineBasicBlock::iterator I = MBB.end(); 577 if (I == MBB.begin()) return 0; 578 --I; 579 if (I->getOpcode() != Mips::J && 580 GetCondFromBranchOpc(I->getOpcode()) == Mips::COND_INVALID) 581 return 0; 582 583 // Remove the branch. 584 I->eraseFromParent(); 585 586 I = MBB.end(); 587 588 if (I == MBB.begin()) return 1; 589 --I; 590 if (GetCondFromBranchOpc(I->getOpcode()) == Mips::COND_INVALID) 591 return 1; 592 593 // Remove the branch. 594 I->eraseFromParent(); 595 return 2; 596} 597 598/// BlockHasNoFallThrough - Analyze if MachineBasicBlock does not 599/// fall-through into its successor block. 600bool MipsInstrInfo:: 601BlockHasNoFallThrough(const MachineBasicBlock &MBB) const 602{ 603 if (MBB.empty()) return false; 604 605 switch (MBB.back().getOpcode()) { 606 case Mips::RET: // Return. 607 case Mips::JR: // Indirect branch. 608 case Mips::J: // Uncond branch. 609 return true; 610 default: return false; 611 } 612} 613 614/// ReverseBranchCondition - Return the inverse opcode of the 615/// specified Branch instruction. 616bool MipsInstrInfo:: 617ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const 618{ 619 assert( (Cond.size() == 3 || Cond.size() == 2) && 620 "Invalid Mips branch condition!"); 621 Cond[0].setImm(GetOppositeBranchCondition((Mips::CondCode)Cond[0].getImm())); 622 return false; 623}
| 20#include "MipsGenInstrInfo.inc" 21 22using namespace llvm; 23 24MipsInstrInfo::MipsInstrInfo(MipsTargetMachine &tm) 25 : TargetInstrInfoImpl(MipsInsts, array_lengthof(MipsInsts)), 26 TM(tm), RI(*TM.getSubtargetImpl(), *this) {} 27 28static bool isZeroImm(const MachineOperand &op) { 29 return op.isImm() && op.getImm() == 0; 30} 31 32/// Return true if the instruction is a register to register move and 33/// leave the source and dest operands in the passed parameters. 34bool MipsInstrInfo:: 35isMoveInstr(const MachineInstr &MI, unsigned &SrcReg, unsigned &DstReg, 36 unsigned &SrcSubIdx, unsigned &DstSubIdx) const 37{ 38 SrcSubIdx = DstSubIdx = 0; // No sub-registers. 39 40 // addu $dst, $src, $zero || addu $dst, $zero, $src 41 // or $dst, $src, $zero || or $dst, $zero, $src 42 if ((MI.getOpcode() == Mips::ADDu) || (MI.getOpcode() == Mips::OR)) { 43 if (MI.getOperand(1).getReg() == Mips::ZERO) { 44 DstReg = MI.getOperand(0).getReg(); 45 SrcReg = MI.getOperand(2).getReg(); 46 return true; 47 } else if (MI.getOperand(2).getReg() == Mips::ZERO) { 48 DstReg = MI.getOperand(0).getReg(); 49 SrcReg = MI.getOperand(1).getReg(); 50 return true; 51 } 52 } 53 54 // mov $fpDst, $fpSrc 55 // mfc $gpDst, $fpSrc 56 // mtc $fpDst, $gpSrc 57 if (MI.getOpcode() == Mips::FMOV_S32 || 58 MI.getOpcode() == Mips::FMOV_D32 || 59 MI.getOpcode() == Mips::MFC1 || 60 MI.getOpcode() == Mips::MTC1 || 61 MI.getOpcode() == Mips::MOVCCRToCCR) { 62 DstReg = MI.getOperand(0).getReg(); 63 SrcReg = MI.getOperand(1).getReg(); 64 return true; 65 } 66 67 // addiu $dst, $src, 0 68 if (MI.getOpcode() == Mips::ADDiu) { 69 if ((MI.getOperand(1).isReg()) && (isZeroImm(MI.getOperand(2)))) { 70 DstReg = MI.getOperand(0).getReg(); 71 SrcReg = MI.getOperand(1).getReg(); 72 return true; 73 } 74 } 75 76 return false; 77} 78 79/// isLoadFromStackSlot - If the specified machine instruction is a direct 80/// load from a stack slot, return the virtual or physical register number of 81/// the destination along with the FrameIndex of the loaded stack slot. If 82/// not, return 0. This predicate must return 0 if the instruction has 83/// any side effects other than loading from the stack slot. 84unsigned MipsInstrInfo:: 85isLoadFromStackSlot(const MachineInstr *MI, int &FrameIndex) const 86{ 87 if ((MI->getOpcode() == Mips::LW) || (MI->getOpcode() == Mips::LWC1) || 88 (MI->getOpcode() == Mips::LDC1)) { 89 if ((MI->getOperand(2).isFI()) && // is a stack slot 90 (MI->getOperand(1).isImm()) && // the imm is zero 91 (isZeroImm(MI->getOperand(1)))) { 92 FrameIndex = MI->getOperand(2).getIndex(); 93 return MI->getOperand(0).getReg(); 94 } 95 } 96 97 return 0; 98} 99 100/// isStoreToStackSlot - If the specified machine instruction is a direct 101/// store to a stack slot, return the virtual or physical register number of 102/// the source reg along with the FrameIndex of the loaded stack slot. If 103/// not, return 0. This predicate must return 0 if the instruction has 104/// any side effects other than storing to the stack slot. 105unsigned MipsInstrInfo:: 106isStoreToStackSlot(const MachineInstr *MI, int &FrameIndex) const 107{ 108 if ((MI->getOpcode() == Mips::SW) || (MI->getOpcode() == Mips::SWC1) || 109 (MI->getOpcode() == Mips::SDC1)) { 110 if ((MI->getOperand(2).isFI()) && // is a stack slot 111 (MI->getOperand(1).isImm()) && // the imm is zero 112 (isZeroImm(MI->getOperand(1)))) { 113 FrameIndex = MI->getOperand(2).getIndex(); 114 return MI->getOperand(0).getReg(); 115 } 116 } 117 return 0; 118} 119 120/// insertNoop - If data hazard condition is found insert the target nop 121/// instruction. 122void MipsInstrInfo:: 123insertNoop(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI) const 124{ 125 DebugLoc DL = DebugLoc::getUnknownLoc(); 126 if (MI != MBB.end()) DL = MI->getDebugLoc(); 127 BuildMI(MBB, MI, DL, get(Mips::NOP)); 128} 129 130bool MipsInstrInfo:: 131copyRegToReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 132 unsigned DestReg, unsigned SrcReg, 133 const TargetRegisterClass *DestRC, 134 const TargetRegisterClass *SrcRC) const { 135 DebugLoc DL = DebugLoc::getUnknownLoc(); 136 if (I != MBB.end()) DL = I->getDebugLoc(); 137 138 if (DestRC != SrcRC) { 139 140 // Copy to/from FCR31 condition register 141 if ((DestRC == Mips::CPURegsRegisterClass) && 142 (SrcRC == Mips::CCRRegisterClass)) 143 BuildMI(MBB, I, DL, get(Mips::CFC1), DestReg).addReg(SrcReg); 144 else if ((DestRC == Mips::CCRRegisterClass) && 145 (SrcRC == Mips::CPURegsRegisterClass)) 146 BuildMI(MBB, I, DL, get(Mips::CTC1), DestReg).addReg(SrcReg); 147 148 // Moves between coprocessors and cpu 149 else if ((DestRC == Mips::CPURegsRegisterClass) && 150 (SrcRC == Mips::FGR32RegisterClass)) 151 BuildMI(MBB, I, DL, get(Mips::MFC1), DestReg).addReg(SrcReg); 152 else if ((DestRC == Mips::FGR32RegisterClass) && 153 (SrcRC == Mips::CPURegsRegisterClass)) 154 BuildMI(MBB, I, DL, get(Mips::MTC1), DestReg).addReg(SrcReg); 155 156 // Move from/to Hi/Lo registers 157 else if ((DestRC == Mips::HILORegisterClass) && 158 (SrcRC == Mips::CPURegsRegisterClass)) { 159 unsigned Opc = (DestReg == Mips::HI) ? Mips::MTHI : Mips::MTLO; 160 BuildMI(MBB, I, DL, get(Opc), DestReg); 161 } else if ((SrcRC == Mips::HILORegisterClass) && 162 (DestRC == Mips::CPURegsRegisterClass)) { 163 unsigned Opc = (SrcReg == Mips::HI) ? Mips::MFHI : Mips::MFLO; 164 BuildMI(MBB, I, DL, get(Opc), DestReg); 165 166 // Can't copy this register 167 } else 168 return false; 169 170 return true; 171 } 172 173 if (DestRC == Mips::CPURegsRegisterClass) 174 BuildMI(MBB, I, DL, get(Mips::ADDu), DestReg).addReg(Mips::ZERO) 175 .addReg(SrcReg); 176 else if (DestRC == Mips::FGR32RegisterClass) 177 BuildMI(MBB, I, DL, get(Mips::FMOV_S32), DestReg).addReg(SrcReg); 178 else if (DestRC == Mips::AFGR64RegisterClass) 179 BuildMI(MBB, I, DL, get(Mips::FMOV_D32), DestReg).addReg(SrcReg); 180 else if (DestRC == Mips::CCRRegisterClass) 181 BuildMI(MBB, I, DL, get(Mips::MOVCCRToCCR), DestReg).addReg(SrcReg); 182 else 183 // Can't copy this register 184 return false; 185 186 return true; 187} 188 189void MipsInstrInfo:: 190storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 191 unsigned SrcReg, bool isKill, int FI, 192 const TargetRegisterClass *RC) const { 193 unsigned Opc; 194 195 DebugLoc DL = DebugLoc::getUnknownLoc(); 196 if (I != MBB.end()) DL = I->getDebugLoc(); 197 198 if (RC == Mips::CPURegsRegisterClass) 199 Opc = Mips::SW; 200 else if (RC == Mips::FGR32RegisterClass) 201 Opc = Mips::SWC1; 202 else { 203 assert(RC == Mips::AFGR64RegisterClass); 204 Opc = Mips::SDC1; 205 } 206 207 BuildMI(MBB, I, DL, get(Opc)).addReg(SrcReg, getKillRegState(isKill)) 208 .addImm(0).addFrameIndex(FI); 209} 210 211void MipsInstrInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, 212 bool isKill, SmallVectorImpl<MachineOperand> &Addr, 213 const TargetRegisterClass *RC, SmallVectorImpl<MachineInstr*> &NewMIs) const 214{ 215 unsigned Opc; 216 if (RC == Mips::CPURegsRegisterClass) 217 Opc = Mips::SW; 218 else if (RC == Mips::FGR32RegisterClass) 219 Opc = Mips::SWC1; 220 else { 221 assert(RC == Mips::AFGR64RegisterClass); 222 Opc = Mips::SDC1; 223 } 224 225 DebugLoc DL = DebugLoc::getUnknownLoc(); 226 MachineInstrBuilder MIB = BuildMI(MF, DL, get(Opc)) 227 .addReg(SrcReg, getKillRegState(isKill)); 228 for (unsigned i = 0, e = Addr.size(); i != e; ++i) 229 MIB.addOperand(Addr[i]); 230 NewMIs.push_back(MIB); 231 return; 232} 233 234void MipsInstrInfo:: 235loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 236 unsigned DestReg, int FI, 237 const TargetRegisterClass *RC) const 238{ 239 unsigned Opc; 240 if (RC == Mips::CPURegsRegisterClass) 241 Opc = Mips::LW; 242 else if (RC == Mips::FGR32RegisterClass) 243 Opc = Mips::LWC1; 244 else { 245 assert(RC == Mips::AFGR64RegisterClass); 246 Opc = Mips::LDC1; 247 } 248 249 DebugLoc DL = DebugLoc::getUnknownLoc(); 250 if (I != MBB.end()) DL = I->getDebugLoc(); 251 BuildMI(MBB, I, DL, get(Opc), DestReg).addImm(0).addFrameIndex(FI); 252} 253 254void MipsInstrInfo::loadRegFromAddr(MachineFunction &MF, unsigned DestReg, 255 SmallVectorImpl<MachineOperand> &Addr, 256 const TargetRegisterClass *RC, 257 SmallVectorImpl<MachineInstr*> &NewMIs) const { 258 unsigned Opc; 259 if (RC == Mips::CPURegsRegisterClass) 260 Opc = Mips::LW; 261 else if (RC == Mips::FGR32RegisterClass) 262 Opc = Mips::LWC1; 263 else { 264 assert(RC == Mips::AFGR64RegisterClass); 265 Opc = Mips::LDC1; 266 } 267 268 DebugLoc DL = DebugLoc::getUnknownLoc(); 269 MachineInstrBuilder MIB = BuildMI(MF, DL, get(Opc), DestReg); 270 for (unsigned i = 0, e = Addr.size(); i != e; ++i) 271 MIB.addOperand(Addr[i]); 272 NewMIs.push_back(MIB); 273 return; 274} 275 276MachineInstr *MipsInstrInfo:: 277foldMemoryOperandImpl(MachineFunction &MF, 278 MachineInstr* MI, 279 const SmallVectorImpl<unsigned> &Ops, int FI) const 280{ 281 if (Ops.size() != 1) return NULL; 282 283 MachineInstr *NewMI = NULL; 284 285 switch (MI->getOpcode()) { 286 case Mips::ADDu: 287 if ((MI->getOperand(0).isReg()) && 288 (MI->getOperand(1).isReg()) && 289 (MI->getOperand(1).getReg() == Mips::ZERO) && 290 (MI->getOperand(2).isReg())) { 291 if (Ops[0] == 0) { // COPY -> STORE 292 unsigned SrcReg = MI->getOperand(2).getReg(); 293 bool isKill = MI->getOperand(2).isKill(); 294 NewMI = BuildMI(MF, MI->getDebugLoc(), get(Mips::SW)) 295 .addReg(SrcReg, getKillRegState(isKill)) 296 .addImm(0).addFrameIndex(FI); 297 } else { // COPY -> LOAD 298 unsigned DstReg = MI->getOperand(0).getReg(); 299 bool isDead = MI->getOperand(0).isDead(); 300 NewMI = BuildMI(MF, MI->getDebugLoc(), get(Mips::LW)) 301 .addReg(DstReg, RegState::Define | getDeadRegState(isDead)) 302 .addImm(0).addFrameIndex(FI); 303 } 304 } 305 break; 306 case Mips::FMOV_S32: 307 case Mips::FMOV_D32: 308 if ((MI->getOperand(0).isReg()) && 309 (MI->getOperand(1).isReg())) { 310 const TargetRegisterClass 311 *RC = RI.getRegClass(MI->getOperand(0).getReg()); 312 unsigned StoreOpc, LoadOpc; 313 314 if (RC == Mips::FGR32RegisterClass) { 315 LoadOpc = Mips::LWC1; StoreOpc = Mips::SWC1; 316 } else { 317 assert(RC == Mips::AFGR64RegisterClass); 318 LoadOpc = Mips::LDC1; StoreOpc = Mips::SDC1; 319 } 320 321 if (Ops[0] == 0) { // COPY -> STORE 322 unsigned SrcReg = MI->getOperand(1).getReg(); 323 bool isKill = MI->getOperand(1).isKill(); 324 NewMI = BuildMI(MF, MI->getDebugLoc(), get(StoreOpc)) 325 .addReg(SrcReg, getKillRegState(isKill)) 326 .addImm(0).addFrameIndex(FI) ; 327 } else { // COPY -> LOAD 328 unsigned DstReg = MI->getOperand(0).getReg(); 329 bool isDead = MI->getOperand(0).isDead(); 330 NewMI = BuildMI(MF, MI->getDebugLoc(), get(LoadOpc)) 331 .addReg(DstReg, RegState::Define | getDeadRegState(isDead)) 332 .addImm(0).addFrameIndex(FI); 333 } 334 } 335 break; 336 } 337 338 return NewMI; 339} 340 341//===----------------------------------------------------------------------===// 342// Branch Analysis 343//===----------------------------------------------------------------------===// 344 345/// GetCondFromBranchOpc - Return the Mips CC that matches 346/// the correspondent Branch instruction opcode. 347static Mips::CondCode GetCondFromBranchOpc(unsigned BrOpc) 348{ 349 switch (BrOpc) { 350 default: return Mips::COND_INVALID; 351 case Mips::BEQ : return Mips::COND_E; 352 case Mips::BNE : return Mips::COND_NE; 353 case Mips::BGTZ : return Mips::COND_GZ; 354 case Mips::BGEZ : return Mips::COND_GEZ; 355 case Mips::BLTZ : return Mips::COND_LZ; 356 case Mips::BLEZ : return Mips::COND_LEZ; 357 358 // We dont do fp branch analysis yet! 359 case Mips::BC1T : 360 case Mips::BC1F : return Mips::COND_INVALID; 361 } 362} 363 364/// GetCondBranchFromCond - Return the Branch instruction 365/// opcode that matches the cc. 366unsigned Mips::GetCondBranchFromCond(Mips::CondCode CC) 367{ 368 switch (CC) { 369 default: assert(0 && "Illegal condition code!"); 370 case Mips::COND_E : return Mips::BEQ; 371 case Mips::COND_NE : return Mips::BNE; 372 case Mips::COND_GZ : return Mips::BGTZ; 373 case Mips::COND_GEZ : return Mips::BGEZ; 374 case Mips::COND_LZ : return Mips::BLTZ; 375 case Mips::COND_LEZ : return Mips::BLEZ; 376 377 case Mips::FCOND_F: 378 case Mips::FCOND_UN: 379 case Mips::FCOND_EQ: 380 case Mips::FCOND_UEQ: 381 case Mips::FCOND_OLT: 382 case Mips::FCOND_ULT: 383 case Mips::FCOND_OLE: 384 case Mips::FCOND_ULE: 385 case Mips::FCOND_SF: 386 case Mips::FCOND_NGLE: 387 case Mips::FCOND_SEQ: 388 case Mips::FCOND_NGL: 389 case Mips::FCOND_LT: 390 case Mips::FCOND_NGE: 391 case Mips::FCOND_LE: 392 case Mips::FCOND_NGT: return Mips::BC1T; 393 394 case Mips::FCOND_T: 395 case Mips::FCOND_OR: 396 case Mips::FCOND_NEQ: 397 case Mips::FCOND_OGL: 398 case Mips::FCOND_UGE: 399 case Mips::FCOND_OGE: 400 case Mips::FCOND_UGT: 401 case Mips::FCOND_OGT: 402 case Mips::FCOND_ST: 403 case Mips::FCOND_GLE: 404 case Mips::FCOND_SNE: 405 case Mips::FCOND_GL: 406 case Mips::FCOND_NLT: 407 case Mips::FCOND_GE: 408 case Mips::FCOND_NLE: 409 case Mips::FCOND_GT: return Mips::BC1F; 410 } 411} 412 413/// GetOppositeBranchCondition - Return the inverse of the specified 414/// condition, e.g. turning COND_E to COND_NE. 415Mips::CondCode Mips::GetOppositeBranchCondition(Mips::CondCode CC) 416{ 417 switch (CC) { 418 default: assert(0 && "Illegal condition code!"); 419 case Mips::COND_E : return Mips::COND_NE; 420 case Mips::COND_NE : return Mips::COND_E; 421 case Mips::COND_GZ : return Mips::COND_LEZ; 422 case Mips::COND_GEZ : return Mips::COND_LZ; 423 case Mips::COND_LZ : return Mips::COND_GEZ; 424 case Mips::COND_LEZ : return Mips::COND_GZ; 425 case Mips::FCOND_F : return Mips::FCOND_T; 426 case Mips::FCOND_UN : return Mips::FCOND_OR; 427 case Mips::FCOND_EQ : return Mips::FCOND_NEQ; 428 case Mips::FCOND_UEQ: return Mips::FCOND_OGL; 429 case Mips::FCOND_OLT: return Mips::FCOND_UGE; 430 case Mips::FCOND_ULT: return Mips::FCOND_OGE; 431 case Mips::FCOND_OLE: return Mips::FCOND_UGT; 432 case Mips::FCOND_ULE: return Mips::FCOND_OGT; 433 case Mips::FCOND_SF: return Mips::FCOND_ST; 434 case Mips::FCOND_NGLE:return Mips::FCOND_GLE; 435 case Mips::FCOND_SEQ: return Mips::FCOND_SNE; 436 case Mips::FCOND_NGL: return Mips::FCOND_GL; 437 case Mips::FCOND_LT: return Mips::FCOND_NLT; 438 case Mips::FCOND_NGE: return Mips::FCOND_GE; 439 case Mips::FCOND_LE: return Mips::FCOND_NLE; 440 case Mips::FCOND_NGT: return Mips::FCOND_GT; 441 } 442} 443 444bool MipsInstrInfo::AnalyzeBranch(MachineBasicBlock &MBB, 445 MachineBasicBlock *&TBB, 446 MachineBasicBlock *&FBB, 447 SmallVectorImpl<MachineOperand> &Cond, 448 bool AllowModify) const 449{ 450 // If the block has no terminators, it just falls into the block after it. 451 MachineBasicBlock::iterator I = MBB.end(); 452 if (I == MBB.begin() || !isUnpredicatedTerminator(--I)) 453 return false; 454 455 // Get the last instruction in the block. 456 MachineInstr *LastInst = I; 457 458 // If there is only one terminator instruction, process it. 459 unsigned LastOpc = LastInst->getOpcode(); 460 if (I == MBB.begin() || !isUnpredicatedTerminator(--I)) { 461 if (!LastInst->getDesc().isBranch()) 462 return true; 463 464 // Unconditional branch 465 if (LastOpc == Mips::J) { 466 TBB = LastInst->getOperand(0).getMBB(); 467 return false; 468 } 469 470 Mips::CondCode BranchCode = GetCondFromBranchOpc(LastInst->getOpcode()); 471 if (BranchCode == Mips::COND_INVALID) 472 return true; // Can't handle indirect branch. 473 474 // Conditional branch 475 // Block ends with fall-through condbranch. 476 if (LastOpc != Mips::COND_INVALID) { 477 int LastNumOp = LastInst->getNumOperands(); 478 479 TBB = LastInst->getOperand(LastNumOp-1).getMBB(); 480 Cond.push_back(MachineOperand::CreateImm(BranchCode)); 481 482 for (int i=0; i<LastNumOp-1; i++) { 483 Cond.push_back(LastInst->getOperand(i)); 484 } 485 486 return false; 487 } 488 } 489 490 // Get the instruction before it if it is a terminator. 491 MachineInstr *SecondLastInst = I; 492 493 // If there are three terminators, we don't know what sort of block this is. 494 if (SecondLastInst && I != MBB.begin() && isUnpredicatedTerminator(--I)) 495 return true; 496 497 // If the block ends with Mips::J and a Mips::BNE/Mips::BEQ, handle it. 498 unsigned SecondLastOpc = SecondLastInst->getOpcode(); 499 Mips::CondCode BranchCode = GetCondFromBranchOpc(SecondLastOpc); 500 501 if (BranchCode != Mips::COND_INVALID && LastOpc == Mips::J) { 502 int SecondNumOp = SecondLastInst->getNumOperands(); 503 504 TBB = SecondLastInst->getOperand(SecondNumOp-1).getMBB(); 505 Cond.push_back(MachineOperand::CreateImm(BranchCode)); 506 507 for (int i=0; i<SecondNumOp-1; i++) { 508 Cond.push_back(SecondLastInst->getOperand(i)); 509 } 510 511 FBB = LastInst->getOperand(0).getMBB(); 512 return false; 513 } 514 515 // If the block ends with two unconditional branches, handle it. The last 516 // one is not executed, so remove it. 517 if ((SecondLastOpc == Mips::J) && (LastOpc == Mips::J)) { 518 TBB = SecondLastInst->getOperand(0).getMBB(); 519 I = LastInst; 520 if (AllowModify) 521 I->eraseFromParent(); 522 return false; 523 } 524 525 // Otherwise, can't handle this. 526 return true; 527} 528 529unsigned MipsInstrInfo:: 530InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, 531 MachineBasicBlock *FBB, 532 const SmallVectorImpl<MachineOperand> &Cond) const { 533 // FIXME this should probably have a DebugLoc argument 534 DebugLoc dl = DebugLoc::getUnknownLoc(); 535 // Shouldn't be a fall through. 536 assert(TBB && "InsertBranch must not be told to insert a fallthrough"); 537 assert((Cond.size() == 3 || Cond.size() == 2 || Cond.size() == 0) && 538 "Mips branch conditions can have two|three components!"); 539 540 if (FBB == 0) { // One way branch. 541 if (Cond.empty()) { 542 // Unconditional branch? 543 BuildMI(&MBB, dl, get(Mips::J)).addMBB(TBB); 544 } else { 545 // Conditional branch. 546 unsigned Opc = GetCondBranchFromCond((Mips::CondCode)Cond[0].getImm()); 547 const TargetInstrDesc &TID = get(Opc); 548 549 if (TID.getNumOperands() == 3) 550 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()) 551 .addReg(Cond[2].getReg()) 552 .addMBB(TBB); 553 else 554 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()) 555 .addMBB(TBB); 556 557 } 558 return 1; 559 } 560 561 // Two-way Conditional branch. 562 unsigned Opc = GetCondBranchFromCond((Mips::CondCode)Cond[0].getImm()); 563 const TargetInstrDesc &TID = get(Opc); 564 565 if (TID.getNumOperands() == 3) 566 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()).addReg(Cond[2].getReg()) 567 .addMBB(TBB); 568 else 569 BuildMI(&MBB, dl, TID).addReg(Cond[1].getReg()).addMBB(TBB); 570 571 BuildMI(&MBB, dl, get(Mips::J)).addMBB(FBB); 572 return 2; 573} 574 575unsigned MipsInstrInfo:: 576RemoveBranch(MachineBasicBlock &MBB) const 577{ 578 MachineBasicBlock::iterator I = MBB.end(); 579 if (I == MBB.begin()) return 0; 580 --I; 581 if (I->getOpcode() != Mips::J && 582 GetCondFromBranchOpc(I->getOpcode()) == Mips::COND_INVALID) 583 return 0; 584 585 // Remove the branch. 586 I->eraseFromParent(); 587 588 I = MBB.end(); 589 590 if (I == MBB.begin()) return 1; 591 --I; 592 if (GetCondFromBranchOpc(I->getOpcode()) == Mips::COND_INVALID) 593 return 1; 594 595 // Remove the branch. 596 I->eraseFromParent(); 597 return 2; 598} 599 600/// BlockHasNoFallThrough - Analyze if MachineBasicBlock does not 601/// fall-through into its successor block. 602bool MipsInstrInfo:: 603BlockHasNoFallThrough(const MachineBasicBlock &MBB) const 604{ 605 if (MBB.empty()) return false; 606 607 switch (MBB.back().getOpcode()) { 608 case Mips::RET: // Return. 609 case Mips::JR: // Indirect branch. 610 case Mips::J: // Uncond branch. 611 return true; 612 default: return false; 613 } 614} 615 616/// ReverseBranchCondition - Return the inverse opcode of the 617/// specified Branch instruction. 618bool MipsInstrInfo:: 619ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const 620{ 621 assert( (Cond.size() == 3 || Cond.size() == 2) && 622 "Invalid Mips branch condition!"); 623 Cond[0].setImm(GetOppositeBranchCondition((Mips::CondCode)Cond[0].getImm())); 624 return false; 625}
|