Add a target callback for FastISel.
authorDan Gohman <gohman@apple.com>
Thu, 28 Aug 2008 23:21:34 +0000 (23:21 +0000)
committerDan Gohman <gohman@apple.com>
Thu, 28 Aug 2008 23:21:34 +0000 (23:21 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@55512 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/CodeGen/FastISel.h
lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
lib/Target/X86/X86FastISel.cpp
utils/TableGen/FastISelEmitter.cpp

index 20a923b1de9c0d65879e24b99997279b65884c31..364f82e0b48dce875df2aff67f6913f2bc37b7ec 100644 (file)
@@ -52,10 +52,21 @@ public:
   /// the generated MachineInstrs.
   BasicBlock::iterator
   SelectInstructions(BasicBlock::iterator Begin, BasicBlock::iterator End,
-                     DenseMap<const Value*, unsigned> &ValueMap,
-                     DenseMap<const BasicBlock*, MachineBasicBlock *> &MBBMap,
+                     DenseMap<const Value *, unsigned> &ValueMap,
+                     DenseMap<const BasicBlock *, MachineBasicBlock *> &MBBMap,
                      MachineBasicBlock *MBB);
 
+  /// TargetSelectInstruction - This method is called by target-independent
+  /// code when the normal FastISel process fails to select an instruction.
+  /// This gives targets a chance to emit code for anything that doesn't
+  /// fit into FastISel's framework. It returns true if it was successful.
+  ///
+  virtual bool
+  TargetSelectInstruction(Instruction *I,
+                          DenseMap<const Value *, unsigned> &ValueMap,
+                      DenseMap<const BasicBlock *, MachineBasicBlock *> &MBBMap,
+                          MachineBasicBlock *MBB) = 0;
+
   virtual ~FastISel();
 
 protected:
index f2246cac2c7c54d52d77f7848aecbf9de283fdd3..9b982f4fb4a91092df9021f35674a32dbc19cdd9 100644 (file)
@@ -5757,10 +5757,15 @@ void SelectionDAGISel::SelectAllBasicBlocks(Function &Fn, MachineFunction &MF) {
           Begin = F->SelectInstructions(Begin, End, FuncInfo->ValueMap,
                                         FuncInfo->MBBMap, BB);
 
+          // If the "fast" selector selected the entire block, we're done.
           if (Begin == End)
-            // The "fast" selector selected the entire block, so we're done.
             break;
 
+          // Next, try calling the target to attempt to handle the instruction.
+          if (F->TargetSelectInstruction(Begin, FuncInfo->ValueMap,
+                                         FuncInfo->MBBMap, BB))
+            continue;
+
           // Handle certain instructions as single-LLVM-Instruction blocks.
           if (isa<CallInst>(Begin) || isa<LoadInst>(Begin) ||
               isa<StoreInst>(Begin)) {
@@ -5783,7 +5788,7 @@ void SelectionDAGISel::SelectAllBasicBlocks(Function &Fn, MachineFunction &MF) {
             // The "fast" selector couldn't handle something and bailed.
             // For the purpose of debugging, just abort.
 #ifndef NDEBUG
-              Begin->dump();
+            Begin->dump();
 #endif
             assert(0 && "FastISel didn't select the entire block");
           }
index f049a4d363de5b1757297d66c25393f273528403..96bdb50fd699dfe3a3e42c7797599c68975b99c4 100644 (file)
 #include "X86FastISel.h"
 #include "X86TargetMachine.h"
 #include "X86GenFastISel.inc"
+
+namespace llvm {
+
+namespace X86 {
+
+bool
+FastISel::TargetSelectInstruction(Instruction *I,
+                                  DenseMap<const Value *, unsigned> &ValueMap,
+                      DenseMap<const BasicBlock *, MachineBasicBlock *> &MBBMap,
+                                  MachineBasicBlock *MBB)  {
+  switch (I->getOpcode()) {
+  default: break;
+  }
+
+  return false;
+}
+
+}
+
+}
index 305158f471415495b3871e173cec7d05c60591d3..fedb44e4d0bbb984bdd9c44211554e7b184e606c 100644 (file)
@@ -351,6 +351,14 @@ void FastISelMap::PrintClass(std::ostream &OS) {
   }
   OS << "\n";
 
+  OS << "bool TargetSelectInstruction(Instruction *I,\n";
+  OS << "                             "
+        "DenseMap<const Value *, unsigned> &ValueMap,\n";
+  OS << "                             "
+        "DenseMap<const BasicBlock *, MachineBasicBlock *> &MBBMap,\n";
+  OS << "                             "
+        "MachineBasicBlock *MBB);\n";
+
   // Declare the Subtarget member, which is used for predicate checks.
   OS << "  const " << InstNS.substr(0, InstNS.size() - 2)
      << "Subtarget *Subtarget;\n";