#include "SPUISelLowering.h"
#include "SPUHazardRecognizers.h"
#include "SPUFrameInfo.h"
+#include "SPURegisterNames.h"
#include "llvm/CodeGen/MachineConstantPool.h"
#include "llvm/CodeGen/MachineInstrBuilder.h"
#include "llvm/CodeGen/MachineFunction.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/MathExtras.h"
#include "llvm/Support/Compiler.h"
-#include <iostream>
#include <queue>
#include <set>
bool
isI64IntS10Immediate(ConstantSDNode *CN)
{
- return isS10Constant(CN->getValue());
+ return isS10Constant(CN->getSignExtended());
}
//! ConstantSDNode predicate for i32 sign-extended, 10-bit immediates
bool
isI32IntS10Immediate(ConstantSDNode *CN)
{
- return isS10Constant((int) CN->getValue());
+ return isS10Constant(CN->getSignExtended());
}
#if 0
bool
isI32IntU10Immediate(ConstantSDNode *CN)
{
- return isU10Constant((int) CN->getValue());
+ return isU10Constant(CN->getSignExtended());
}
//! ConstantSDNode predicate for i16 sign-extended, 10-bit immediate values
bool
isI16IntS10Immediate(ConstantSDNode *CN)
{
- return isS10Constant((short) CN->getValue());
+ return isS10Constant(CN->getSignExtended());
}
//! SDNode predicate for i16 sign-extended, 10-bit immediate values
bool
isIntS16Immediate(ConstantSDNode *CN, short &Imm)
{
- MVT::ValueType vt = CN->getValueType(0);
+ MVT vt = CN->getValueType(0);
Imm = (short) CN->getValue();
- if (vt >= MVT::i1 && vt <= MVT::i16) {
+ if (vt.getSimpleVT() >= MVT::i1 && vt.getSimpleVT() <= MVT::i16) {
return true;
} else if (vt == MVT::i32) {
int32_t i_val = (int32_t) CN->getValue();
static bool
isFPS16Immediate(ConstantFPSDNode *FPN, short &Imm)
{
- MVT::ValueType vt = FPN->getValueType(0);
+ MVT vt = FPN->getValueType(0);
if (vt == MVT::f32) {
int val = FloatToBits(FPN->getValueAPF().convertToFloat());
int sval = (int) ((val << 16) >> 16);
}
//===------------------------------------------------------------------===//
- //! MVT::ValueType to "useful stuff" mapping structure:
+ //! MVT to "useful stuff" mapping structure:
struct valtype_map_s {
- MVT::ValueType VT;
+ MVT VT;
unsigned ldresult_ins; /// LDRESULT instruction (0 = undefined)
bool ldresult_imm; /// LDRESULT instruction requires immediate?
int prefslot_byte; /// Byte offset of the "preferred" slot
const size_t n_valtype_map = sizeof(valtype_map) / sizeof(valtype_map[0]);
- const valtype_map_s *getValueTypeMapEntry(MVT::ValueType VT)
+ const valtype_map_s *getValueTypeMapEntry(MVT VT)
{
const valtype_map_s *retval = 0;
for (size_t i = 0; i < n_valtype_map; ++i) {
#ifndef NDEBUG
if (retval == 0) {
cerr << "SPUISelDAGToDAG.cpp: getValueTypeMapEntry returns NULL for "
- << MVT::getValueTypeString(VT)
+ << VT.getMVTString()
<< "\n";
abort();
}
}
}
+namespace {
+
//===--------------------------------------------------------------------===//
/// SPUDAGToDAGISel - Cell SPU-specific code to select SPU machine
/// instructions for SelectionDAG operations.
#include "SPUGenDAGISel.inc"
};
+}
+
/// InstructionSelectBasicBlock - This callback is invoked by
/// SelectionDAGISel when it has created a SelectionDAG for us to codegen.
void
SPUDAGToDAGISel::SelectAFormAddr(SDOperand Op, SDOperand N, SDOperand &Base,
SDOperand &Index) {
// These match the addr256k operand type:
- MVT::ValueType OffsVT = MVT::i16;
+ MVT OffsVT = MVT::i16;
SDOperand Zero = CurDAG->getTargetConstant(0, OffsVT);
switch (N.getOpcode()) {
bool
SPUDAGToDAGISel::SelectDForm2Addr(SDOperand Op, SDOperand N, SDOperand &Disp,
SDOperand &Base) {
- return DFormAddressPredicate(Op, N, Disp, Base, -(1 << 7), (1 << 7) - 1);
+ const int minDForm2Offset = -(1 << 7);
+ const int maxDForm2Offset = (1 << 7) - 1;
+ return DFormAddressPredicate(Op, N, Disp, Base, minDForm2Offset,
+ maxDForm2Offset);
}
/*!
SDOperand &Index, int minOffset,
int maxOffset) {
unsigned Opc = N.getOpcode();
- unsigned PtrTy = SPUtli.getPointerTy();
+ MVT PtrTy = SPUtli.getPointerTy();
if (Opc == ISD::FrameIndex) {
// Stack frame index must be less than 512 (divided by 16):
- FrameIndexSDNode *FI = dyn_cast<FrameIndexSDNode>(N);
+ FrameIndexSDNode *FIN = dyn_cast<FrameIndexSDNode>(N);
+ int FI = int(FIN->getIndex());
DEBUG(cerr << "SelectDFormAddr: ISD::FrameIndex = "
- << FI->getIndex() << "\n");
- if (FI->getIndex() < maxOffset) {
+ << FI << "\n");
+ if (SPUFrameInfo::FItoStackOffset(FI) < maxOffset) {
Base = CurDAG->getTargetConstant(0, PtrTy);
- Index = CurDAG->getTargetFrameIndex(FI->getIndex(), PtrTy);
+ Index = CurDAG->getTargetFrameIndex(FI, PtrTy);
return true;
}
} else if (Opc == ISD::ADD) {
int32_t offset = int32_t(CN->getSignExtended());
if (Op0.getOpcode() == ISD::FrameIndex) {
- FrameIndexSDNode *FI = dyn_cast<FrameIndexSDNode>(Op0);
+ FrameIndexSDNode *FIN = dyn_cast<FrameIndexSDNode>(Op0);
+ int FI = int(FIN->getIndex());
DEBUG(cerr << "SelectDFormAddr: ISD::ADD offset = " << offset
- << " frame index = " << FI->getIndex() << "\n");
+ << " frame index = " << FI << "\n");
- if (FI->getIndex() < maxOffset) {
+ if (SPUFrameInfo::FItoStackOffset(FI) < maxOffset) {
Base = CurDAG->getTargetConstant(offset, PtrTy);
- Index = CurDAG->getTargetFrameIndex(FI->getIndex(), PtrTy);
+ Index = CurDAG->getTargetFrameIndex(FI, PtrTy);
return true;
}
} else if (offset > minOffset && offset < maxOffset) {
int32_t offset = int32_t(CN->getSignExtended());
if (Op1.getOpcode() == ISD::FrameIndex) {
- FrameIndexSDNode *FI = dyn_cast<FrameIndexSDNode>(Op1);
+ FrameIndexSDNode *FIN = dyn_cast<FrameIndexSDNode>(Op1);
+ int FI = int(FIN->getIndex());
DEBUG(cerr << "SelectDFormAddr: ISD::ADD offset = " << offset
- << " frame index = " << FI->getIndex() << "\n");
+ << " frame index = " << FI << "\n");
- if (FI->getIndex() < maxOffset) {
+ if (SPUFrameInfo::FItoStackOffset(FI) < maxOffset) {
Base = CurDAG->getTargetConstant(offset, PtrTy);
- Index = CurDAG->getTargetFrameIndex(FI->getIndex(), PtrTy);
+ Index = CurDAG->getTargetFrameIndex(FI, PtrTy);
return true;
}
} else if (offset > minOffset && offset < maxOffset) {
unsigned Opc = N->getOpcode();
int n_ops = -1;
unsigned NewOpc;
- MVT::ValueType OpVT = Op.getValueType();
+ MVT OpVT = Op.getValueType();
SDOperand Ops[8];
if (Opc >= ISD::BUILTIN_OP_END && Opc < SPUISD::FIRST_NUMBER) {
return NULL; // Already selected.
} else if (Opc == ISD::FrameIndex) {
- // Selects to AIr32 FI, 0 which in turn will become AIr32 SP, imm.
- int FI = cast<FrameIndexSDNode>(N)->getIndex();
- MVT::ValueType PtrVT = SPUtli.getPointerTy();
- SDOperand Zero = CurDAG->getTargetConstant(0, PtrVT);
- SDOperand TFI = CurDAG->getTargetFrameIndex(FI, PtrVT);
-
- DEBUG(cerr << "SPUDAGToDAGISel: Replacing FrameIndex with AI32 <FI>, 0\n");
- NewOpc = SPU::AIr32;
- Ops[0] = TFI;
- Ops[1] = Zero;
- n_ops = 2;
+ // Selects to (add $sp, FI * stackSlotSize)
+ int FI =
+ SPUFrameInfo::FItoStackOffset(cast<FrameIndexSDNode>(N)->getIndex());
+ MVT PtrVT = SPUtli.getPointerTy();
+
+ // Adjust stack slot to actual offset in frame:
+ if (isS10Constant(FI)) {
+ DEBUG(cerr << "SPUDAGToDAGISel: Replacing FrameIndex with AIr32 $sp, "
+ << FI
+ << "\n");
+ NewOpc = SPU::AIr32;
+ Ops[0] = CurDAG->getRegister(SPU::R1, PtrVT);
+ Ops[1] = CurDAG->getTargetConstant(FI, PtrVT);
+ n_ops = 2;
+ } else {
+ DEBUG(cerr << "SPUDAGToDAGISel: Replacing FrameIndex with Ar32 $sp, "
+ << FI
+ << "\n");
+ NewOpc = SPU::Ar32;
+ Ops[0] = CurDAG->getRegister(SPU::R1, PtrVT);
+ Ops[1] = CurDAG->getConstant(FI, PtrVT);
+ n_ops = 2;
+
+ AddToISelQueue(Ops[1]);
+ }
} else if (Opc == ISD::ZERO_EXTEND) {
// (zero_extend:i16 (and:i8 <arg>, <const>))
const SDOperand &Op1 = N->getOperand(0);
}
} else if (Opc == SPUISD::LDRESULT) {
// Custom select instructions for LDRESULT
- unsigned VT = N->getValueType(0);
+ MVT VT = N->getValueType(0);
SDOperand Arg = N->getOperand(0);
SDOperand Chain = N->getOperand(1);
SDNode *Result;
if (vtm->ldresult_ins == 0) {
cerr << "LDRESULT for unsupported type: "
- << MVT::getValueTypeString(VT)
+ << VT.getMVTString()
<< "\n";
abort();
}
/* || Op0.getOpcode() == SPUISD::AFormAddr) */
// (IndirectAddr (LDRESULT, imm))
SDOperand Op1 = Op.getOperand(1);
- MVT::ValueType VT = Op.getValueType();
+ MVT VT = Op.getValueType();
DEBUG(cerr << "CellSPU: IndirectAddr(LDRESULT, imm):\nOp0 = ");
DEBUG(Op.getOperand(0).Val->dump(CurDAG));