Moved implementation of class UltraSparcInstrInfo here.
authorVikram S. Adve <vadve@cs.uiuc.edu>
Thu, 18 Oct 2001 00:01:48 +0000 (00:01 +0000)
committerVikram S. Adve <vadve@cs.uiuc.edu>
Thu, 18 Oct 2001 00:01:48 +0000 (00:01 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@861 91177308-0d34-0410-b5e6-96231b3b80d8

lib/Target/SparcV9/SparcV9InstrInfo.cpp [new file with mode: 0644]

diff --git a/lib/Target/SparcV9/SparcV9InstrInfo.cpp b/lib/Target/SparcV9/SparcV9InstrInfo.cpp
new file mode 100644 (file)
index 0000000..6b6a406
--- /dev/null
@@ -0,0 +1,143 @@
+// $Id$
+//***************************************************************************
+// File:
+//     SparcInstrInfo.cpp
+// 
+// Purpose:
+//     
+// History:
+//     10/15/01         -  Vikram Adve  -  Created
+//**************************************************************************/
+
+
+#include "SparcInternals.h"
+#include "SparcInstrSelectionSupport.h"
+#include "llvm/Target/Sparc.h"
+#include "llvm/CodeGen/InstrSelection.h"
+#include "llvm/CodeGen/InstrSelectionSupport.h"
+#include "llvm/CodeGen/MachineInstr.h"
+#include "llvm/ConstPoolVals.h"
+#include "llvm/Type.h"
+
+
+//************************ Internal Functions ******************************/
+
+
+static inline MachineInstr*
+CreateIntSetInstruction(int64_t C, bool isSigned, Value* dest)
+{
+  MachineInstr* minstr;
+  if (isSigned)
+    {
+      minstr = new MachineInstr(SETSW);
+      minstr->SetMachineOperand(0, MachineOperand::MO_SignExtendedImmed, C);
+    }
+  else
+    {
+      minstr = new MachineInstr(SETUW);
+      minstr->SetMachineOperand(0, MachineOperand::MO_UnextendedImmed, C);
+    }
+  
+  minstr->SetMachineOperand(1, MachineOperand::MO_VirtualRegister, dest);
+  
+  return minstr;
+}
+
+//************************* External Classes *******************************/
+
+//---------------------------------------------------------------------------
+// class UltraSparcInstrInfo 
+// 
+// Purpose:
+//   Information about individual instructions.
+//   Most information is stored in the SparcMachineInstrDesc array above.
+//   Other information is computed on demand, and most such functions
+//   default to member functions in base class MachineInstrInfo. 
+//---------------------------------------------------------------------------
+
+/*ctor*/
+UltraSparcInstrInfo::UltraSparcInstrInfo()
+  : MachineInstrInfo(SparcMachineInstrDesc,
+                    /*descSize = */ NUM_TOTAL_OPCODES,
+                    /*numRealOpCodes = */ NUM_REAL_OPCODES)
+{
+}
+
+
+// Create an instruction sequence to put the constant `val' into
+// the virtual register `dest'.  `val' may be a ConstPoolVal or a
+// GlobalValue, viz., the constant address of a global variable or function.
+// The generated instructions are returned in `minstrVec'.
+// Any temp. registers (TmpInstruction) created are returned in `tempVec'.
+// 
+void
+UltraSparcInstrInfo::CreateCodeToLoadConst(Value* val,
+                                       Instruction* dest,
+                                       vector<MachineInstr*>& minstrVec,
+                                       vector<TmpInstruction*>& tempVec) const
+{
+  MachineInstr* minstr;
+  
+  assert(isa<ConstPoolVal>(val) || isa<GlobalValue>(val) &&
+         "I only know about constant values and global addresses");
+  
+  // Use a "set" instruction for known constants that can go in an integer reg.
+  // Use a "load" instruction for all other constants, in particular,
+  // floating point constants and addresses of globals.
+  // 
+  const Type* valType = val->getType();
+  
+  if (valType->isIntegral() || valType == Type::BoolTy)
+    {
+      bool isValidConstant;
+      int64_t C = GetConstantValueAsSignedInt(val, isValidConstant);
+      assert(isValidConstant && "Unrecognized constant");
+      minstr = CreateIntSetInstruction(C, valType->isSigned(), dest);
+      minstrVec.push_back(minstr);
+    }
+  else
+    {
+      // Make an instruction sequence to load the constant, viz:
+      //            SETSW <addr-of-constant>, addrReg
+      //            LOAD  /*addr*/ addrReg, /*offset*/ 0, dest
+      // Only the SETSW is needed if `val' is a GlobalValue, i.e,. it is
+      // itself a constant address.  Otherwise, both are needed.
+      
+      Value* addrVal;
+      int64_t zeroOffset = 0; // to avoid ambiguity with (Value*) 0
+      
+      if (isa<ConstPoolVal>(val))
+        {
+          // Create another TmpInstruction for the hidden integer register
+          TmpInstruction* addrReg =
+            new TmpInstruction(Instruction::UserOp1, val, NULL);
+          tempVec.push_back(addrReg);
+          addrVal = addrReg;
+        }
+      else
+        addrVal = dest;
+      
+      minstr = new MachineInstr(SETUW);
+      minstr->SetMachineOperand(0, MachineOperand::MO_PCRelativeDisp, val);
+      minstr->SetMachineOperand(1, MachineOperand::MO_VirtualRegister,addrVal);
+      minstrVec.push_back(minstr);
+      
+      if (isa<ConstPoolVal>(val))
+        {
+          // addrVal->addMachineInstruction(minstr);
+      
+          minstr = new MachineInstr(ChooseLoadInstruction(val->getType()));
+          minstr->SetMachineOperand(0, MachineOperand::MO_VirtualRegister,
+                                       addrVal);
+          minstr->SetMachineOperand(1, MachineOperand::MO_SignExtendedImmed,
+                                       zeroOffset);
+          minstr->SetMachineOperand(2, MachineOperand::MO_VirtualRegister,
+                                       dest);
+          minstrVec.push_back(minstr);
+        }
+    }
+}
+
+
+//************************ External Functions ******************************/
+