add a hook to allow targets to hack on inline asms to lower them to llvm
authorChris Lattner <sabre@nondot.org>
Wed, 29 Nov 2006 01:12:32 +0000 (01:12 +0000)
committerChris Lattner <sabre@nondot.org>
Wed, 29 Nov 2006 01:12:32 +0000 (01:12 +0000)
when they want to.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@31997 91177308-0d34-0410-b5e6-96231b3b80d8

include/llvm/Target/TargetAsmInfo.h
lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp

index 2c695e9d73e30d6e389189f80b7fdbea753795c4..28c144afa4781e0bf923b573bef8bc990d185449 100644 (file)
@@ -20,9 +20,8 @@
 #include "llvm/Support/DataTypes.h"
 
 namespace llvm {
-
-  // Forward declaration.
   class TargetMachine;
+  class CallInst;
 
   /// TargetAsmInfo - This class is intended to be used as a base class for asm
   /// properties and features specific to the target.
@@ -286,8 +285,15 @@ namespace llvm {
     /// Measure the specified inline asm to determine an approximation of its
     /// length.
     unsigned getInlineAsmLength(const char *Str) const;
+
+    /// ExpandInlineAsm - This hook allows the target to expand an inline asm
+    /// call to be explicit llvm code if it wants to.  This is useful for
+    /// turning simple inline asms into LLVM intrinsics, which gives the
+    /// compiler more information about the behavior of the code.
+    virtual bool ExpandInlineAsm(CallInst *CI) const {
+      return false;
+    }
     
-    //
     // Accessors.
     //
     const char *getTextSection() const {
index 0257e1b77534db9a434d538c86b3475bc84777b1..fbfd3f7b710bfcafe0cf94c0a1eda40bd77c5846 100644 (file)
@@ -33,6 +33,7 @@
 #include "llvm/CodeGen/SelectionDAG.h"
 #include "llvm/CodeGen/SSARegMap.h"
 #include "llvm/Target/MRegisterInfo.h"
+#include "llvm/Target/TargetAsmInfo.h"
 #include "llvm/Target/TargetData.h"
 #include "llvm/Target/TargetFrameInfo.h"
 #include "llvm/Target/TargetInstrInfo.h"
@@ -3780,7 +3781,17 @@ bool SelectionDAGISel::runOnFunction(Function &Fn) {
     
     for (BasicBlock::iterator BBI = BB->begin(), E = BB->end(); BBI != E; ) {
       Instruction *I = BBI++;
-      if (GetElementPtrInst *GEPI = dyn_cast<GetElementPtrInst>(I)) {
+      
+      if (CallInst *CI = dyn_cast<CallInst>(I)) {
+        // If we found an inline asm expession, and if the target knows how to
+        // lower it to normal LLVM code, do so now.
+        if (isa<InlineAsm>(CI->getCalledValue()))
+          if (const TargetAsmInfo *TAI = 
+                TLI.getTargetMachine().getTargetAsmInfo()) {
+            if (TAI->ExpandInlineAsm(CI))
+              BBI = BB->begin();
+          }
+      } else if (GetElementPtrInst *GEPI = dyn_cast<GetElementPtrInst>(I)) {
         MadeChange |= OptimizeGEPExpression(GEPI, TLI.getTargetData());
       } else if (CastInst *CI = dyn_cast<CastInst>(I)) {
         // If the source of the cast is a constant, then this should have
@@ -4004,6 +4015,7 @@ void SelectionDAGISel::BuildSelectionDAG(SelectionDAG &DAG, BasicBlock *LLVMBB,
       
       unsigned Reg;
       Value *PHIOp = PN->getIncomingValueForBlock(LLVMBB);
+      
       if (Constant *C = dyn_cast<Constant>(PHIOp)) {
         unsigned &RegOut = ConstantsOut[C];
         if (RegOut == 0) {