// Replace Br with a branch which has the opposite condition code and a // MachineBasicBlock operand MBBOpnd. void MipsLongBranch::replaceBranch(MachineBasicBlock &MBB, Iter Br, const DebugLoc &DL, MachineBasicBlock *MBBOpnd) { const MipsInstrInfo *TII = static_cast<const MipsInstrInfo *>( MBB.getParent()->getSubtarget().getInstrInfo()); unsigned NewOpc = TII->getOppositeBranchOpc(Br->getOpcode()); const MCInstrDesc &NewDesc = TII->get(NewOpc); MachineInstrBuilder MIB = BuildMI(MBB, Br, DL, NewDesc); for (unsigned I = 0, E = Br->getDesc().getNumOperands(); I < E; ++I) { MachineOperand &MO = Br->getOperand(I); if (!MO.isReg()) { assert(MO.isMBB() && "MBB operand expected."); break; } MIB.addReg(MO.getReg()); } MIB.addMBB(MBBOpnd); if (Br->hasDelaySlot()) { // Bundle the instruction in the delay slot to the newly created branch // and erase the original branch. assert(Br->isBundledWithSucc()); MachineBasicBlock::instr_iterator II(Br); MIBundleBuilder(&*MIB).append((++II)->removeFromBundle()); } Br->eraseFromParent(); }
bool Filler::searchSuccBBs(MachineBasicBlock &MBB, Iter Slot) const { if (DisableSuccBBSearch) return false; MachineBasicBlock *SuccBB = selectSuccBB(MBB); if (!SuccBB) return false; RegDefsUses RegDU(*MBB.getParent()->getSubtarget().getRegisterInfo()); bool HasMultipleSuccs = false; BB2BrMap BrMap; std::unique_ptr<InspectMemInstr> IM; Iter Filler; auto *Fn = MBB.getParent(); // Iterate over SuccBB's predecessor list. for (MachineBasicBlock::pred_iterator PI = SuccBB->pred_begin(), PE = SuccBB->pred_end(); PI != PE; ++PI) if (!examinePred(**PI, *SuccBB, RegDU, HasMultipleSuccs, BrMap)) return false; // Do not allow moving instructions which have unallocatable register operands // across basic block boundaries. RegDU.setUnallocatableRegs(*Fn); // Only allow moving loads from stack or constants if any of the SuccBB's // predecessors have multiple successors. if (HasMultipleSuccs) { IM.reset(new LoadFromStackOrConst()); } else { const MachineFrameInfo *MFI = Fn->getFrameInfo(); IM.reset(new MemDefsUses(Fn->getDataLayout(), MFI)); } if (!searchRange(MBB, SuccBB->begin(), SuccBB->end(), RegDU, *IM, Slot, Filler)) return false; insertDelayFiller(Filler, BrMap); addLiveInRegs(Filler, *SuccBB); Filler->eraseFromParent(); return true; }
// Replace Br with a branch which has the opposite condition code and a // MachineBasicBlock operand MBBOpnd. void MipsLongBranch::replaceBranch(MachineBasicBlock &MBB, Iter Br, DebugLoc DL, MachineBasicBlock *MBBOpnd) { const MipsInstrInfo *TII = static_cast<const MipsInstrInfo*>(TM.getInstrInfo()); unsigned NewOpc = TII->getOppositeBranchOpc(Br->getOpcode()); const MCInstrDesc &NewDesc = TII->get(NewOpc); MachineInstrBuilder MIB = BuildMI(MBB, Br, DL, NewDesc); for (unsigned I = 0, E = Br->getDesc().getNumOperands(); I < E; ++I) { MachineOperand &MO = Br->getOperand(I); if (!MO.isReg()) { assert(MO.isMBB() && "MBB operand expected."); break; } MIB.addReg(MO.getReg()); } MIB.addMBB(MBBOpnd); Br->eraseFromParent(); }