add shifts to addressing mode 1

llvm-svn: 30291
This commit is contained in:
Rafael Espindola 2006-09-13 12:09:43 +00:00
parent 84cc1f7cb8
commit 3130a756ef
6 changed files with 81 additions and 32 deletions

View File

@ -41,6 +41,16 @@ namespace llvm {
}; };
} }
namespace ARMShift {
enum ShiftTypes {
LSL,
LSR,
ASR,
ROR,
RRX
};
}
static const char *ARMCondCodeToString(ARMCC::CondCodes CC) { static const char *ARMCondCodeToString(ARMCC::CondCodes CC) {
switch (CC) { switch (CC) {
default: assert(0 && "Unknown condition code"); default: assert(0 && "Unknown condition code");

View File

@ -158,13 +158,38 @@ bool ARMAsmPrinter::runOnMachineFunction(MachineFunction &MF) {
} }
void ARMAsmPrinter::printAddrMode1(const MachineInstr *MI, int opNum) { void ARMAsmPrinter::printAddrMode1(const MachineInstr *MI, int opNum) {
const MachineOperand &MO1 = MI->getOperand(opNum); const MachineOperand &Arg = MI->getOperand(opNum);
const MachineOperand &Shift = MI->getOperand(opNum + 1);
const MachineOperand &ShiftType = MI->getOperand(opNum + 2);
if(MO1.isImmediate()) { if(Arg.isImmediate()) {
assert(Shift.getImmedValue() == 0);
printOperand(MI, opNum); printOperand(MI, opNum);
} else { } else {
assert(MO1.isRegister()); assert(Arg.isRegister());
printOperand(MI, opNum); printOperand(MI, opNum);
if(Shift.isRegister() || Shift.getImmedValue() != 0) {
const char *s = NULL;
switch(ShiftType.getImmedValue()) {
case ARMShift::LSL:
s = ", lsl ";
break;
case ARMShift::LSR:
s = ", lsr ";
break;
case ARMShift::ASR:
s = ", asr ";
break;
case ARMShift::ROR:
s = ", ror ";
break;
case ARMShift::RRX:
s = ", rrx ";
break;
}
O << s;
printOperand(MI, opNum + 1);
}
} }
} }

View File

@ -445,7 +445,8 @@ public:
SDNode *Select(SDOperand Op); SDNode *Select(SDOperand Op);
virtual void InstructionSelectBasicBlock(SelectionDAG &DAG); virtual void InstructionSelectBasicBlock(SelectionDAG &DAG);
bool SelectAddrRegImm(SDOperand N, SDOperand &Offset, SDOperand &Base); bool SelectAddrRegImm(SDOperand N, SDOperand &Offset, SDOperand &Base);
bool SelectAddrMode1(SDOperand N, SDOperand &Arg); bool SelectAddrMode1(SDOperand N, SDOperand &Arg, SDOperand &Shift,
SDOperand &ShiftType);
// Include the pieces autogenerated from the target description. // Include the pieces autogenerated from the target description.
#include "ARMGenDAGISel.inc" #include "ARMGenDAGISel.inc"
@ -480,17 +481,38 @@ static bool isInt12Immediate(SDOperand Op, short &Imm) {
} }
bool ARMDAGToDAGISel::SelectAddrMode1(SDOperand N, bool ARMDAGToDAGISel::SelectAddrMode1(SDOperand N,
SDOperand &Arg) { SDOperand &Arg,
SDOperand &Shift,
SDOperand &ShiftType) {
switch(N.getOpcode()) { switch(N.getOpcode()) {
case ISD::Constant: { case ISD::Constant: {
//TODO:check that we have a valid constant //TODO:check that we have a valid constant
int32_t t = cast<ConstantSDNode>(N)->getValue(); int32_t t = cast<ConstantSDNode>(N)->getValue();
Arg = CurDAG->getTargetConstant(t, MVT::i32); Arg = CurDAG->getTargetConstant(t, MVT::i32);
Shift = CurDAG->getTargetConstant(0, MVT::i32);
ShiftType = CurDAG->getTargetConstant(ARMShift::LSL, MVT::i32);
return true; return true;
} }
case ISD::SRA:
Arg = N.getOperand(0);
Shift = N.getOperand(1);
ShiftType = CurDAG->getTargetConstant(ARMShift::ASR, MVT::i32);
return true;
case ISD::SRL:
Arg = N.getOperand(0);
Shift = N.getOperand(1);
ShiftType = CurDAG->getTargetConstant(ARMShift::LSR, MVT::i32);
return true;
case ISD::SHL:
Arg = N.getOperand(0);
Shift = N.getOperand(1);
ShiftType = CurDAG->getTargetConstant(ARMShift::LSL, MVT::i32);
return true;
} }
Arg = N; Arg = N;
Shift = CurDAG->getTargetConstant(0, MVT::i32);
ShiftType = CurDAG->getTargetConstant(ARMShift::LSL, MVT::i32);
return true; return true;
} }

View File

@ -33,15 +33,18 @@ bool ARMInstrInfo::isMoveInstr(const MachineInstr &MI,
unsigned &SrcReg, unsigned &DstReg) const { unsigned &SrcReg, unsigned &DstReg) const {
MachineOpCode oc = MI.getOpcode(); MachineOpCode oc = MI.getOpcode();
switch (oc) { switch (oc) {
case ARM::MOV: case ARM::MOV: {
assert(MI.getNumOperands() == 2 && assert(MI.getNumOperands() == 4 &&
MI.getOperand(0).isRegister() && MI.getOperand(0).isRegister() &&
"Invalid ARM MOV instruction"); "Invalid ARM MOV instruction");
if (MI.getOperand(1).isRegister()) { const MachineOperand &Arg = MI.getOperand(1);
const MachineOperand &Shift = MI.getOperand(2);
if (Arg.isRegister() && Shift.isImmediate() && Shift.getImmedValue() == 0) {
SrcReg = MI.getOperand(1).getReg(); SrcReg = MI.getOperand(1).getReg();
DstReg = MI.getOperand(0).getReg(); DstReg = MI.getOperand(0).getReg();
return true; return true;
} }
} }
}
return false; return false;
} }

View File

@ -15,8 +15,8 @@
// Address operands // Address operands
def op_addr_mode1 : Operand<iPTR> { def op_addr_mode1 : Operand<iPTR> {
let PrintMethod = "printAddrMode1"; let PrintMethod = "printAddrMode1";
let NumMIOperands = 1; let NumMIOperands = 3;
let MIOperandInfo = (ops ptr_rc); let MIOperandInfo = (ops ptr_rc, ptr_rc, i32imm);
} }
def memri : Operand<iPTR> { def memri : Operand<iPTR> {
@ -27,7 +27,7 @@ def memri : Operand<iPTR> {
// Define ARM specific addressing mode. // Define ARM specific addressing mode.
//Addressing Mode 1: data processing operands //Addressing Mode 1: data processing operands
def addr_mode1 : ComplexPattern<iPTR, 1, "SelectAddrMode1", [imm]>; def addr_mode1 : ComplexPattern<iPTR, 3, "SelectAddrMode1", [imm, sra, shl, srl]>;
//register plus/minus 12 bit offset //register plus/minus 12 bit offset
def iaddr : ComplexPattern<iPTR, 2, "SelectAddrRegImm", [frameindex]>; def iaddr : ComplexPattern<iPTR, 2, "SelectAddrRegImm", [frameindex]>;
@ -119,21 +119,6 @@ def AND : InstARM<(ops IntRegs:$dst, IntRegs:$a, op_addr_mode1:$b),
"and $dst, $a, $b", "and $dst, $a, $b",
[(set IntRegs:$dst, (and IntRegs:$a, addr_mode1:$b))]>; [(set IntRegs:$dst, (and IntRegs:$a, addr_mode1:$b))]>;
// All arm data processing instructions have a shift. Maybe we don't have
// to implement this
def SHL : InstARM<(ops IntRegs:$dst, IntRegs:$a, IntRegs:$b),
"mov $dst, $a, lsl $b",
[(set IntRegs:$dst, (shl IntRegs:$a, IntRegs:$b))]>;
def SRA : InstARM<(ops IntRegs:$dst, IntRegs:$a, IntRegs:$b),
"mov $dst, $a, asr $b",
[(set IntRegs:$dst, (sra IntRegs:$a, IntRegs:$b))]>;
def SRL : InstARM<(ops IntRegs:$dst, IntRegs:$a, IntRegs:$b),
"mov $dst, $a, lsr $b",
[(set IntRegs:$dst, (srl IntRegs:$a, IntRegs:$b))]>;
def EOR : InstARM<(ops IntRegs:$dst, IntRegs:$a, op_addr_mode1:$b), def EOR : InstARM<(ops IntRegs:$dst, IntRegs:$a, op_addr_mode1:$b),
"eor $dst, $a, $b", "eor $dst, $a, $b",
[(set IntRegs:$dst, (xor IntRegs:$a, addr_mode1:$b))]>; [(set IntRegs:$dst, (xor IntRegs:$a, addr_mode1:$b))]>;

View File

@ -48,7 +48,8 @@ void ARMRegisterInfo::copyRegToReg(MachineBasicBlock &MBB,
unsigned DestReg, unsigned SrcReg, unsigned DestReg, unsigned SrcReg,
const TargetRegisterClass *RC) const { const TargetRegisterClass *RC) const {
assert (RC == ARM::IntRegsRegisterClass); assert (RC == ARM::IntRegsRegisterClass);
BuildMI(MBB, I, ARM::MOV, 1, DestReg).addReg(SrcReg); BuildMI(MBB, I, ARM::MOV, 3, DestReg).addReg(SrcReg).addImm(0)
.addImm(ARMShift::LSL);
} }
MachineInstr *ARMRegisterInfo::foldMemoryOperand(MachineInstr* MI, MachineInstr *ARMRegisterInfo::foldMemoryOperand(MachineInstr* MI,
@ -114,7 +115,8 @@ ARMRegisterInfo::eliminateFrameIndex(MachineBasicBlock::iterator II) const {
// Insert a set of r12 with the full address // Insert a set of r12 with the full address
// r12 = r13 + offset // r12 = r13 + offset
MachineBasicBlock *MBB2 = MI.getParent(); MachineBasicBlock *MBB2 = MI.getParent();
BuildMI(*MBB2, II, ARM::ADD, 2, ARM::R12).addReg(ARM::R13).addImm(Offset); BuildMI(*MBB2, II, ARM::ADD, 4, ARM::R12).addReg(ARM::R13).addImm(Offset)
.addImm(0).addImm(ARMShift::LSL);
// Replace the FrameIndex with r12 // Replace the FrameIndex with r12
MI.getOperand(FrameIdx).ChangeToRegister(ARM::R12, false); MI.getOperand(FrameIdx).ChangeToRegister(ARM::R12, false);
@ -140,7 +142,8 @@ void ARMRegisterInfo::emitPrologue(MachineFunction &MF) const {
MFI->setStackSize(NumBytes); MFI->setStackSize(NumBytes);
//sub sp, sp, #NumBytes //sub sp, sp, #NumBytes
BuildMI(MBB, MBBI, ARM::SUB, 2, ARM::R13).addReg(ARM::R13).addImm(NumBytes); BuildMI(MBB, MBBI, ARM::SUB, 4, ARM::R13).addReg(ARM::R13).addImm(NumBytes)
.addImm(0).addImm(ARMShift::LSL);
} }
void ARMRegisterInfo::emitEpilogue(MachineFunction &MF, void ARMRegisterInfo::emitEpilogue(MachineFunction &MF,
@ -153,7 +156,8 @@ void ARMRegisterInfo::emitEpilogue(MachineFunction &MF,
int NumBytes = (int) MFI->getStackSize(); int NumBytes = (int) MFI->getStackSize();
//add sp, sp, #NumBytes //add sp, sp, #NumBytes
BuildMI(MBB, MBBI, ARM::ADD, 2, ARM::R13).addReg(ARM::R13).addImm(NumBytes); BuildMI(MBB, MBBI, ARM::ADD, 4, ARM::R13).addReg(ARM::R13).addImm(NumBytes)
.addImm(0).addImm(ARMShift::LSL);
} }
unsigned ARMRegisterInfo::getRARegister() const { unsigned ARMRegisterInfo::getRARegister() const {