bool PatmosInstrInfo::AnalyzeBranch(MachineBasicBlock &MBB, MachineBasicBlock *&TBB, MachineBasicBlock *&FBB, SmallVectorImpl<MachineOperand> &Cond, bool AllowModify) const { // If the client does not want to only simplify the branch, // the output arguments must be initialized. assert(AllowModify || (TBB==0 && FBB==0 && Cond.size()==0)); // Start from the bottom of the block and work up, examining the // terminator instructions. MachineBasicBlock::iterator I = MBB.end(); while (I != MBB.begin()) { --I; if (I->isDebugValue() || I->isPseudo()) continue; // Working from the bottom, when we see a non-terminator inst, we're done. if (!isUnpredicatedTerminator(I)) break; // A terminator that isn't a (direct) branch can't easily be handled // by this analysis. if (!I->isBranch() || I->isIndirectBranch()) return true; // Handle Unconditional branches if (!isPredicated(I)) { // fix instruction, if necessary if (!I->isUnconditionalBranch()) fixOpcodeForGuard(I); // TBB is used to indicate the unconditional destination. TBB = getBranchTarget(I); if (AllowModify) { // If the block has any instructions after an uncond branch, delete them. while (llvm::next(I) != MBB.end()) llvm::next(I)->eraseFromParent(); } continue; } // Handle conditional branches if (isPredicated(I)) { // fix instruction, if necessary if (!I->isConditionalBranch()) fixOpcodeForGuard(I); // we only treat the first conditional branch in a row if (Cond.size() > 0) return true; // Get branch condition int i = I->findFirstPredOperandIdx(); assert(i != -1 ); Cond.push_back(I->getOperand(i)); // reg Cond.push_back(I->getOperand(i+1)); // flag // We've processed an unconditional branch before, // the unconditional target goes to FBB now if (TBB) FBB = TBB; // target of conditional branch goes to TBB TBB = getBranchTarget(I); continue; } // we explicitly leave or continue. llvm_unreachable("AnalyzeBranch error."); } // left the loop? then we're done return false; }