1 //===- llvm/CodeGen/GlobalISel/InstructionSelect.cpp - InstructionSelect ---==// 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 /// This file implements the InstructionSelect class. 11 //===----------------------------------------------------------------------===// 12 13 #include "llvm/CodeGen/GlobalISel/InstructionSelect.h" 14 #include "llvm/ADT/PostOrderIterator.h" 15 #include "llvm/ADT/Twine.h" 16 #include "llvm/CodeGen/GlobalISel/InstructionSelector.h" 17 #include "llvm/CodeGen/GlobalISel/MachineLegalizer.h" 18 #include "llvm/CodeGen/MachineRegisterInfo.h" 19 #include "llvm/IR/Function.h" 20 #include "llvm/Support/CommandLine.h" 21 #include "llvm/Support/Debug.h" 22 #include "llvm/Target/TargetSubtargetInfo.h" 23 24 #define DEBUG_TYPE "instruction-select" 25 26 using namespace llvm; 27 28 char InstructionSelect::ID = 0; 29 INITIALIZE_PASS(InstructionSelect, DEBUG_TYPE, 30 "Select target instructions out of generic instructions", 31 false, false); 32 33 InstructionSelect::InstructionSelect() : MachineFunctionPass(ID) { 34 initializeInstructionSelectPass(*PassRegistry::getPassRegistry()); 35 } 36 37 static void reportSelectionError(const MachineInstr &MI, const Twine &Message) { 38 const MachineFunction &MF = *MI.getParent()->getParent(); 39 std::string ErrStorage; 40 raw_string_ostream Err(ErrStorage); 41 Err << Message << ":\nIn function: " << MF.getName() << '\n' << MI << '\n'; 42 report_fatal_error(Err.str()); 43 } 44 45 bool InstructionSelect::runOnMachineFunction(MachineFunction &MF) { 46 DEBUG(dbgs() << "Selecting function: " << MF.getName() << '\n'); 47 48 const InstructionSelector *ISel = MF.getSubtarget().getInstructionSelector(); 49 assert(ISel && "Cannot work without InstructionSelector"); 50 51 // FIXME: freezeReservedRegs is now done in IRTranslator, but there are many 52 // other MF/MFI fields we need to initialize. 53 54 #ifndef NDEBUG 55 // Check that our input is fully legal: we require the function to have the 56 // Legalized property, so it should be. 57 // FIXME: This should be in the MachineVerifier, but it can't use the 58 // MachineLegalizer as it's currently in the separate GlobalISel library. 59 // The RegBankSelected property is already checked in the verifier. Note 60 // that it has the same layering problem, but we only use inline methods so 61 // end up not needing to link against the GlobalISel library. 62 if (const MachineLegalizer *MLI = MF.getSubtarget().getMachineLegalizer()) 63 for (const MachineBasicBlock &MBB : MF) 64 for (const MachineInstr &MI : MBB) 65 if (isPreISelGenericOpcode(MI.getOpcode()) && !MLI->isLegal(MI)) 66 reportSelectionError(MI, "Instruction is not legal"); 67 68 // FIXME: We could introduce new blocks and will need to fix the outer loop. 69 // Until then, keep track of the number of blocks to assert that we don't. 70 const size_t NumBlocks = MF.size(); 71 #endif 72 73 for (MachineBasicBlock *MBB : post_order(&MF)) { 74 for (MachineBasicBlock::reverse_iterator MII = MBB->rbegin(), 75 End = MBB->rend(); 76 MII != End;) { 77 MachineInstr &MI = *MII++; 78 DEBUG(dbgs() << "Selecting: " << MI << '\n'); 79 if (!ISel->select(MI)) 80 reportSelectionError(MI, "Cannot select"); 81 // FIXME: It would be nice to dump all inserted instructions. It's not 82 // obvious how, esp. considering select() can insert after MI. 83 } 84 } 85 86 assert(MF.size() == NumBlocks && "Inserting blocks is not supported yet"); 87 88 // Now that selection is complete, there are no more generic vregs. 89 // FIXME: We're still discussing what to do with the vreg->size map: 90 // it's somewhat redundant (with the def MIs type size), but having to 91 // examine MIs is also awkward. Another alternative is to track the type on 92 // the vreg instead, but that's not ideal either, because it's saying that 93 // vregs have types, which they really don't. But then again, LLT is just 94 // a size and a "shape": it's probably the same information as regbank info. 95 MF.getRegInfo().clearVirtRegSizes(); 96 97 // FIXME: Should we accurately track changes? 98 return true; 99 } 100