MachineInstr.cpp revision e949da5bb18f89de40b6781237dfe616cba7bfc9
170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// $Id$
270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//***************************************************************************
370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// File:
470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//	MachineInstr.cpp
570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Purpose:
770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Strategy:
1070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
1170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// History:
1270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//	7/2/01	 -  Vikram Adve  -  Created
1370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//**************************************************************************/
1470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
155b79591450c47920139705712a402251af7eed79Vikram S. Adve
16822b4fb896846b87dd11a330ae13f2239329aeefChris Lattner#include "llvm/CodeGen/MachineInstr.h"
176e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve#include "llvm/Target/MachineRegInfo.h"
185b79591450c47920139705712a402251af7eed79Vikram S. Adve#include "llvm/Method.h"
1970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve#include "llvm/ConstPoolVals.h"
2070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve#include "llvm/Instruction.h"
215b79591450c47920139705712a402251af7eed79Vikram S. Adve
2270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
2370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//************************ Class Implementations **************************/
2470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
251885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve// Constructor for instructions with fixed #operands (nearly all)
2670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveMachineInstr::MachineInstr(MachineOpCode _opCode,
2770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve			   OpCodeMask    _opCodeMask)
2870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  : opCode(_opCode),
2970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    opCodeMask(_opCodeMask),
306a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve    operands(TargetInstrDescriptors[_opCode].numOperands)
3170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
321885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve  assert(TargetInstrDescriptors[_opCode].numOperands >= 0);
331885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve}
341885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve
351885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve// Constructor for instructions with variable #operands
361885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. AdveMachineInstr::MachineInstr(MachineOpCode _opCode,
371885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve			   unsigned	 numOperands,
381885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve			   OpCodeMask    _opCodeMask)
391885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve  : opCode(_opCode),
401885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve    opCodeMask(_opCodeMask),
411885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve    operands(numOperands)
421885da4f49cf32efde2d4c840365c4333a0c8579Vikram S. Adve{
4370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
4470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
4570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Advevoid
4670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveMachineInstr::SetMachineOperand(unsigned int i,
4770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve				MachineOperand::MachineOperandType operandType,
4845c171ee25619f6650e90fa5e3102d9969fd82b3Ruchira Sasanka				Value* _val, bool isdef=false)
4970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
506a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  assert(i < operands.size());
5170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  operands[i].Initialize(operandType, _val);
52149977b48a02735861697d5b4df1fe5a8592245fVikram S. Adve  operands[i].isDef = isdef ||
536e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    TargetInstrDescriptors[opCode].resultPos == (int) i;
5470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
5570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
5670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Advevoid
5770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveMachineInstr::SetMachineOperand(unsigned int i,
5870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve				MachineOperand::MachineOperandType operandType,
5945c171ee25619f6650e90fa5e3102d9969fd82b3Ruchira Sasanka				int64_t intValue, bool isdef=false)
6070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
616a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  assert(i < operands.size());
6270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  operands[i].InitializeConst(operandType, intValue);
63149977b48a02735861697d5b4df1fe5a8592245fVikram S. Adve  operands[i].isDef = isdef ||
646e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    TargetInstrDescriptors[opCode].resultPos == (int) i;
6570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
6670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
6770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Advevoid
6870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveMachineInstr::SetMachineOperand(unsigned int i,
6945c171ee25619f6650e90fa5e3102d9969fd82b3Ruchira Sasanka				unsigned int regNum, bool isdef=false)
7070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
716a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  assert(i < operands.size());
7270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  operands[i].InitializeReg(regNum);
73149977b48a02735861697d5b4df1fe5a8592245fVikram S. Adve  operands[i].isDef = isdef ||
746e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    TargetInstrDescriptors[opCode].resultPos == (int) i;
7570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
7670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
7770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Advevoid
780b03c6a492a0e09049b6c0bd127bd0ede7732aa5Ruchira SasankaMachineInstr::dump(unsigned int indent) const
7970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
8070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  for (unsigned i=0; i < indent; i++)
8170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    cout << "    ";
8270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
8370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  cout << *this;
8470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
8570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
8670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adveostream&
8770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adveoperator<< (ostream& os, const MachineInstr& minstr)
8870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
896a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  os << TargetInstrDescriptors[minstr.opCode].opCodeString;
9070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
9170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  for (unsigned i=0, N=minstr.getNumOperands(); i < N; i++)
9270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    os << "\t" << minstr.getOperand(i);
9370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
946a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve#undef DEBUG_VAL_OP_ITERATOR
956a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve#ifdef DEBUG_VAL_OP_ITERATOR
966a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  os << endl << "\tValue operands are: ";
976a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  for (MachineInstr::val_op_const_iterator vo(&minstr); ! vo.done(); ++vo)
986a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve    {
996a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve      const Value* val = *vo;
1006a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve      os << val << (vo.isDef()? "(def), " : ", ");
1016a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve    }
1026a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  os << endl;
1036a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve#endif
1046a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve
10570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  return os;
10670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
10770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
1086e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Advestatic inline ostream&
1096e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. AdveOutputOperand(ostream &os, const MachineOperand &mop)
1106e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve{
1116e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  switch (mop.getOperandType())
1126e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
1136e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_CCRegister:
1146e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_VirtualRegister:
1156e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return os << "(val " << mop.getVRegValue() << ")";
1166e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_MachineRegister:
1176e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return os << "("     << mop.getMachineRegNum() << ")";
1186e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    default:
1196e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      assert(0 && "Unknown operand type");
1206e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return os;
1216e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
122e6fdb11e1ae823d69e646e76828ccb5d427a9d3aChris Lattner}
12370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
124e6fdb11e1ae823d69e646e76828ccb5d427a9d3aChris Lattner
1256e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adveostream&
1266e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adveoperator<<(ostream &os, const MachineOperand &mop)
1276e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve{
1286e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  switch(mop.opType)
1296e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
1306e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_VirtualRegister:
1316e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_MachineRegister:
1326e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      os << "%reg";
1336e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return OutputOperand(os, mop);
1346e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_CCRegister:
1356e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      os << "%ccreg";
1366e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return OutputOperand(os, mop);
1376e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_SignExtendedImmed:
1386e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return os << mop.immedVal;
1396e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_UnextendedImmed:
1406e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return os << mop.immedVal;
1416e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    case MachineOperand::MO_PCRelativeDisp:
142e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve      {
143e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve        const Value* opVal = mop.getVRegValue();
144e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve        bool isLabel = opVal->isMethod() || opVal->isBasicBlock();
145e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve        return os << "%disp("
146e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve                  << (isLabel? "label " : "addr-of-val ")
147e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve                  << opVal << ")";
148e949da5bb18f89de40b6781237dfe616cba7bfc9Vikram S. Adve      }
1496e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    default:
1506e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      assert(0 && "Unrecognized operand type");
1516e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      break;
1526e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
153e6fdb11e1ae823d69e646e76828ccb5d427a9d3aChris Lattner
15470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  return os;
15570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
15670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
15770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
15870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//---------------------------------------------------------------------------
15970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Target-independent utility routines for creating machine instructions
16070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//---------------------------------------------------------------------------
16170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
16270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
16370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//------------------------------------------------------------------------
16470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Function Set2OperandsFromInstr
16570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Function Set3OperandsFromInstr
16670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
16770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// For the common case of 2- and 3-operand arithmetic/logical instructions,
16870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// set the m/c instr. operands directly from the VM instruction's operands.
169c2a2396e17f8fd6c78afd81368d2b80e8cfe6c42Chris Lattner// Check whether the first or second operand is 0 and can use a dedicated "0"
170c2a2396e17f8fd6c78afd81368d2b80e8cfe6c42Chris Lattner// register.
17170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Check whether the second operand should use an immediate field or register.
17270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// (First and third operands are never immediates for such instructions.)
17370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
17470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// Arguments:
17570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// canDiscardResult: Specifies that the result operand can be discarded
17670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//		     by using the dedicated "0"
17770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
17870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// op1position, op2position and resultPosition: Specify in which position
17970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//		     in the machine instruction the 3 operands (arg1, arg2
18070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//		     and result) should go.
18170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//
18270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve// RETURN VALUE: unsigned int flags, where
18370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//	flags & 0x01	=> operand 1 is constant and needs a register
18470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//	flags & 0x02	=> operand 2 is constant and needs a register
18570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve//------------------------------------------------------------------------
18670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
18770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Advevoid
18870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveSet2OperandsFromInstr(MachineInstr* minstr,
18970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      InstructionNode* vmInstrNode,
1906a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve		      const TargetMachine& target,
19170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      bool canDiscardResult,
19270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      int op1Position,
19370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      int resultPosition)
19470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
1956a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  Set3OperandsFromInstr(minstr, vmInstrNode, target,
19670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve			canDiscardResult, op1Position,
19770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve			/*op2Position*/ -1, resultPosition);
19870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
19970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
2006a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve#undef REVERT_TO_EXPLICIT_CONSTANT_CHECKS
2016a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve#ifdef REVERT_TO_EXPLICIT_CONSTANT_CHECKS
20270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adveunsigned
20370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveSet3OperandsFromInstrJUNK(MachineInstr* minstr,
2046e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			  InstructionNode* vmInstrNode,
2056e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			  const TargetMachine& target,
2066e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			  bool canDiscardResult,
2076e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			  int op1Position,
2086e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			  int op2Position,
2096e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			  int resultPosition)
21070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
21170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  assert(op1Position >= 0);
21270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  assert(resultPosition >= 0);
21370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
21470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  unsigned returnFlags = 0x0;
21570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
2165b79591450c47920139705712a402251af7eed79Vikram S. Adve  // Check if operand 1 is 0.  If so, try to use a hardwired 0 register.
21770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  Value* op1Value = vmInstrNode->leftChild()->getValue();
21870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  bool isValidConstant;
21970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  int64_t intValue = GetConstantValueAsSignedInt(op1Value, isValidConstant);
2206a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  if (isValidConstant && intValue == 0 && target.zeroRegNum >= 0)
2216a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve    minstr->SetMachineOperand(op1Position, /*regNum*/ target.zeroRegNum);
22270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  else
22370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    {
2246e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      if (op1Value->isConstant())
2256e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	{
2266e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	  // value is constant and must be loaded from constant pool
2276e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	  returnFlags = returnFlags | (1 << op1Position);
2286e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	}
229b221a763862ccaed46dee3fbf56c384981d84fbdChris Lattner      minstr->SetMachineOperand(op1Position, MachineOperand::MO_VirtualRegister,
230b221a763862ccaed46dee3fbf56c384981d84fbdChris Lattner				op1Value);
23170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    }
23270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
2335b79591450c47920139705712a402251af7eed79Vikram S. Adve  // Check if operand 2 (if any) fits in the immed. field of the instruction,
2345b79591450c47920139705712a402251af7eed79Vikram S. Adve  // or if it is 0 and can use a dedicated machine register
23570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  if (op2Position >= 0)
23670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    {
23770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve      Value* op2Value = vmInstrNode->rightChild()->getValue();
23870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve      int64_t immedValue;
23970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve      unsigned int machineRegNum;
24070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
24170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve      MachineOperand::MachineOperandType
2426a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	op2type = ChooseRegOrImmed(op2Value, minstr->getOpCode(), target,
24370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve				   /*canUseImmed*/ true,
2446a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve				   machineRegNum, immedValue);
24570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
2466a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve      if (op2type == MachineOperand::MO_MachineRegister)
2476a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	minstr->SetMachineOperand(op2Position, machineRegNum);
2486a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve      else if (op2type == MachineOperand::MO_VirtualRegister)
24970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve	{
2506e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	  if (op2Value->isConstant())
2516e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	    {
2526e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	      // value is constant and must be loaded from constant pool
2536e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	      returnFlags = returnFlags | (1 << op2Position);
2546e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	    }
2556a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	  minstr->SetMachineOperand(op2Position, op2type, op2Value);
25670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve	}
25770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve      else
2586a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	{
2596a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	  assert(op2type != MO_CCRegister);
2606a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	  minstr->SetMachineOperand(op2Position, op2type, immedValue);
2616a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve	}
26270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve    }
26370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
26470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // If operand 3 (result) can be discarded, use a dead register if one exists
2656a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  if (canDiscardResult && target.zeroRegNum >= 0)
266149977b48a02735861697d5b4df1fe5a8592245fVikram S. Adve    minstr->SetMachineOperand(resultPosition, target.zeroRegNum);
26770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  else
268149977b48a02735861697d5b4df1fe5a8592245fVikram S. Adve    minstr->SetMachineOperand(resultPosition, MachineOperand::MO_VirtualRegister, vmInstrNode->getValue());
26970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
27070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  return returnFlags;
27170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
2726a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve#endif
27370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
27470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
27570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Advevoid
27670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveSet3OperandsFromInstr(MachineInstr* minstr,
27770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      InstructionNode* vmInstrNode,
2786a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve		      const TargetMachine& target,
27970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      bool canDiscardResult,
28070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      int op1Position,
28170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      int op2Position,
28270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		      int resultPosition)
28370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
28470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  assert(op1Position >= 0);
28570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  assert(resultPosition >= 0);
28670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
28770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // operand 1
2886a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  minstr->SetMachineOperand(op1Position, MachineOperand::MO_VirtualRegister,
28970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve			    vmInstrNode->leftChild()->getValue());
29070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
29170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // operand 2 (if any)
29270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  if (op2Position >= 0)
2936a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve    minstr->SetMachineOperand(op2Position, MachineOperand::MO_VirtualRegister,
29470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve			      vmInstrNode->rightChild()->getValue());
29570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
29670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // result operand: if it can be discarded, use a dead register if one exists
2976e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  if (canDiscardResult && target.getRegInfo().getZeroRegNum() >= 0)
2986e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    minstr->SetMachineOperand(resultPosition,
2996e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			      target.getRegInfo().getZeroRegNum());
30070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  else
3016e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    minstr->SetMachineOperand(resultPosition,
3026e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve			      MachineOperand::MO_VirtualRegister, vmInstrNode->getValue());
30370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
30470bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
30570bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
30670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveMachineOperand::MachineOperandType
30770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. AdveChooseRegOrImmed(Value* val,
30870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		 MachineOpCode opCode,
3096a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve		 const TargetMachine& target,
31070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		 bool canUseImmed,
31170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		 unsigned int& getMachineRegNum,
31270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve		 int64_t& getImmedValue)
31370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve{
3146a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve  MachineOperand::MachineOperandType opType =
3156a175e01eb164baac5cc16311c474ff644ce17c1Vikram S. Adve    MachineOperand::MO_VirtualRegister;
31670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  getMachineRegNum = 0;
31770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  getImmedValue = 0;
31870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
31970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // Check for the common case first: argument is not constant
32070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  //
321990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner  ConstPoolVal *CPV = val->castConstant();
322990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner  if (!CPV) return opType;
323990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner
3246e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  if (CPV->getType() == Type::BoolTy)
3256e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
3266e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      ConstPoolBool *CPB = (ConstPoolBool*)CPV;
3276e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      if (!CPB->getValue() && target.getRegInfo().getZeroRegNum() >= 0)
3286e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	{
3296e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	  getMachineRegNum = target.getRegInfo().getZeroRegNum();
3306e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	  return MachineOperand::MO_MachineRegister;
3316e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	}
332990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner
3336e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      getImmedValue = 1;
3346e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      return MachineOperand::MO_SignExtendedImmed;
3356e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
33670bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
337990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner  if (!CPV->getType()->isIntegral()) return opType;
338990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner
33970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // Now get the constant value and check if it fits in the IMMED field.
34070bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // Take advantage of the fact that the max unsigned value will rarely
34170bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // fit into any IMMED field and ignore that case (i.e., cast smaller
34270bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  // unsigned constants to signed).
34370bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  //
344990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner  int64_t intValue;
3456e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  if (CPV->getType()->isSigned())
3466e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
3476e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      intValue = ((ConstPoolSInt*)CPV)->getValue();
3486e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
3496e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  else
3506e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
3516e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      uint64_t V = ((ConstPoolUInt*)CPV)->getValue();
3526e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      if (V >= INT64_MAX) return opType;
3536e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      intValue = (int64_t)V;
3546e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
355990f2a5a1a0b16d0dc07cee486033c0a3864334eChris Lattner
3566e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  if (intValue == 0 && target.getRegInfo().getZeroRegNum() >= 0)
3576e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
3586e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      opType = MachineOperand::MO_MachineRegister;
3596e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      getMachineRegNum = target.getRegInfo().getZeroRegNum();
3606e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
3616e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve  else if (canUseImmed &&
3626e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve	   target.getInstrInfo().constantFitsInImmedField(opCode, intValue))
3636e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    {
3646e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      opType = MachineOperand::MO_SignExtendedImmed;
3656e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve      getImmedValue = intValue;
3666e447181928b95902c38ea89e57bc835ecd83cb5Vikram S. Adve    }
36770bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve
36870bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve  return opType;
36970bc4b5d1a3795a8f41be96723cfcbccac8e1671Vikram S. Adve}
3705b79591450c47920139705712a402251af7eed79Vikram S. Adve
3715b79591450c47920139705712a402251af7eed79Vikram S. Adve
3725b79591450c47920139705712a402251af7eed79Vikram S. Advevoid
373ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira SasankaPrintMachineInstructions(const Method *const method)
374ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka{
375ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka  cout << "\n" << method->getReturnType()
376ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka       << " \"" << method->getName() << "\"" << endl;
377ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka
378ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka  for (Method::const_iterator BI = method->begin(); BI != method->end(); ++BI)
379ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka    {
380ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka      BasicBlock* bb = *BI;
381ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka      cout << "\n"
382ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka	   << (bb->hasName()? bb->getName() : "Label")
383ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka	   << " (" << bb << ")" << ":"
384ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka	   << endl;
385ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka
386ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka      MachineCodeForBasicBlock& mvec = bb->getMachineInstrVec();
387ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka      for (unsigned i=0; i < mvec.size(); i++)
388ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka	cout << "\t" << *mvec[i] << endl;
389ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka    }
390ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka  cout << endl << "End method \"" << method->getName() << "\""
391ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka       << endl << endl;
392ed8f674b9a18312886355288ac49f9a2dd5e4e94Ruchira Sasanka}
393