LLVM API Documentation
00001 //===- MipsInstrInfo.cpp - Mips Instruction Information ---------*- C++ -*-===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This file contains the Mips implementation of the TargetInstrInfo class. 00011 // 00012 //===----------------------------------------------------------------------===// 00013 00014 #include "MipsInstrInfo.h" 00015 #include "MipsTargetMachine.h" 00016 #include "llvm/ADT/STLExtras.h" 00017 #include "llvm/CodeGen/MachineInstrBuilder.h" 00018 #include "MipsGenInstrInfo.inc" 00019 00020 using namespace llvm; 00021 00022 MipsInstrInfo::MipsInstrInfo(MipsTargetMachine &tm) 00023 : TargetInstrInfoImpl(MipsInsts, array_lengthof(MipsInsts)), 00024 TM(tm), RI(*TM.getSubtargetImpl(), *this) {} 00025 00026 static bool isZeroImm(const MachineOperand &op) { 00027 return op.isImm() && op.getImm() == 0; 00028 } 00029 00030 /// Return true if the instruction is a register to register move and 00031 /// leave the source and dest operands in the passed parameters. 00032 bool MipsInstrInfo:: 00033 isMoveInstr(const MachineInstr &MI, unsigned &SrcReg, unsigned &DstReg, 00034 unsigned &SrcSubIdx, unsigned &DstSubIdx) const 00035 { 00036 SrcSubIdx = DstSubIdx = 0; // No sub-registers. 00037 00038 // addu $dst, $src, $zero || addu $dst, $zero, $src 00039 // or $dst, $src, $zero || or $dst, $zero, $src 00040 if ((MI.getOpcode() == Mips::ADDu) || (MI.getOpcode() == Mips::OR)) { 00041 if (MI.getOperand(1).getReg() == Mips::ZERO) { 00042 DstReg = MI.getOperand(0).getReg(); 00043 SrcReg = MI.getOperand(2).getReg(); 00044 return true; 00045 } else if (MI.getOperand(2).getReg() == Mips::ZERO) { 00046 DstReg = MI.getOperand(0).getReg(); 00047 SrcReg = MI.getOperand(1).getReg(); 00048 return true; 00049 } 00050 } 00051 00052 // mov $fpDst, $fpSrc 00053 // mfc $gpDst, $fpSrc 00054 // mtc $fpDst, $gpSrc 00055 if (MI.getOpcode() == Mips::FMOV_SO32 || MI.getOpcode() == Mips::FMOV_AS32 || 00056 MI.getOpcode() == Mips::FMOV_D32 || MI.getOpcode() == Mips::MFC1A || 00057 MI.getOpcode() == Mips::MFC1 || MI.getOpcode() == Mips::MTC1A || 00058 MI.getOpcode() == Mips::MTC1 ) { 00059 DstReg = MI.getOperand(0).getReg(); 00060 SrcReg = MI.getOperand(1).getReg(); 00061 return true; 00062 } 00063 00064 // addiu $dst, $src, 0 00065 if (MI.getOpcode() == Mips::ADDiu) { 00066 if ((MI.getOperand(1).isReg()) && (isZeroImm(MI.getOperand(2)))) { 00067 DstReg = MI.getOperand(0).getReg(); 00068 SrcReg = MI.getOperand(1).getReg(); 00069 return true; 00070 } 00071 } 00072 return false; 00073 } 00074 00075 /// isLoadFromStackSlot - If the specified machine instruction is a direct 00076 /// load from a stack slot, return the virtual or physical register number of 00077 /// the destination along with the FrameIndex of the loaded stack slot. If 00078 /// not, return 0. This predicate must return 0 if the instruction has 00079 /// any side effects other than loading from the stack slot. 00080 unsigned MipsInstrInfo:: 00081 isLoadFromStackSlot(const MachineInstr *MI, int &FrameIndex) const 00082 { 00083 if ((MI->getOpcode() == Mips::LW) || (MI->getOpcode() == Mips::LWC1) || 00084 (MI->getOpcode() == Mips::LWC1A) || (MI->getOpcode() == Mips::LDC1)) { 00085 if ((MI->getOperand(2).isFI()) && // is a stack slot 00086 (MI->getOperand(1).isImm()) && // the imm is zero 00087 (isZeroImm(MI->getOperand(1)))) { 00088 FrameIndex = MI->getOperand(2).getIndex(); 00089 return MI->getOperand(0).getReg(); 00090 } 00091 } 00092 00093 return 0; 00094 } 00095 00096 /// isStoreToStackSlot - If the specified machine instruction is a direct 00097 /// store to a stack slot, return the virtual or physical register number of 00098 /// the source reg along with the FrameIndex of the loaded stack slot. If 00099 /// not, return 0. This predicate must return 0 if the instruction has 00100 /// any side effects other than storing to the stack slot. 00101 unsigned MipsInstrInfo:: 00102 isStoreToStackSlot(const MachineInstr *MI, int &FrameIndex) const 00103 { 00104 if ((MI->getOpcode() == Mips::SW) || (MI->getOpcode() == Mips::SWC1) || 00105 (MI->getOpcode() == Mips::SWC1A) || (MI->getOpcode() == Mips::SDC1)) { 00106 if ((MI->getOperand(2).isFI()) && // is a stack slot 00107 (MI->getOperand(1).isImm()) && // the imm is zero 00108 (isZeroImm(MI->getOperand(1)))) { 00109 FrameIndex = MI->getOperand(2).getIndex(); 00110 return MI->getOperand(0).getReg(); 00111 } 00112 } 00113 return 0; 00114 } 00115 00116 /// insertNoop - If data hazard condition is found insert the target nop 00117 /// instruction. 00118 void MipsInstrInfo:: 00119 insertNoop(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI) const 00120 { 00121 BuildMI(MBB, MI, get(Mips::NOP)); 00122 } 00123 00124 bool MipsInstrInfo:: 00125 copyRegToReg(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 00126 unsigned DestReg, unsigned SrcReg, 00127 const TargetRegisterClass *DestRC, 00128 const TargetRegisterClass *SrcRC) const { 00129 if (DestRC != SrcRC) { 00130 if ((DestRC == Mips::CPURegsRegisterClass) && 00131 (SrcRC == Mips::FGR32RegisterClass)) 00132 BuildMI(MBB, I, get(Mips::MFC1), DestReg).addReg(SrcReg); 00133 else if ((DestRC == Mips::CPURegsRegisterClass) && 00134 (SrcRC == Mips::AFGR32RegisterClass)) 00135 BuildMI(MBB, I, get(Mips::MFC1A), DestReg).addReg(SrcReg); 00136 else if ((DestRC == Mips::FGR32RegisterClass) && 00137 (SrcRC == Mips::CPURegsRegisterClass)) 00138 BuildMI(MBB, I, get(Mips::MTC1), DestReg).addReg(SrcReg); 00139 else if ((DestRC == Mips::AFGR32RegisterClass) && 00140 (SrcRC == Mips::CPURegsRegisterClass)) 00141 BuildMI(MBB, I, get(Mips::MTC1A), DestReg).addReg(SrcReg); 00142 else if ((DestRC == Mips::AFGR32RegisterClass) && 00143 (SrcRC == Mips::CPURegsRegisterClass)) 00144 BuildMI(MBB, I, get(Mips::MTC1A), DestReg).addReg(SrcReg); 00145 else if ((SrcRC == Mips::CCRRegisterClass) && 00146 (SrcReg == Mips::FCR31)) 00147 return true; // This register is used implicitly, no copy needed. 00148 else if ((DestRC == Mips::CCRRegisterClass) && 00149 (DestReg == Mips::FCR31)) 00150 return true; // This register is used implicitly, no copy needed. 00151 else if ((DestRC == Mips::HILORegisterClass) && 00152 (SrcRC == Mips::CPURegsRegisterClass)) { 00153 unsigned Opc = (DestReg == Mips::HI) ? Mips::MTHI : Mips::MTLO; 00154 BuildMI(MBB, I, get(Opc), DestReg); 00155 } else if ((SrcRC == Mips::HILORegisterClass) && 00156 (DestRC == Mips::CPURegsRegisterClass)) { 00157 unsigned Opc = (SrcReg == Mips::HI) ? Mips::MFHI : Mips::MFLO; 00158 BuildMI(MBB, I, get(Opc), DestReg); 00159 } else 00160 // DestRC != SrcRC, Can't copy this register 00161 return false; 00162 00163 return true; 00164 } 00165 00166 if (DestRC == Mips::CPURegsRegisterClass) 00167 BuildMI(MBB, I, get(Mips::ADDu), DestReg).addReg(Mips::ZERO) 00168 .addReg(SrcReg); 00169 else if (DestRC == Mips::FGR32RegisterClass) 00170 BuildMI(MBB, I, get(Mips::FMOV_SO32), DestReg).addReg(SrcReg); 00171 else if (DestRC == Mips::AFGR32RegisterClass) 00172 BuildMI(MBB, I, get(Mips::FMOV_AS32), DestReg).addReg(SrcReg); 00173 else if (DestRC == Mips::AFGR64RegisterClass) 00174 BuildMI(MBB, I, get(Mips::FMOV_D32), DestReg).addReg(SrcReg); 00175 else 00176 // Can't copy this register 00177 return false; 00178 00179 return true; 00180 } 00181 00182 void MipsInstrInfo:: 00183 storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 00184 unsigned SrcReg, bool isKill, int FI, 00185 const TargetRegisterClass *RC) const 00186 { 00187 unsigned Opc; 00188 if (RC == Mips::CPURegsRegisterClass) 00189 Opc = Mips::SW; 00190 else if (RC == Mips::FGR32RegisterClass) 00191 Opc = Mips::SWC1; 00192 else if (RC == Mips::AFGR32RegisterClass) 00193 Opc = Mips::SWC1A; 00194 else if (RC == Mips::AFGR64RegisterClass) 00195 Opc = Mips::SDC1; 00196 else 00197 assert(0 && "Can't store this register to stack slot"); 00198 00199 BuildMI(MBB, I, get(Opc)).addReg(SrcReg, false, false, isKill) 00200 .addImm(0).addFrameIndex(FI); 00201 } 00202 00203 void MipsInstrInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, 00204 bool isKill, SmallVectorImpl<MachineOperand> &Addr, 00205 const TargetRegisterClass *RC, SmallVectorImpl<MachineInstr*> &NewMIs) const 00206 { 00207 unsigned Opc; 00208 if (RC == Mips::CPURegsRegisterClass) 00209 Opc = Mips::SW; 00210 else if (RC == Mips::FGR32RegisterClass) 00211 Opc = Mips::SWC1; 00212 else if (RC == Mips::AFGR32RegisterClass) 00213 Opc = Mips::SWC1A; 00214 else if (RC == Mips::AFGR64RegisterClass) 00215 Opc = Mips::SDC1; 00216 else 00217 assert(0 && "Can't store this register"); 00218 00219 MachineInstrBuilder MIB = BuildMI(MF, get(Opc)) 00220 .addReg(SrcReg, false, false, isKill); 00221 for (unsigned i = 0, e = Addr.size(); i != e; ++i) { 00222 MachineOperand &MO = Addr[i]; 00223 if (MO.isReg()) 00224 MIB.addReg(MO.getReg()); 00225 else if (MO.isImm()) 00226 MIB.addImm(MO.getImm()); 00227 else 00228 MIB.addFrameIndex(MO.getIndex()); 00229 } 00230 NewMIs.push_back(MIB); 00231 return; 00232 } 00233 00234 void MipsInstrInfo:: 00235 loadRegFromStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, 00236 unsigned DestReg, int FI, 00237 const TargetRegisterClass *RC) const 00238 { 00239 unsigned Opc; 00240 if (RC == Mips::CPURegsRegisterClass) 00241 Opc = Mips::LW; 00242 else if (RC == Mips::FGR32RegisterClass) 00243 Opc = Mips::LWC1; 00244 else if (RC == Mips::AFGR32RegisterClass) 00245 Opc = Mips::LWC1A; 00246 else if (RC == Mips::AFGR64RegisterClass) 00247 Opc = Mips::LDC1; 00248 else 00249 assert(0 && "Can't load this register from stack slot"); 00250 00251 BuildMI(MBB, I, get(Opc), DestReg).addImm(0).addFrameIndex(FI); 00252 } 00253 00254 void MipsInstrInfo::loadRegFromAddr(MachineFunction &MF, unsigned DestReg, 00255 SmallVectorImpl<MachineOperand> &Addr, 00256 const TargetRegisterClass *RC, 00257 SmallVectorImpl<MachineInstr*> &NewMIs) const { 00258 unsigned Opc; 00259 if (RC == Mips::CPURegsRegisterClass) 00260 Opc = Mips::LW; 00261 else if (RC == Mips::FGR32RegisterClass) 00262 Opc = Mips::LWC1; 00263 else if (RC == Mips::AFGR32RegisterClass) 00264 Opc = Mips::LWC1A; 00265 else if (RC == Mips::AFGR64RegisterClass) 00266 Opc = Mips::LDC1; 00267 else 00268 assert(0 && "Can't load this register"); 00269 00270 MachineInstrBuilder MIB = BuildMI(MF, get(Opc), DestReg); 00271 for (unsigned i = 0, e = Addr.size(); i != e; ++i) { 00272 MachineOperand &MO = Addr[i]; 00273 if (MO.isReg()) 00274 MIB.addReg(MO.getReg()); 00275 else if (MO.isImm()) 00276 MIB.addImm(MO.getImm()); 00277 else 00278 MIB.addFrameIndex(MO.getIndex()); 00279 } 00280 NewMIs.push_back(MIB); 00281 return; 00282 } 00283 00284 MachineInstr *MipsInstrInfo:: 00285 foldMemoryOperandImpl(MachineFunction &MF, 00286 MachineInstr* MI, 00287 const SmallVectorImpl<unsigned> &Ops, int FI) const 00288 { 00289 if (Ops.size() != 1) return NULL; 00290 00291 MachineInstr *NewMI = NULL; 00292 00293 switch (MI->getOpcode()) { 00294 case Mips::ADDu: 00295 if ((MI->getOperand(0).isReg()) && 00296 (MI->getOperand(1).isReg()) && 00297 (MI->getOperand(1).getReg() == Mips::ZERO) && 00298 (MI->getOperand(2).isReg())) { 00299 if (Ops[0] == 0) { // COPY -> STORE 00300 unsigned SrcReg = MI->getOperand(2).getReg(); 00301 bool isKill = MI->getOperand(2).isKill(); 00302 NewMI = BuildMI(MF, get(Mips::SW)).addReg(SrcReg, false, false, isKill) 00303 .addImm(0).addFrameIndex(FI); 00304 } else { // COPY -> LOAD 00305 unsigned DstReg = MI->getOperand(0).getReg(); 00306 bool isDead = MI->getOperand(0).isDead(); 00307 NewMI = BuildMI(MF, get(Mips::LW)) 00308 .addReg(DstReg, true, false, false, isDead) 00309 .addImm(0).addFrameIndex(FI); 00310 } 00311 } 00312 break; 00313 case Mips::FMOV_SO32: 00314 case Mips::FMOV_AS32: 00315 case Mips::FMOV_D32: 00316 if ((MI->getOperand(0).isReg()) && 00317 (MI->getOperand(1).isReg())) { 00318 const TargetRegisterClass 00319 *RC = RI.getRegClass(MI->getOperand(0).getReg()); 00320 unsigned StoreOpc, LoadOpc; 00321 00322 if (RC == Mips::FGR32RegisterClass) { 00323 LoadOpc = Mips::LWC1; StoreOpc = Mips::SWC1; 00324 } else if (RC == Mips::AFGR32RegisterClass) { 00325 LoadOpc = Mips::LWC1A; StoreOpc = Mips::SWC1A; 00326 } else if (RC == Mips::AFGR64RegisterClass) { 00327 LoadOpc = Mips::LDC1; StoreOpc = Mips::SDC1; 00328 } else 00329 assert(0 && "foldMemoryOperandImpl register unknown"); 00330 00331 if (Ops[0] == 0) { // COPY -> STORE 00332 unsigned SrcReg = MI->getOperand(1).getReg(); 00333 bool isKill = MI->getOperand(1).isKill(); 00334 NewMI = BuildMI(MF, get(StoreOpc)).addReg(SrcReg, false, false, isKill) 00335 .addImm(0).addFrameIndex(FI) ; 00336 } else { // COPY -> LOAD 00337 unsigned DstReg = MI->getOperand(0).getReg(); 00338 bool isDead = MI->getOperand(0).isDead(); 00339 NewMI = BuildMI(MF, get(LoadOpc)) 00340 .addReg(DstReg, true, false, false, isDead) 00341 .addImm(0).addFrameIndex(FI); 00342 } 00343 } 00344 break; 00345 } 00346 00347 return NewMI; 00348 } 00349 00350 //===----------------------------------------------------------------------===// 00351 // Branch Analysis 00352 //===----------------------------------------------------------------------===// 00353 00354 /// GetCondFromBranchOpc - Return the Mips CC that matches 00355 /// the correspondent Branch instruction opcode. 00356 static Mips::CondCode GetCondFromBranchOpc(unsigned BrOpc) 00357 { 00358 switch (BrOpc) { 00359 default: return Mips::COND_INVALID; 00360 case Mips::BEQ : return Mips::COND_E; 00361 case Mips::BNE : return Mips::COND_NE; 00362 case Mips::BGTZ : return Mips::COND_GZ; 00363 case Mips::BGEZ : return Mips::COND_GEZ; 00364 case Mips::BLTZ : return Mips::COND_LZ; 00365 case Mips::BLEZ : return Mips::COND_LEZ; 00366 00367 // We dont do fp branch analysis yet! 00368 case Mips::BC1T : 00369 case Mips::BC1F : return Mips::COND_INVALID; 00370 } 00371 } 00372 00373 /// GetCondBranchFromCond - Return the Branch instruction 00374 /// opcode that matches the cc. 00375 unsigned Mips::GetCondBranchFromCond(Mips::CondCode CC) 00376 { 00377 switch (CC) { 00378 default: assert(0 && "Illegal condition code!"); 00379 case Mips::COND_E : return Mips::BEQ; 00380 case Mips::COND_NE : return Mips::BNE; 00381 case Mips::COND_GZ : return Mips::BGTZ; 00382 case Mips::COND_GEZ : return Mips::BGEZ; 00383 case Mips::COND_LZ : return Mips::BLTZ; 00384 case Mips::COND_LEZ : return Mips::BLEZ; 00385 00386 case Mips::FCOND_F: 00387 case Mips::FCOND_UN: 00388 case Mips::FCOND_EQ: 00389 case Mips::FCOND_UEQ: 00390 case Mips::FCOND_OLT: 00391 case Mips::FCOND_ULT: 00392 case Mips::FCOND_OLE: 00393 case Mips::FCOND_ULE: 00394 case Mips::FCOND_SF: 00395 case Mips::FCOND_NGLE: 00396 case Mips::FCOND_SEQ: 00397 case Mips::FCOND_NGL: 00398 case Mips::FCOND_LT: 00399 case Mips::FCOND_NGE: 00400 case Mips::FCOND_LE: 00401 case Mips::FCOND_NGT: return Mips::BC1T; 00402 00403 case Mips::FCOND_T: 00404 case Mips::FCOND_OR: 00405 case Mips::FCOND_NEQ: 00406 case Mips::FCOND_OGL: 00407 case Mips::FCOND_UGE: 00408 case Mips::FCOND_OGE: 00409 case Mips::FCOND_UGT: 00410 case Mips::FCOND_OGT: 00411 case Mips::FCOND_ST: 00412 case Mips::FCOND_GLE: 00413 case Mips::FCOND_SNE: 00414 case Mips::FCOND_GL: 00415 case Mips::FCOND_NLT: 00416 case Mips::FCOND_GE: 00417 case Mips::FCOND_NLE: 00418 case Mips::FCOND_GT: return Mips::BC1F; 00419 } 00420 } 00421 00422 /// GetOppositeBranchCondition - Return the inverse of the specified 00423 /// condition, e.g. turning COND_E to COND_NE. 00424 Mips::CondCode Mips::GetOppositeBranchCondition(Mips::CondCode CC) 00425 { 00426 switch (CC) { 00427 default: assert(0 && "Illegal condition code!"); 00428 case Mips::COND_E : return Mips::COND_NE; 00429 case Mips::COND_NE : return Mips::COND_E; 00430 case Mips::COND_GZ : return Mips::COND_LEZ; 00431 case Mips::COND_GEZ : return Mips::COND_LZ; 00432 case Mips::COND_LZ : return Mips::COND_GEZ; 00433 case Mips::COND_LEZ : return Mips::COND_GZ; 00434 case Mips::FCOND_F : return Mips::FCOND_T; 00435 case Mips::FCOND_UN : return Mips::FCOND_OR; 00436 case Mips::FCOND_EQ : return Mips::FCOND_NEQ; 00437 case Mips::FCOND_UEQ: return Mips::FCOND_OGL; 00438 case Mips::FCOND_OLT: return Mips::FCOND_UGE; 00439 case Mips::FCOND_ULT: return Mips::FCOND_OGE; 00440 case Mips::FCOND_OLE: return Mips::FCOND_UGT; 00441 case Mips::FCOND_ULE: return Mips::FCOND_OGT; 00442 case Mips::FCOND_SF: return Mips::FCOND_ST; 00443 case Mips::FCOND_NGLE:return Mips::FCOND_GLE; 00444 case Mips::FCOND_SEQ: return Mips::FCOND_SNE; 00445 case Mips::FCOND_NGL: return Mips::FCOND_GL; 00446 case Mips::FCOND_LT: return Mips::FCOND_NLT; 00447 case Mips::FCOND_NGE: return Mips::FCOND_GE; 00448 case Mips::FCOND_LE: return Mips::FCOND_NLE; 00449 case Mips::FCOND_NGT: return Mips::FCOND_GT; 00450 } 00451 } 00452 00453 bool MipsInstrInfo::AnalyzeBranch(MachineBasicBlock &MBB, 00454 MachineBasicBlock *&TBB, 00455 MachineBasicBlock *&FBB, 00456 SmallVectorImpl<MachineOperand> &Cond, 00457 bool AllowModify) const 00458 { 00459 // If the block has no terminators, it just falls into the block after it. 00460 MachineBasicBlock::iterator I = MBB.end(); 00461 if (I == MBB.begin() || !isUnpredicatedTerminator(--I)) 00462 return false; 00463 00464 // Get the last instruction in the block. 00465 MachineInstr *LastInst = I; 00466 00467 // If there is only one terminator instruction, process it. 00468 unsigned LastOpc = LastInst->getOpcode(); 00469 if (I == MBB.begin() || !isUnpredicatedTerminator(--I)) { 00470 if (!LastInst->getDesc().isBranch()) 00471 return true; 00472 00473 // Unconditional branch 00474 if (LastOpc == Mips::J) { 00475 TBB = LastInst->getOperand(0).getMBB(); 00476 return false; 00477 } 00478 00479 Mips::CondCode BranchCode = GetCondFromBranchOpc(LastInst->getOpcode()); 00480 if (BranchCode == Mips::COND_INVALID) 00481 return true; // Can't handle indirect branch. 00482 00483 // Conditional branch 00484 // Block ends with fall-through condbranch. 00485 if (LastOpc != Mips::COND_INVALID) { 00486 int LastNumOp = LastInst->getNumOperands(); 00487 00488 TBB = LastInst->getOperand(LastNumOp-1).getMBB(); 00489 Cond.push_back(MachineOperand::CreateImm(BranchCode)); 00490 00491 for (int i=0; i<LastNumOp-1; i++) { 00492 Cond.push_back(LastInst->getOperand(i)); 00493 } 00494 00495 return false; 00496 } 00497 } 00498 00499 // Get the instruction before it if it is a terminator. 00500 MachineInstr *SecondLastInst = I; 00501 00502 // If there are three terminators, we don't know what sort of block this is. 00503 if (SecondLastInst && I != MBB.begin() && isUnpredicatedTerminator(--I)) 00504 return true; 00505 00506 // If the block ends with Mips::J and a Mips::BNE/Mips::BEQ, handle it. 00507 unsigned SecondLastOpc = SecondLastInst->getOpcode(); 00508 Mips::CondCode BranchCode = GetCondFromBranchOpc(SecondLastOpc); 00509 00510 if (BranchCode != Mips::COND_INVALID && LastOpc == Mips::J) { 00511 int SecondNumOp = SecondLastInst->getNumOperands(); 00512 00513 TBB = SecondLastInst->getOperand(SecondNumOp-1).getMBB(); 00514 Cond.push_back(MachineOperand::CreateImm(BranchCode)); 00515 00516 for (int i=0; i<SecondNumOp-1; i++) { 00517 Cond.push_back(SecondLastInst->getOperand(i)); 00518 } 00519 00520 FBB = LastInst->getOperand(0).getMBB(); 00521 return false; 00522 } 00523 00524 // If the block ends with two unconditional branches, handle it. The last 00525 // one is not executed, so remove it. 00526 if ((SecondLastOpc == Mips::J) && (LastOpc == Mips::J)) { 00527 TBB = SecondLastInst->getOperand(0).getMBB(); 00528 I = LastInst; 00529 if (AllowModify) 00530 I->eraseFromParent(); 00531 return false; 00532 } 00533 00534 // Otherwise, can't handle this. 00535 return true; 00536 } 00537 00538 unsigned MipsInstrInfo:: 00539 InsertBranch(MachineBasicBlock &MBB, MachineBasicBlock *TBB, 00540 MachineBasicBlock *FBB, 00541 const SmallVectorImpl<MachineOperand> &Cond) const { 00542 // Shouldn't be a fall through. 00543 assert(TBB && "InsertBranch must not be told to insert a fallthrough"); 00544 assert((Cond.size() == 3 || Cond.size() == 2 || Cond.size() == 0) && 00545 "Mips branch conditions can have two|three components!"); 00546 00547 if (FBB == 0) { // One way branch. 00548 if (Cond.empty()) { 00549 // Unconditional branch? 00550 BuildMI(&MBB, get(Mips::J)).addMBB(TBB); 00551 } else { 00552 // Conditional branch. 00553 unsigned Opc = GetCondBranchFromCond((Mips::CondCode)Cond[0].getImm()); 00554 const TargetInstrDesc &TID = get(Opc); 00555 00556 if (TID.getNumOperands() == 3) 00557 BuildMI(&MBB, TID).addReg(Cond[1].getReg()) 00558 .addReg(Cond[2].getReg()) 00559 .addMBB(TBB); 00560 else 00561 BuildMI(&MBB, TID).addReg(Cond[1].getReg()) 00562 .addMBB(TBB); 00563 00564 } 00565 return 1; 00566 } 00567 00568 // Two-way Conditional branch. 00569 unsigned Opc = GetCondBranchFromCond((Mips::CondCode)Cond[0].getImm()); 00570 const TargetInstrDesc &TID = get(Opc); 00571 00572 if (TID.getNumOperands() == 3) 00573 BuildMI(&MBB, TID).addReg(Cond[1].getReg()).addReg(Cond[2].getReg()) 00574 .addMBB(TBB); 00575 else 00576 BuildMI(&MBB, TID).addReg(Cond[1].getReg()).addMBB(TBB); 00577 00578 BuildMI(&MBB, get(Mips::J)).addMBB(FBB); 00579 return 2; 00580 } 00581 00582 unsigned MipsInstrInfo:: 00583 RemoveBranch(MachineBasicBlock &MBB) const 00584 { 00585 MachineBasicBlock::iterator I = MBB.end(); 00586 if (I == MBB.begin()) return 0; 00587 --I; 00588 if (I->getOpcode() != Mips::J && 00589 GetCondFromBranchOpc(I->getOpcode()) == Mips::COND_INVALID) 00590 return 0; 00591 00592 // Remove the branch. 00593 I->eraseFromParent(); 00594 00595 I = MBB.end(); 00596 00597 if (I == MBB.begin()) return 1; 00598 --I; 00599 if (GetCondFromBranchOpc(I->getOpcode()) == Mips::COND_INVALID) 00600 return 1; 00601 00602 // Remove the branch. 00603 I->eraseFromParent(); 00604 return 2; 00605 } 00606 00607 /// BlockHasNoFallThrough - Analyze if MachineBasicBlock does not 00608 /// fall-through into its successor block. 00609 bool MipsInstrInfo:: 00610 BlockHasNoFallThrough(const MachineBasicBlock &MBB) const 00611 { 00612 if (MBB.empty()) return false; 00613 00614 switch (MBB.back().getOpcode()) { 00615 case Mips::RET: // Return. 00616 case Mips::JR: // Indirect branch. 00617 case Mips::J: // Uncond branch. 00618 return true; 00619 default: return false; 00620 } 00621 } 00622 00623 /// ReverseBranchCondition - Return the inverse opcode of the 00624 /// specified Branch instruction. 00625 bool MipsInstrInfo:: 00626 ReverseBranchCondition(SmallVectorImpl<MachineOperand> &Cond) const 00627 { 00628 assert( (Cond.size() == 3 || Cond.size() == 2) && 00629 "Invalid Mips branch condition!"); 00630 Cond[0].setImm(GetOppositeBranchCondition((Mips::CondCode)Cond[0].getImm())); 00631 return false; 00632 }