[llvm-commits] [llvm] r89720 - in /llvm/trunk: lib/Target/ARM/ARMBaseInstrInfo.h lib/Target/ARM/ARMExpandPseudoInsts.cpp lib/Target/ARM/ARMISelDAGToDAG.cpp lib/Target/ARM/ARMISelLowering.cpp lib/Target/ARM/ARMInstrInfo.td lib/Target/ARM/ARMInstrThumb2.td lib/Target/ARM/ARMSubtarget.cpp lib/Target/ARM/ARMSubtarget.h lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp lib/Target/ARM/Thumb2SizeReduction.cpp test/CodeGen/ARM/movt-movw-global.ll
Evan Cheng
evan.cheng at apple.com
Mon Nov 23 18:47:28 PST 2009
Hi Anton,
Can you remove the "UseMovt" subtarget feature and just check for V6T2?
Evan
On Nov 23, 2009, at 4:44 PM, Anton Korobeynikov wrote:
> Author: asl
> Date: Mon Nov 23 18:44:37 2009
> New Revision: 89720
>
> URL: http://llvm.org/viewvc/llvm-project?rev=89720&view=rev
> Log:
> Materialize global addresses via movt/movw pair, this is always better
> than doing the same via constpool:
> 1. Load from constpool costs 3 cycles on A9, movt/movw pair - just 2.
> 2. Load from constpool might stall up to 300 cycles due to cache miss.
> 3. Movt/movw does not use load/store unit.
> 4. Less constpool entries => better compiler performance.
>
> This is only enabled on ELF systems, since darwin does not have needed
> relocations (yet).
>
> Added:
> llvm/trunk/test/CodeGen/ARM/movt-movw-global.ll
> Modified:
> llvm/trunk/lib/Target/ARM/ARMBaseInstrInfo.h
> llvm/trunk/lib/Target/ARM/ARMExpandPseudoInsts.cpp
> llvm/trunk/lib/Target/ARM/ARMISelDAGToDAG.cpp
> llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp
> llvm/trunk/lib/Target/ARM/ARMInstrInfo.td
> llvm/trunk/lib/Target/ARM/ARMInstrThumb2.td
> llvm/trunk/lib/Target/ARM/ARMSubtarget.cpp
> llvm/trunk/lib/Target/ARM/ARMSubtarget.h
> llvm/trunk/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp
> llvm/trunk/lib/Target/ARM/Thumb2SizeReduction.cpp
>
> Modified: llvm/trunk/lib/Target/ARM/ARMBaseInstrInfo.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMBaseInstrInfo.h?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMBaseInstrInfo.h (original)
> +++ llvm/trunk/lib/Target/ARM/ARMBaseInstrInfo.h Mon Nov 23 18:44:37 2009
> @@ -162,6 +162,22 @@
> I_BitShift = 25,
> CondShift = 28
> };
> +
> + /// Target Operand Flag enum.
> + enum TOF {
> + //===------------------------------------------------------------------===//
> + // ARM Specific MachineOperand flags.
> +
> + MO_NO_FLAG,
> +
> + /// MO_LO16 - On a symbol operand, this represents a relocation containing
> + /// lower 16 bit of the address. Used only via movw instruction.
> + MO_LO16,
> +
> + /// MO_HI16 - On a symbol operand, this represents a relocation containing
> + /// higher 16 bit of the address. Used only via movt instruction.
> + MO_HI16
> + };
> }
>
> class ARMBaseInstrInfo : public TargetInstrInfoImpl {
>
> Modified: llvm/trunk/lib/Target/ARM/ARMExpandPseudoInsts.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMExpandPseudoInsts.cpp?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMExpandPseudoInsts.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/ARMExpandPseudoInsts.cpp Mon Nov 23 18:44:37 2009
> @@ -75,17 +75,30 @@
> }
> case ARM::t2MOVi32imm: {
> unsigned DstReg = MI.getOperand(0).getReg();
> - unsigned Imm = MI.getOperand(1).getImm();
> - unsigned Lo16 = Imm & 0xffff;
> - unsigned Hi16 = (Imm >> 16) & 0xffff;
> if (!MI.getOperand(0).isDead()) {
> - AddDefaultPred(BuildMI(MBB, MBBI, MI.getDebugLoc(),
> - TII->get(ARM::t2MOVi16), DstReg)
> - .addImm(Lo16));
> - AddDefaultPred(BuildMI(MBB, MBBI, MI.getDebugLoc(),
> - TII->get(ARM::t2MOVTi16))
> - .addReg(DstReg, getDefRegState(true))
> - .addReg(DstReg).addImm(Hi16));
> + const MachineOperand &MO = MI.getOperand(1);
> + MachineInstrBuilder LO16, HI16;
> +
> + LO16 = BuildMI(MBB, MBBI, MI.getDebugLoc(), TII->get(ARM::t2MOVi16),
> + DstReg);
> + HI16 = BuildMI(MBB, MBBI, MI.getDebugLoc(), TII->get(ARM::t2MOVTi16))
> + .addReg(DstReg, getDefRegState(true)).addReg(DstReg);
> +
> + if (MO.isImm()) {
> + unsigned Imm = MO.getImm();
> + unsigned Lo16 = Imm & 0xffff;
> + unsigned Hi16 = (Imm >> 16) & 0xffff;
> + LO16 = LO16.addImm(Lo16);
> + HI16 = HI16.addImm(Hi16);
> + } else {
> + GlobalValue *GV = MO.getGlobal();
> + unsigned TF = MO.getTargetFlags();
> + LO16 = LO16.addGlobalAddress(GV, MO.getOffset(), TF | ARMII::MO_LO16);
> + HI16 = HI16.addGlobalAddress(GV, MO.getOffset(), TF | ARMII::MO_HI16);
> + // FIXME: What's about memoperands?
> + }
> + AddDefaultPred(LO16);
> + AddDefaultPred(HI16);
> }
> MI.eraseFromParent();
> Modified = true;
>
> Modified: llvm/trunk/lib/Target/ARM/ARMISelDAGToDAG.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMISelDAGToDAG.cpp?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMISelDAGToDAG.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/ARMISelDAGToDAG.cpp Mon Nov 23 18:44:37 2009
> @@ -261,7 +261,9 @@
> if (N.getOpcode() == ISD::FrameIndex) {
> int FI = cast<FrameIndexSDNode>(N)->getIndex();
> Base = CurDAG->getTargetFrameIndex(FI, TLI.getPointerTy());
> - } else if (N.getOpcode() == ARMISD::Wrapper) {
> + } else if (N.getOpcode() == ARMISD::Wrapper &&
> + !(Subtarget->useMovt() &&
> + N.getOperand(0).getOpcode() == ISD::TargetGlobalAddress)) {
> Base = N.getOperand(0);
> }
> Offset = CurDAG->getRegister(0, MVT::i32);
> @@ -463,7 +465,9 @@
> if (N.getOpcode() == ISD::FrameIndex) {
> int FI = cast<FrameIndexSDNode>(N)->getIndex();
> Base = CurDAG->getTargetFrameIndex(FI, TLI.getPointerTy());
> - } else if (N.getOpcode() == ARMISD::Wrapper) {
> + } else if (N.getOpcode() == ARMISD::Wrapper &&
> + !(Subtarget->useMovt() &&
> + N.getOperand(0).getOpcode() == ISD::TargetGlobalAddress)) {
> Base = N.getOperand(0);
> }
> Offset = CurDAG->getTargetConstant(ARM_AM::getAM5Opc(ARM_AM::add, 0),
> @@ -558,7 +562,13 @@
> }
>
> if (N.getOpcode() != ISD::ADD) {
> - Base = (N.getOpcode() == ARMISD::Wrapper) ? N.getOperand(0) : N;
> + if (N.getOpcode() == ARMISD::Wrapper &&
> + !(Subtarget->useMovt() &&
> + N.getOperand(0).getOpcode() == ISD::TargetGlobalAddress)) {
> + Base = N.getOperand(0);
> + } else
> + Base = N;
> +
> Offset = CurDAG->getRegister(0, MVT::i32);
> OffImm = CurDAG->getTargetConstant(0, MVT::i32);
> return true;
> @@ -681,7 +691,9 @@
> Base = CurDAG->getTargetFrameIndex(FI, TLI.getPointerTy());
> OffImm = CurDAG->getTargetConstant(0, MVT::i32);
> return true;
> - } else if (N.getOpcode() == ARMISD::Wrapper) {
> + } else if (N.getOpcode() == ARMISD::Wrapper &&
> + !(Subtarget->useMovt() &&
> + N.getOperand(0).getOpcode() == ISD::TargetGlobalAddress)) {
> Base = N.getOperand(0);
> if (Base.getOpcode() == ISD::TargetConstantPool)
> return false; // We want to select t2LDRpci instead.
>
> Modified: llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/ARMISelLowering.cpp Mon Nov 23 18:44:37 2009
> @@ -39,6 +39,7 @@
> #include "llvm/CodeGen/SelectionDAG.h"
> #include "llvm/Target/TargetOptions.h"
> #include "llvm/ADT/VectorExtras.h"
> +#include "llvm/Support/CommandLine.h"
> #include "llvm/Support/ErrorHandling.h"
> #include "llvm/Support/MathExtras.h"
> #include <sstream>
> @@ -1356,10 +1357,17 @@
> PseudoSourceValue::getGOT(), 0);
> return Result;
> } else {
> - SDValue CPAddr = DAG.getTargetConstantPool(GV, PtrVT, 4);
> - CPAddr = DAG.getNode(ARMISD::Wrapper, dl, MVT::i32, CPAddr);
> - return DAG.getLoad(PtrVT, dl, DAG.getEntryNode(), CPAddr,
> - PseudoSourceValue::getConstantPool(), 0);
> + // If we have T2 ops, we can materialize the address directly via movt/movw
> + // pair. This is always cheaper.
> + if (Subtarget->useMovt()) {
> + return DAG.getNode(ARMISD::Wrapper, dl, PtrVT,
> + DAG.getTargetGlobalAddress(GV, PtrVT));
> + } else {
> + SDValue CPAddr = DAG.getTargetConstantPool(GV, PtrVT, 4);
> + CPAddr = DAG.getNode(ARMISD::Wrapper, dl, MVT::i32, CPAddr);
> + return DAG.getLoad(PtrVT, dl, DAG.getEntryNode(), CPAddr,
> + PseudoSourceValue::getConstantPool(), 0);
> + }
> }
> }
>
>
> Modified: llvm/trunk/lib/Target/ARM/ARMInstrInfo.td
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMInstrInfo.td?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMInstrInfo.td (original)
> +++ llvm/trunk/lib/Target/ARM/ARMInstrInfo.td Mon Nov 23 18:44:37 2009
> @@ -116,6 +116,10 @@
> def CarryDefIsUnused : Predicate<"!N.getNode()->hasAnyUseOfValue(1)">;
> def CarryDefIsUsed : Predicate<"N.getNode()->hasAnyUseOfValue(1)">;
>
> +// FIXME: Eventually this will be just "hasV6T2Ops".
> +def UseMovt : Predicate<"Subtarget->useMovt()">;
> +def DontUseMovt : Predicate<"!Subtarget->useMovt()">;
> +
> //===----------------------------------------------------------------------===//
> // ARM Flag Definitions.
>
> @@ -204,7 +208,7 @@
> def lo16AllZero : PatLeaf<(i32 imm), [{
> // Returns true if all low 16-bits are 0.
> return (((uint32_t)N->getZExtValue()) & 0xFFFFUL) == 0;
> - }], hi16>;
> +}], hi16>;
>
> /// imm0_65535 predicate - True if the 32-bit immediate is in the range
> /// [0.65535].
> @@ -1002,7 +1006,7 @@
> let Constraints = "$src = $dst" in
> def MOVTi16 : AI1<0b1010, (outs GPR:$dst), (ins GPR:$src, i32imm:$imm),
> DPFrm, IIC_iMOVi,
> - "movt", "\t$dst, $imm",
> + "movt", "\t$dst, $imm",
> [(set GPR:$dst,
> (or (and GPR:$src, 0xffff),
> lo16AllZero:$imm))]>, UnaryDP,
> @@ -1603,12 +1607,6 @@
> // Non-Instruction Patterns
> //
>
> -// ConstantPool, GlobalAddress, and JumpTable
> -def : ARMPat<(ARMWrapper tglobaladdr :$dst), (LEApcrel tglobaladdr :$dst)>;
> -def : ARMPat<(ARMWrapper tconstpool :$dst), (LEApcrel tconstpool :$dst)>;
> -def : ARMPat<(ARMWrapperJT tjumptable:$dst, imm:$id),
> - (LEApcrelJT tjumptable:$dst, imm:$id)>;
> -
> // Large immediate handling.
>
> // Two piece so_imms.
> @@ -1638,10 +1636,19 @@
> // FIXME: Remove this when we can do generalized remat.
> let isReMaterializable = 1 in
> def MOVi32imm : AI1x2<(outs GPR:$dst), (ins i32imm:$src), Pseudo, IIC_iMOVi,
> - "movw", "\t$dst, ${src:lo16}\n\tmovt${p} $dst, ${src:hi16}",
> + "movw", "\t$dst, ${src:lo16}\n\tmovt${p}\t$dst, ${src:hi16}",
> [(set GPR:$dst, (i32 imm:$src))]>,
> Requires<[IsARM, HasV6T2]>;
>
> +// ConstantPool, GlobalAddress, and JumpTable
> +def : ARMPat<(ARMWrapper tglobaladdr :$dst), (LEApcrel tglobaladdr :$dst)>,
> + Requires<[IsARM, DontUseMovt]>;
> +def : ARMPat<(ARMWrapper tconstpool :$dst), (LEApcrel tconstpool :$dst)>;
> +def : ARMPat<(ARMWrapper tglobaladdr :$dst), (MOVi32imm tglobaladdr :$dst)>,
> + Requires<[IsARM, UseMovt]>;
> +def : ARMPat<(ARMWrapperJT tjumptable:$dst, imm:$id),
> + (LEApcrelJT tjumptable:$dst, imm:$id)>;
> +
> // TODO: add,sub,and, 3-instr forms?
>
>
>
> Modified: llvm/trunk/lib/Target/ARM/ARMInstrThumb2.td
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMInstrThumb2.td?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMInstrThumb2.td (original)
> +++ llvm/trunk/lib/Target/ARM/ARMInstrThumb2.td Mon Nov 23 18:44:37 2009
> @@ -1181,12 +1181,6 @@
> (t2SUBri (t2SUBri GPR:$LHS, (t2_so_neg_imm2part_1 imm:$RHS)),
> (t2_so_neg_imm2part_2 imm:$RHS))>;
>
> -// ConstantPool, GlobalAddress, and JumpTable
> -def : T2Pat<(ARMWrapper tglobaladdr :$dst), (t2LEApcrel tglobaladdr :$dst)>;
> -def : T2Pat<(ARMWrapper tconstpool :$dst), (t2LEApcrel tconstpool :$dst)>;
> -def : T2Pat<(ARMWrapperJT tjumptable:$dst, imm:$id),
> - (t2LEApcrelJT tjumptable:$dst, imm:$id)>;
> -
> // 32-bit immediate using movw + movt.
> // This is a single pseudo instruction to make it re-materializable. Remove
> // when we can do generalized remat.
> @@ -1195,6 +1189,16 @@
> "movw", "\t$dst, ${src:lo16}\n\tmovt${p}\t$dst, ${src:hi16}",
> [(set GPR:$dst, (i32 imm:$src))]>;
>
> +// ConstantPool, GlobalAddress, and JumpTable
> +def : T2Pat<(ARMWrapper tglobaladdr :$dst), (t2LEApcrel tglobaladdr :$dst)>,
> + Requires<[IsThumb2, DontUseMovt]>;
> +def : T2Pat<(ARMWrapper tconstpool :$dst), (t2LEApcrel tconstpool :$dst)>;
> +def : T2Pat<(ARMWrapper tglobaladdr :$dst), (t2MOVi32imm tglobaladdr :$dst)>,
> + Requires<[IsThumb2, UseMovt]>;
> +
> +def : T2Pat<(ARMWrapperJT tjumptable:$dst, imm:$id),
> + (t2LEApcrelJT tjumptable:$dst, imm:$id)>;
> +
> // Pseudo instruction that combines ldr from constpool and add pc. This should
> // be expanded into two instructions late to allow if-conversion and
> // scheduling.
>
> Modified: llvm/trunk/lib/Target/ARM/ARMSubtarget.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMSubtarget.cpp?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMSubtarget.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/ARMSubtarget.cpp Mon Nov 23 18:44:37 2009
> @@ -27,6 +27,10 @@
> cl::desc("Use NEON for single-precision FP"),
> cl::init(false), cl::Hidden);
>
> +static cl::opt<bool>
> +UseMOVT("arm-use-movt",
> + cl::init(true), cl::Hidden);
> +
> ARMSubtarget::ARMSubtarget(const std::string &TT, const std::string &FS,
> bool isT)
> : ARMArchVersion(V4T)
> @@ -36,6 +40,7 @@
> , ThumbMode(Thumb1)
> , PostRAScheduler(false)
> , IsR9Reserved(ReserveR9)
> + , UseMovt(UseMOVT)
> , stackAlignment(4)
> , CPUString("generic")
> , TargetType(isELF) // Default to ELF unless otherwise specified.
>
> Modified: llvm/trunk/lib/Target/ARM/ARMSubtarget.h
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/ARMSubtarget.h?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/ARMSubtarget.h (original)
> +++ llvm/trunk/lib/Target/ARM/ARMSubtarget.h Mon Nov 23 18:44:37 2009
> @@ -65,6 +65,10 @@
> /// IsR9Reserved - True if R9 is a not available as general purpose register.
> bool IsR9Reserved;
>
> + /// UseMovt - True if MOVT / MOVW pairs are used for materialization of 32-bit
> + /// imms (including global addresses).
> + bool UseMovt;
> +
> /// stackAlignment - The minimum alignment known to hold of the stack frame on
> /// entry to the function and which must be maintained by every function.
> unsigned stackAlignment;
> @@ -130,8 +134,10 @@
>
> bool isR9Reserved() const { return IsR9Reserved; }
>
> + bool useMovt() const { return UseMovt && hasV6T2Ops(); }
> +
> const std::string & getCPUString() const { return CPUString; }
> -
> +
> /// enablePostRAScheduler - True at 'More' optimization.
> bool enablePostRAScheduler(CodeGenOpt::Level OptLevel,
> TargetSubtarget::AntiDepBreakMode& Mode,
>
> Modified: llvm/trunk/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/AsmPrinter/ARMAsmPrinter.cpp Mon Nov 23 18:44:37 2009
> @@ -330,6 +330,8 @@
> void ARMAsmPrinter::printOperand(const MachineInstr *MI, int OpNum,
> const char *Modifier) {
> const MachineOperand &MO = MI->getOperand(OpNum);
> + unsigned TF = MO.getTargetFlags();
> +
> switch (MO.getType()) {
> default:
> assert(0 && "<unknown operand type>");
> @@ -356,12 +358,12 @@
> case MachineOperand::MO_Immediate: {
> int64_t Imm = MO.getImm();
> O << '#';
> - if (Modifier) {
> - if (strcmp(Modifier, "lo16") == 0)
> - O << ":lower16:";
> - else if (strcmp(Modifier, "hi16") == 0)
> - O << ":upper16:";
> - }
> + if ((Modifier && strcmp(Modifier, "lo16") == 0) ||
> + (TF & ARMII::MO_LO16))
> + O << ":lower16:";
> + else if ((Modifier && strcmp(Modifier, "hi16") == 0) ||
> + (TF & ARMII::MO_HI16))
> + O << ":upper16:";
> O << Imm;
> break;
> }
> @@ -371,6 +373,13 @@
> case MachineOperand::MO_GlobalAddress: {
> bool isCallOp = Modifier && !strcmp(Modifier, "call");
> GlobalValue *GV = MO.getGlobal();
> +
> + if ((Modifier && strcmp(Modifier, "lo16") == 0) ||
> + (TF & ARMII::MO_LO16))
> + O << ":lower16:";
> + else if ((Modifier && strcmp(Modifier, "hi16") == 0) ||
> + (TF & ARMII::MO_HI16))
> + O << ":upper16:";
> O << Mang->getMangledName(GV);
>
> printOffset(MO.getOffset());
>
> Modified: llvm/trunk/lib/Target/ARM/Thumb2SizeReduction.cpp
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Target/ARM/Thumb2SizeReduction.cpp?rev=89720&r1=89719&r2=89720&view=diff
>
> ==============================================================================
> --- llvm/trunk/lib/Target/ARM/Thumb2SizeReduction.cpp (original)
> +++ llvm/trunk/lib/Target/ARM/Thumb2SizeReduction.cpp Mon Nov 23 18:44:37 2009
> @@ -78,7 +78,7 @@
> { ARM::t2LSRri, ARM::tLSRri, 0, 5, 0, 1, 0, 0,0, 0 },
> { ARM::t2LSRrr, 0, ARM::tLSRrr, 0, 0, 0, 1, 0,0, 0 },
> { ARM::t2MOVi, ARM::tMOVi8, 0, 8, 0, 1, 0, 0,0, 0 },
> - { ARM::t2MOVi16,ARM::tMOVi8, 0, 8, 0, 1, 0, 0,0, 0 },
> + { ARM::t2MOVi16,ARM::tMOVi8, 0, 8, 0, 1, 0, 0,0, 1 },
> // FIXME: Do we need the 16-bit 'S' variant?
> { ARM::t2MOVr,ARM::tMOVgpr2gpr,0, 0, 0, 0, 0, 1,0, 0 },
> { ARM::t2MOVCCr,0, ARM::tMOVCCr, 0, 0, 0, 0, 0,1, 0 },
> @@ -413,6 +413,12 @@
> if (MI->getOperand(2).getImm() == 0)
> return ReduceToNarrow(MBB, MI, Entry, LiveCPSR);
> break;
> + case ARM::t2MOVi16:
> + // Can convert only 'pure' immediate operands, not immediates obtained as
> + // globals' addresses.
> + if (MI->getOperand(1).isImm())
> + return ReduceToNarrow(MBB, MI, Entry, LiveCPSR);
> + break;
> }
> return false;
> }
>
> Added: llvm/trunk/test/CodeGen/ARM/movt-movw-global.ll
> URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/ARM/movt-movw-global.ll?rev=89720&view=auto
>
> ==============================================================================
> --- llvm/trunk/test/CodeGen/ARM/movt-movw-global.ll (added)
> +++ llvm/trunk/test/CodeGen/ARM/movt-movw-global.ll Mon Nov 23 18:44:37 2009
> @@ -0,0 +1,20 @@
> +; RUN: llc < %s | FileCheck %s
> +target datalayout = "e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64"
> +target triple = "armv7-eabi"
> +
> + at foo = common global i32 0 ; <i32*> [#uses=1]
> +
> +define arm_aapcs_vfpcc i32* @bar1() nounwind readnone {
> +entry:
> +; CHECK: movw r0, :lower16:foo
> +; CHECK-NEXT: movt r0, :upper16:foo
> + ret i32* @foo
> +}
> +
> +define arm_aapcs_vfpcc void @bar2(i32 %baz) nounwind {
> +entry:
> +; CHECK: movw r1, :lower16:foo
> +; CHECK-NEXT: movt r1, :upper16:foo
> + store i32 %baz, i32* @foo, align 4
> + ret void
> +}
>
>
> _______________________________________________
> llvm-commits mailing list
> llvm-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits
More information about the llvm-commits
mailing list