1 //===-- ARMISelDAGToDAG.cpp - A dag to dag inst selector for ARM ----------===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 // This file defines an instruction selector for the ARM target.
12 //===----------------------------------------------------------------------===//
15 #include "ARMAddressingModes.h"
16 #include "ARMConstantPoolValue.h"
17 #include "ARMISelLowering.h"
18 #include "ARMTargetMachine.h"
19 #include "llvm/CallingConv.h"
20 #include "llvm/Constants.h"
21 #include "llvm/DerivedTypes.h"
22 #include "llvm/Function.h"
23 #include "llvm/Intrinsics.h"
24 #include "llvm/LLVMContext.h"
25 #include "llvm/CodeGen/MachineFrameInfo.h"
26 #include "llvm/CodeGen/MachineFunction.h"
27 #include "llvm/CodeGen/MachineInstrBuilder.h"
28 #include "llvm/CodeGen/SelectionDAG.h"
29 #include "llvm/CodeGen/SelectionDAGISel.h"
30 #include "llvm/Target/TargetLowering.h"
31 #include "llvm/Target/TargetOptions.h"
32 #include "llvm/Support/Compiler.h"
33 #include "llvm/Support/Debug.h"
34 #include "llvm/Support/ErrorHandling.h"
35 #include "llvm/Support/raw_ostream.h"
39 static const unsigned arm_dsubreg_0
= 5;
40 static const unsigned arm_dsubreg_1
= 6;
42 //===--------------------------------------------------------------------===//
43 /// ARMDAGToDAGISel - ARM specific code to select ARM machine
44 /// instructions for SelectionDAG operations.
47 class ARMDAGToDAGISel
: public SelectionDAGISel
{
48 ARMBaseTargetMachine
&TM
;
50 /// Subtarget - Keep a pointer to the ARMSubtarget around so that we can
51 /// make the right decision when generating code for different targets.
52 const ARMSubtarget
*Subtarget
;
55 explicit ARMDAGToDAGISel(ARMBaseTargetMachine
&tm
)
56 : SelectionDAGISel(tm
), TM(tm
),
57 Subtarget(&TM
.getSubtarget
<ARMSubtarget
>()) {
60 virtual const char *getPassName() const {
61 return "ARM Instruction Selection";
64 /// getI32Imm - Return a target constant with the specified value, of type i32.
65 inline SDValue
getI32Imm(unsigned Imm
) {
66 return CurDAG
->getTargetConstant(Imm
, MVT::i32
);
69 SDNode
*Select(SDValue Op
);
70 virtual void InstructionSelect();
71 bool SelectShifterOperandReg(SDValue Op
, SDValue N
, SDValue
&A
,
72 SDValue
&B
, SDValue
&C
);
73 bool SelectAddrMode2(SDValue Op
, SDValue N
, SDValue
&Base
,
74 SDValue
&Offset
, SDValue
&Opc
);
75 bool SelectAddrMode2Offset(SDValue Op
, SDValue N
,
76 SDValue
&Offset
, SDValue
&Opc
);
77 bool SelectAddrMode3(SDValue Op
, SDValue N
, SDValue
&Base
,
78 SDValue
&Offset
, SDValue
&Opc
);
79 bool SelectAddrMode3Offset(SDValue Op
, SDValue N
,
80 SDValue
&Offset
, SDValue
&Opc
);
81 bool SelectAddrMode4(SDValue Op
, SDValue N
, SDValue
&Addr
,
83 bool SelectAddrMode5(SDValue Op
, SDValue N
, SDValue
&Base
,
85 bool SelectAddrMode6(SDValue Op
, SDValue N
, SDValue
&Addr
, SDValue
&Update
,
88 bool SelectAddrModePC(SDValue Op
, SDValue N
, SDValue
&Offset
,
91 bool SelectThumbAddrModeRR(SDValue Op
, SDValue N
, SDValue
&Base
,
93 bool SelectThumbAddrModeRI5(SDValue Op
, SDValue N
, unsigned Scale
,
94 SDValue
&Base
, SDValue
&OffImm
,
96 bool SelectThumbAddrModeS1(SDValue Op
, SDValue N
, SDValue
&Base
,
97 SDValue
&OffImm
, SDValue
&Offset
);
98 bool SelectThumbAddrModeS2(SDValue Op
, SDValue N
, SDValue
&Base
,
99 SDValue
&OffImm
, SDValue
&Offset
);
100 bool SelectThumbAddrModeS4(SDValue Op
, SDValue N
, SDValue
&Base
,
101 SDValue
&OffImm
, SDValue
&Offset
);
102 bool SelectThumbAddrModeSP(SDValue Op
, SDValue N
, SDValue
&Base
,
105 bool SelectT2ShifterOperandReg(SDValue Op
, SDValue N
,
106 SDValue
&BaseReg
, SDValue
&Opc
);
107 bool SelectT2AddrModeImm12(SDValue Op
, SDValue N
, SDValue
&Base
,
109 bool SelectT2AddrModeImm8(SDValue Op
, SDValue N
, SDValue
&Base
,
111 bool SelectT2AddrModeImm8Offset(SDValue Op
, SDValue N
,
113 bool SelectT2AddrModeImm8s4(SDValue Op
, SDValue N
, SDValue
&Base
,
115 bool SelectT2AddrModeSoReg(SDValue Op
, SDValue N
, SDValue
&Base
,
116 SDValue
&OffReg
, SDValue
&ShImm
);
118 // Include the pieces autogenerated from the target description.
119 #include "ARMGenDAGISel.inc"
122 /// SelectARMIndexedLoad - Indexed (pre/post inc/dec) load matching code for
124 SDNode
*SelectARMIndexedLoad(SDValue Op
);
125 SDNode
*SelectT2IndexedLoad(SDValue Op
);
127 /// SelectDYN_ALLOC - Select dynamic alloc for Thumb.
128 SDNode
*SelectDYN_ALLOC(SDValue Op
);
130 /// SelectInlineAsmMemoryOperand - Implement addressing mode selection for
131 /// inline asm expressions.
132 virtual bool SelectInlineAsmMemoryOperand(const SDValue
&Op
,
134 std::vector
<SDValue
> &OutOps
);
138 void ARMDAGToDAGISel::InstructionSelect() {
142 CurDAG
->RemoveDeadNodes();
145 bool ARMDAGToDAGISel::SelectShifterOperandReg(SDValue Op
,
150 ARM_AM::ShiftOpc ShOpcVal
= ARM_AM::getShiftOpcForNode(N
);
152 // Don't match base register only case. That is matched to a separate
153 // lower complexity pattern with explicit register operand.
154 if (ShOpcVal
== ARM_AM::no_shift
) return false;
156 BaseReg
= N
.getOperand(0);
157 unsigned ShImmVal
= 0;
158 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
159 ShReg
= CurDAG
->getRegister(0, MVT::i32
);
160 ShImmVal
= RHS
->getZExtValue() & 31;
162 ShReg
= N
.getOperand(1);
164 Opc
= CurDAG
->getTargetConstant(ARM_AM::getSORegOpc(ShOpcVal
, ShImmVal
),
169 bool ARMDAGToDAGISel::SelectAddrMode2(SDValue Op
, SDValue N
,
170 SDValue
&Base
, SDValue
&Offset
,
172 if (N
.getOpcode() == ISD::MUL
) {
173 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
174 // X * [3,5,9] -> X + X * [2,4,8] etc.
175 int RHSC
= (int)RHS
->getZExtValue();
178 ARM_AM::AddrOpc AddSub
= ARM_AM::add
;
180 AddSub
= ARM_AM::sub
;
183 if (isPowerOf2_32(RHSC
)) {
184 unsigned ShAmt
= Log2_32(RHSC
);
185 Base
= Offset
= N
.getOperand(0);
186 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM2Opc(AddSub
, ShAmt
,
195 if (N
.getOpcode() != ISD::ADD
&& N
.getOpcode() != ISD::SUB
) {
197 if (N
.getOpcode() == ISD::FrameIndex
) {
198 int FI
= cast
<FrameIndexSDNode
>(N
)->getIndex();
199 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
200 } else if (N
.getOpcode() == ARMISD::Wrapper
) {
201 Base
= N
.getOperand(0);
203 Offset
= CurDAG
->getRegister(0, MVT::i32
);
204 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM2Opc(ARM_AM::add
, 0,
210 // Match simple R +/- imm12 operands.
211 if (N
.getOpcode() == ISD::ADD
)
212 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
213 int RHSC
= (int)RHS
->getZExtValue();
214 if ((RHSC
>= 0 && RHSC
< 0x1000) ||
215 (RHSC
< 0 && RHSC
> -0x1000)) { // 12 bits.
216 Base
= N
.getOperand(0);
217 if (Base
.getOpcode() == ISD::FrameIndex
) {
218 int FI
= cast
<FrameIndexSDNode
>(Base
)->getIndex();
219 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
221 Offset
= CurDAG
->getRegister(0, MVT::i32
);
223 ARM_AM::AddrOpc AddSub
= ARM_AM::add
;
225 AddSub
= ARM_AM::sub
;
228 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM2Opc(AddSub
, RHSC
,
235 // Otherwise this is R +/- [possibly shifted] R
236 ARM_AM::AddrOpc AddSub
= N
.getOpcode() == ISD::ADD
? ARM_AM::add
:ARM_AM::sub
;
237 ARM_AM::ShiftOpc ShOpcVal
= ARM_AM::getShiftOpcForNode(N
.getOperand(1));
240 Base
= N
.getOperand(0);
241 Offset
= N
.getOperand(1);
243 if (ShOpcVal
!= ARM_AM::no_shift
) {
244 // Check to see if the RHS of the shift is a constant, if not, we can't fold
246 if (ConstantSDNode
*Sh
=
247 dyn_cast
<ConstantSDNode
>(N
.getOperand(1).getOperand(1))) {
248 ShAmt
= Sh
->getZExtValue();
249 Offset
= N
.getOperand(1).getOperand(0);
251 ShOpcVal
= ARM_AM::no_shift
;
255 // Try matching (R shl C) + (R).
256 if (N
.getOpcode() == ISD::ADD
&& ShOpcVal
== ARM_AM::no_shift
) {
257 ShOpcVal
= ARM_AM::getShiftOpcForNode(N
.getOperand(0));
258 if (ShOpcVal
!= ARM_AM::no_shift
) {
259 // Check to see if the RHS of the shift is a constant, if not, we can't
261 if (ConstantSDNode
*Sh
=
262 dyn_cast
<ConstantSDNode
>(N
.getOperand(0).getOperand(1))) {
263 ShAmt
= Sh
->getZExtValue();
264 Offset
= N
.getOperand(0).getOperand(0);
265 Base
= N
.getOperand(1);
267 ShOpcVal
= ARM_AM::no_shift
;
272 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM2Opc(AddSub
, ShAmt
, ShOpcVal
),
277 bool ARMDAGToDAGISel::SelectAddrMode2Offset(SDValue Op
, SDValue N
,
278 SDValue
&Offset
, SDValue
&Opc
) {
279 unsigned Opcode
= Op
.getOpcode();
280 ISD::MemIndexedMode AM
= (Opcode
== ISD::LOAD
)
281 ? cast
<LoadSDNode
>(Op
)->getAddressingMode()
282 : cast
<StoreSDNode
>(Op
)->getAddressingMode();
283 ARM_AM::AddrOpc AddSub
= (AM
== ISD::PRE_INC
|| AM
== ISD::POST_INC
)
284 ? ARM_AM::add
: ARM_AM::sub
;
285 if (ConstantSDNode
*C
= dyn_cast
<ConstantSDNode
>(N
)) {
286 int Val
= (int)C
->getZExtValue();
287 if (Val
>= 0 && Val
< 0x1000) { // 12 bits.
288 Offset
= CurDAG
->getRegister(0, MVT::i32
);
289 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM2Opc(AddSub
, Val
,
297 ARM_AM::ShiftOpc ShOpcVal
= ARM_AM::getShiftOpcForNode(N
);
299 if (ShOpcVal
!= ARM_AM::no_shift
) {
300 // Check to see if the RHS of the shift is a constant, if not, we can't fold
302 if (ConstantSDNode
*Sh
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
303 ShAmt
= Sh
->getZExtValue();
304 Offset
= N
.getOperand(0);
306 ShOpcVal
= ARM_AM::no_shift
;
310 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM2Opc(AddSub
, ShAmt
, ShOpcVal
),
316 bool ARMDAGToDAGISel::SelectAddrMode3(SDValue Op
, SDValue N
,
317 SDValue
&Base
, SDValue
&Offset
,
319 if (N
.getOpcode() == ISD::SUB
) {
320 // X - C is canonicalize to X + -C, no need to handle it here.
321 Base
= N
.getOperand(0);
322 Offset
= N
.getOperand(1);
323 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM3Opc(ARM_AM::sub
, 0),MVT::i32
);
327 if (N
.getOpcode() != ISD::ADD
) {
329 if (N
.getOpcode() == ISD::FrameIndex
) {
330 int FI
= cast
<FrameIndexSDNode
>(N
)->getIndex();
331 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
333 Offset
= CurDAG
->getRegister(0, MVT::i32
);
334 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM3Opc(ARM_AM::add
, 0),MVT::i32
);
338 // If the RHS is +/- imm8, fold into addr mode.
339 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
340 int RHSC
= (int)RHS
->getZExtValue();
341 if ((RHSC
>= 0 && RHSC
< 256) ||
342 (RHSC
< 0 && RHSC
> -256)) { // note -256 itself isn't allowed.
343 Base
= N
.getOperand(0);
344 if (Base
.getOpcode() == ISD::FrameIndex
) {
345 int FI
= cast
<FrameIndexSDNode
>(Base
)->getIndex();
346 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
348 Offset
= CurDAG
->getRegister(0, MVT::i32
);
350 ARM_AM::AddrOpc AddSub
= ARM_AM::add
;
352 AddSub
= ARM_AM::sub
;
355 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM3Opc(AddSub
, RHSC
),MVT::i32
);
360 Base
= N
.getOperand(0);
361 Offset
= N
.getOperand(1);
362 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM3Opc(ARM_AM::add
, 0), MVT::i32
);
366 bool ARMDAGToDAGISel::SelectAddrMode3Offset(SDValue Op
, SDValue N
,
367 SDValue
&Offset
, SDValue
&Opc
) {
368 unsigned Opcode
= Op
.getOpcode();
369 ISD::MemIndexedMode AM
= (Opcode
== ISD::LOAD
)
370 ? cast
<LoadSDNode
>(Op
)->getAddressingMode()
371 : cast
<StoreSDNode
>(Op
)->getAddressingMode();
372 ARM_AM::AddrOpc AddSub
= (AM
== ISD::PRE_INC
|| AM
== ISD::POST_INC
)
373 ? ARM_AM::add
: ARM_AM::sub
;
374 if (ConstantSDNode
*C
= dyn_cast
<ConstantSDNode
>(N
)) {
375 int Val
= (int)C
->getZExtValue();
376 if (Val
>= 0 && Val
< 256) {
377 Offset
= CurDAG
->getRegister(0, MVT::i32
);
378 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM3Opc(AddSub
, Val
), MVT::i32
);
384 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM3Opc(AddSub
, 0), MVT::i32
);
388 bool ARMDAGToDAGISel::SelectAddrMode4(SDValue Op
, SDValue N
,
389 SDValue
&Addr
, SDValue
&Mode
) {
391 Mode
= CurDAG
->getTargetConstant(0, MVT::i32
);
395 bool ARMDAGToDAGISel::SelectAddrMode5(SDValue Op
, SDValue N
,
396 SDValue
&Base
, SDValue
&Offset
) {
397 if (N
.getOpcode() != ISD::ADD
) {
399 if (N
.getOpcode() == ISD::FrameIndex
) {
400 int FI
= cast
<FrameIndexSDNode
>(N
)->getIndex();
401 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
402 } else if (N
.getOpcode() == ARMISD::Wrapper
) {
403 Base
= N
.getOperand(0);
405 Offset
= CurDAG
->getTargetConstant(ARM_AM::getAM5Opc(ARM_AM::add
, 0),
410 // If the RHS is +/- imm8, fold into addr mode.
411 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
412 int RHSC
= (int)RHS
->getZExtValue();
413 if ((RHSC
& 3) == 0) { // The constant is implicitly multiplied by 4.
415 if ((RHSC
>= 0 && RHSC
< 256) ||
416 (RHSC
< 0 && RHSC
> -256)) { // note -256 itself isn't allowed.
417 Base
= N
.getOperand(0);
418 if (Base
.getOpcode() == ISD::FrameIndex
) {
419 int FI
= cast
<FrameIndexSDNode
>(Base
)->getIndex();
420 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
423 ARM_AM::AddrOpc AddSub
= ARM_AM::add
;
425 AddSub
= ARM_AM::sub
;
428 Offset
= CurDAG
->getTargetConstant(ARM_AM::getAM5Opc(AddSub
, RHSC
),
436 Offset
= CurDAG
->getTargetConstant(ARM_AM::getAM5Opc(ARM_AM::add
, 0),
441 bool ARMDAGToDAGISel::SelectAddrMode6(SDValue Op
, SDValue N
,
442 SDValue
&Addr
, SDValue
&Update
,
445 // The optional writeback is handled in ARMLoadStoreOpt.
446 Update
= CurDAG
->getRegister(0, MVT::i32
);
447 Opc
= CurDAG
->getTargetConstant(ARM_AM::getAM6Opc(false), MVT::i32
);
451 bool ARMDAGToDAGISel::SelectAddrModePC(SDValue Op
, SDValue N
,
452 SDValue
&Offset
, SDValue
&Label
) {
453 if (N
.getOpcode() == ARMISD::PIC_ADD
&& N
.hasOneUse()) {
454 Offset
= N
.getOperand(0);
455 SDValue N1
= N
.getOperand(1);
456 Label
= CurDAG
->getTargetConstant(cast
<ConstantSDNode
>(N1
)->getZExtValue(),
463 bool ARMDAGToDAGISel::SelectThumbAddrModeRR(SDValue Op
, SDValue N
,
464 SDValue
&Base
, SDValue
&Offset
){
465 // FIXME dl should come from the parent load or store, not the address
466 DebugLoc dl
= Op
.getDebugLoc();
467 if (N
.getOpcode() != ISD::ADD
) {
468 ConstantSDNode
*NC
= dyn_cast
<ConstantSDNode
>(N
);
469 if (!NC
|| NC
->getZExtValue() != 0)
476 Base
= N
.getOperand(0);
477 Offset
= N
.getOperand(1);
482 ARMDAGToDAGISel::SelectThumbAddrModeRI5(SDValue Op
, SDValue N
,
483 unsigned Scale
, SDValue
&Base
,
484 SDValue
&OffImm
, SDValue
&Offset
) {
486 SDValue TmpBase
, TmpOffImm
;
487 if (SelectThumbAddrModeSP(Op
, N
, TmpBase
, TmpOffImm
))
488 return false; // We want to select tLDRspi / tSTRspi instead.
489 if (N
.getOpcode() == ARMISD::Wrapper
&&
490 N
.getOperand(0).getOpcode() == ISD::TargetConstantPool
)
491 return false; // We want to select tLDRpci instead.
494 if (N
.getOpcode() != ISD::ADD
) {
495 Base
= (N
.getOpcode() == ARMISD::Wrapper
) ? N
.getOperand(0) : N
;
496 Offset
= CurDAG
->getRegister(0, MVT::i32
);
497 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
501 // Thumb does not have [sp, r] address mode.
502 RegisterSDNode
*LHSR
= dyn_cast
<RegisterSDNode
>(N
.getOperand(0));
503 RegisterSDNode
*RHSR
= dyn_cast
<RegisterSDNode
>(N
.getOperand(1));
504 if ((LHSR
&& LHSR
->getReg() == ARM::SP
) ||
505 (RHSR
&& RHSR
->getReg() == ARM::SP
)) {
507 Offset
= CurDAG
->getRegister(0, MVT::i32
);
508 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
512 // If the RHS is + imm5 * scale, fold into addr mode.
513 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
514 int RHSC
= (int)RHS
->getZExtValue();
515 if ((RHSC
& (Scale
-1)) == 0) { // The constant is implicitly multiplied.
517 if (RHSC
>= 0 && RHSC
< 32) {
518 Base
= N
.getOperand(0);
519 Offset
= CurDAG
->getRegister(0, MVT::i32
);
520 OffImm
= CurDAG
->getTargetConstant(RHSC
, MVT::i32
);
526 Base
= N
.getOperand(0);
527 Offset
= N
.getOperand(1);
528 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
532 bool ARMDAGToDAGISel::SelectThumbAddrModeS1(SDValue Op
, SDValue N
,
533 SDValue
&Base
, SDValue
&OffImm
,
535 return SelectThumbAddrModeRI5(Op
, N
, 1, Base
, OffImm
, Offset
);
538 bool ARMDAGToDAGISel::SelectThumbAddrModeS2(SDValue Op
, SDValue N
,
539 SDValue
&Base
, SDValue
&OffImm
,
541 return SelectThumbAddrModeRI5(Op
, N
, 2, Base
, OffImm
, Offset
);
544 bool ARMDAGToDAGISel::SelectThumbAddrModeS4(SDValue Op
, SDValue N
,
545 SDValue
&Base
, SDValue
&OffImm
,
547 return SelectThumbAddrModeRI5(Op
, N
, 4, Base
, OffImm
, Offset
);
550 bool ARMDAGToDAGISel::SelectThumbAddrModeSP(SDValue Op
, SDValue N
,
551 SDValue
&Base
, SDValue
&OffImm
) {
552 if (N
.getOpcode() == ISD::FrameIndex
) {
553 int FI
= cast
<FrameIndexSDNode
>(N
)->getIndex();
554 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
555 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
559 if (N
.getOpcode() != ISD::ADD
)
562 RegisterSDNode
*LHSR
= dyn_cast
<RegisterSDNode
>(N
.getOperand(0));
563 if (N
.getOperand(0).getOpcode() == ISD::FrameIndex
||
564 (LHSR
&& LHSR
->getReg() == ARM::SP
)) {
565 // If the RHS is + imm8 * scale, fold into addr mode.
566 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
567 int RHSC
= (int)RHS
->getZExtValue();
568 if ((RHSC
& 3) == 0) { // The constant is implicitly multiplied.
570 if (RHSC
>= 0 && RHSC
< 256) {
571 Base
= N
.getOperand(0);
572 if (Base
.getOpcode() == ISD::FrameIndex
) {
573 int FI
= cast
<FrameIndexSDNode
>(Base
)->getIndex();
574 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
576 OffImm
= CurDAG
->getTargetConstant(RHSC
, MVT::i32
);
586 bool ARMDAGToDAGISel::SelectT2ShifterOperandReg(SDValue Op
, SDValue N
,
589 ARM_AM::ShiftOpc ShOpcVal
= ARM_AM::getShiftOpcForNode(N
);
591 // Don't match base register only case. That is matched to a separate
592 // lower complexity pattern with explicit register operand.
593 if (ShOpcVal
== ARM_AM::no_shift
) return false;
595 BaseReg
= N
.getOperand(0);
596 unsigned ShImmVal
= 0;
597 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
598 ShImmVal
= RHS
->getZExtValue() & 31;
599 Opc
= getI32Imm(ARM_AM::getSORegOpc(ShOpcVal
, ShImmVal
));
606 bool ARMDAGToDAGISel::SelectT2AddrModeImm12(SDValue Op
, SDValue N
,
607 SDValue
&Base
, SDValue
&OffImm
) {
608 // Match simple R + imm12 operands.
611 if (N
.getOpcode() != ISD::ADD
&& N
.getOpcode() != ISD::SUB
) {
612 if (N
.getOpcode() == ISD::FrameIndex
) {
613 // Match frame index...
614 int FI
= cast
<FrameIndexSDNode
>(N
)->getIndex();
615 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
616 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
618 } else if (N
.getOpcode() == ARMISD::Wrapper
) {
619 Base
= N
.getOperand(0);
620 if (Base
.getOpcode() == ISD::TargetConstantPool
)
621 return false; // We want to select t2LDRpci instead.
624 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
628 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
629 if (SelectT2AddrModeImm8(Op
, N
, Base
, OffImm
))
630 // Let t2LDRi8 handle (R - imm8).
633 int RHSC
= (int)RHS
->getZExtValue();
634 if (N
.getOpcode() == ISD::SUB
)
637 if (RHSC
>= 0 && RHSC
< 0x1000) { // 12 bits (unsigned)
638 Base
= N
.getOperand(0);
639 if (Base
.getOpcode() == ISD::FrameIndex
) {
640 int FI
= cast
<FrameIndexSDNode
>(Base
)->getIndex();
641 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
643 OffImm
= CurDAG
->getTargetConstant(RHSC
, MVT::i32
);
650 OffImm
= CurDAG
->getTargetConstant(0, MVT::i32
);
654 bool ARMDAGToDAGISel::SelectT2AddrModeImm8(SDValue Op
, SDValue N
,
655 SDValue
&Base
, SDValue
&OffImm
) {
656 // Match simple R - imm8 operands.
657 if (N
.getOpcode() == ISD::ADD
|| N
.getOpcode() == ISD::SUB
) {
658 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
659 int RHSC
= (int)RHS
->getSExtValue();
660 if (N
.getOpcode() == ISD::SUB
)
663 if ((RHSC
>= -255) && (RHSC
< 0)) { // 8 bits (always negative)
664 Base
= N
.getOperand(0);
665 if (Base
.getOpcode() == ISD::FrameIndex
) {
666 int FI
= cast
<FrameIndexSDNode
>(Base
)->getIndex();
667 Base
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
669 OffImm
= CurDAG
->getTargetConstant(RHSC
, MVT::i32
);
678 bool ARMDAGToDAGISel::SelectT2AddrModeImm8Offset(SDValue Op
, SDValue N
,
680 unsigned Opcode
= Op
.getOpcode();
681 ISD::MemIndexedMode AM
= (Opcode
== ISD::LOAD
)
682 ? cast
<LoadSDNode
>(Op
)->getAddressingMode()
683 : cast
<StoreSDNode
>(Op
)->getAddressingMode();
684 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
)) {
685 int RHSC
= (int)RHS
->getZExtValue();
686 if (RHSC
>= 0 && RHSC
< 0x100) { // 8 bits.
687 OffImm
= ((AM
== ISD::PRE_INC
) || (AM
== ISD::POST_INC
))
688 ? CurDAG
->getTargetConstant(RHSC
, MVT::i32
)
689 : CurDAG
->getTargetConstant(-RHSC
, MVT::i32
);
697 bool ARMDAGToDAGISel::SelectT2AddrModeImm8s4(SDValue Op
, SDValue N
,
698 SDValue
&Base
, SDValue
&OffImm
) {
699 if (N
.getOpcode() == ISD::ADD
) {
700 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
701 int RHSC
= (int)RHS
->getZExtValue();
702 if (((RHSC
& 0x3) == 0) &&
703 ((RHSC
>= 0 && RHSC
< 0x400) || (RHSC
< 0 && RHSC
> -0x400))) { // 8 bits.
704 Base
= N
.getOperand(0);
705 OffImm
= CurDAG
->getTargetConstant(RHSC
, MVT::i32
);
709 } else if (N
.getOpcode() == ISD::SUB
) {
710 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
711 int RHSC
= (int)RHS
->getZExtValue();
712 if (((RHSC
& 0x3) == 0) && (RHSC
>= 0 && RHSC
< 0x400)) { // 8 bits.
713 Base
= N
.getOperand(0);
714 OffImm
= CurDAG
->getTargetConstant(-RHSC
, MVT::i32
);
723 bool ARMDAGToDAGISel::SelectT2AddrModeSoReg(SDValue Op
, SDValue N
,
725 SDValue
&OffReg
, SDValue
&ShImm
) {
726 // (R - imm8) should be handled by t2LDRi8. The rest are handled by t2LDRi12.
727 if (N
.getOpcode() != ISD::ADD
)
730 // Leave (R + imm12) for t2LDRi12, (R - imm8) for t2LDRi8.
731 if (ConstantSDNode
*RHS
= dyn_cast
<ConstantSDNode
>(N
.getOperand(1))) {
732 int RHSC
= (int)RHS
->getZExtValue();
733 if (RHSC
>= 0 && RHSC
< 0x1000) // 12 bits (unsigned)
735 else if (RHSC
< 0 && RHSC
>= -255) // 8 bits
739 // Look for (R + R) or (R + (R << [1,2,3])).
741 Base
= N
.getOperand(0);
742 OffReg
= N
.getOperand(1);
744 // Swap if it is ((R << c) + R).
745 ARM_AM::ShiftOpc ShOpcVal
= ARM_AM::getShiftOpcForNode(OffReg
);
746 if (ShOpcVal
!= ARM_AM::lsl
) {
747 ShOpcVal
= ARM_AM::getShiftOpcForNode(Base
);
748 if (ShOpcVal
== ARM_AM::lsl
)
749 std::swap(Base
, OffReg
);
752 if (ShOpcVal
== ARM_AM::lsl
) {
753 // Check to see if the RHS of the shift is a constant, if not, we can't fold
755 if (ConstantSDNode
*Sh
= dyn_cast
<ConstantSDNode
>(OffReg
.getOperand(1))) {
756 ShAmt
= Sh
->getZExtValue();
759 ShOpcVal
= ARM_AM::no_shift
;
761 OffReg
= OffReg
.getOperand(0);
763 ShOpcVal
= ARM_AM::no_shift
;
767 ShImm
= CurDAG
->getTargetConstant(ShAmt
, MVT::i32
);
772 //===--------------------------------------------------------------------===//
774 /// getAL - Returns a ARMCC::AL immediate node.
775 static inline SDValue
getAL(SelectionDAG
*CurDAG
) {
776 return CurDAG
->getTargetConstant((uint64_t)ARMCC::AL
, MVT::i32
);
779 SDNode
*ARMDAGToDAGISel::SelectARMIndexedLoad(SDValue Op
) {
780 LoadSDNode
*LD
= cast
<LoadSDNode
>(Op
);
781 ISD::MemIndexedMode AM
= LD
->getAddressingMode();
782 if (AM
== ISD::UNINDEXED
)
785 EVT LoadedVT
= LD
->getMemoryVT();
786 SDValue Offset
, AMOpc
;
787 bool isPre
= (AM
== ISD::PRE_INC
) || (AM
== ISD::PRE_DEC
);
790 if (LoadedVT
== MVT::i32
&&
791 SelectAddrMode2Offset(Op
, LD
->getOffset(), Offset
, AMOpc
)) {
792 Opcode
= isPre
? ARM::LDR_PRE
: ARM::LDR_POST
;
794 } else if (LoadedVT
== MVT::i16
&&
795 SelectAddrMode3Offset(Op
, LD
->getOffset(), Offset
, AMOpc
)) {
797 Opcode
= (LD
->getExtensionType() == ISD::SEXTLOAD
)
798 ? (isPre
? ARM::LDRSH_PRE
: ARM::LDRSH_POST
)
799 : (isPre
? ARM::LDRH_PRE
: ARM::LDRH_POST
);
800 } else if (LoadedVT
== MVT::i8
|| LoadedVT
== MVT::i1
) {
801 if (LD
->getExtensionType() == ISD::SEXTLOAD
) {
802 if (SelectAddrMode3Offset(Op
, LD
->getOffset(), Offset
, AMOpc
)) {
804 Opcode
= isPre
? ARM::LDRSB_PRE
: ARM::LDRSB_POST
;
807 if (SelectAddrMode2Offset(Op
, LD
->getOffset(), Offset
, AMOpc
)) {
809 Opcode
= isPre
? ARM::LDRB_PRE
: ARM::LDRB_POST
;
815 SDValue Chain
= LD
->getChain();
816 SDValue Base
= LD
->getBasePtr();
817 SDValue Ops
[]= { Base
, Offset
, AMOpc
, getAL(CurDAG
),
818 CurDAG
->getRegister(0, MVT::i32
), Chain
};
819 return CurDAG
->getTargetNode(Opcode
, Op
.getDebugLoc(), MVT::i32
, MVT::i32
,
826 SDNode
*ARMDAGToDAGISel::SelectT2IndexedLoad(SDValue Op
) {
827 LoadSDNode
*LD
= cast
<LoadSDNode
>(Op
);
828 ISD::MemIndexedMode AM
= LD
->getAddressingMode();
829 if (AM
== ISD::UNINDEXED
)
832 EVT LoadedVT
= LD
->getMemoryVT();
833 bool isSExtLd
= LD
->getExtensionType() == ISD::SEXTLOAD
;
835 bool isPre
= (AM
== ISD::PRE_INC
) || (AM
== ISD::PRE_DEC
);
838 if (SelectT2AddrModeImm8Offset(Op
, LD
->getOffset(), Offset
)) {
839 switch (LoadedVT
.getSimpleVT().SimpleTy
) {
841 Opcode
= isPre
? ARM::t2LDR_PRE
: ARM::t2LDR_POST
;
845 Opcode
= isPre
? ARM::t2LDRSH_PRE
: ARM::t2LDRSH_POST
;
847 Opcode
= isPre
? ARM::t2LDRH_PRE
: ARM::t2LDRH_POST
;
852 Opcode
= isPre
? ARM::t2LDRSB_PRE
: ARM::t2LDRSB_POST
;
854 Opcode
= isPre
? ARM::t2LDRB_PRE
: ARM::t2LDRB_POST
;
863 SDValue Chain
= LD
->getChain();
864 SDValue Base
= LD
->getBasePtr();
865 SDValue Ops
[]= { Base
, Offset
, getAL(CurDAG
),
866 CurDAG
->getRegister(0, MVT::i32
), Chain
};
867 return CurDAG
->getTargetNode(Opcode
, Op
.getDebugLoc(), MVT::i32
, MVT::i32
,
874 SDNode
*ARMDAGToDAGISel::SelectDYN_ALLOC(SDValue Op
) {
875 SDNode
*N
= Op
.getNode();
876 DebugLoc dl
= N
->getDebugLoc();
877 EVT VT
= Op
.getValueType();
878 SDValue Chain
= Op
.getOperand(0);
879 SDValue Size
= Op
.getOperand(1);
880 SDValue Align
= Op
.getOperand(2);
881 SDValue SP
= CurDAG
->getRegister(ARM::SP
, MVT::i32
);
882 int32_t AlignVal
= cast
<ConstantSDNode
>(Align
)->getSExtValue();
884 // We need to align the stack. Use Thumb1 tAND which is the only thumb
885 // instruction that can read and write SP. This matches to a pseudo
886 // instruction that has a chain to ensure the result is written back to
887 // the stack pointer.
888 SP
= SDValue(CurDAG
->getTargetNode(ARM::tANDsp
, dl
, VT
, SP
, Align
), 0);
890 bool isC
= isa
<ConstantSDNode
>(Size
);
891 uint32_t C
= isC
? cast
<ConstantSDNode
>(Size
)->getZExtValue() : ~0UL;
892 // Handle the most common case for both Thumb1 and Thumb2:
893 // tSUBspi - immediate is between 0 ... 508 inclusive.
894 if (C
<= 508 && ((C
& 3) == 0))
895 // FIXME: tSUBspi encode scale 4 implicitly.
896 return CurDAG
->SelectNodeTo(N
, ARM::tSUBspi_
, VT
, MVT::Other
, SP
,
897 CurDAG
->getTargetConstant(C
/4, MVT::i32
),
900 if (Subtarget
->isThumb1Only()) {
901 // Use tADDspr since Thumb1 does not have a sub r, sp, r. ARMISelLowering
902 // should have negated the size operand already. FIXME: We can't insert
903 // new target independent node at this stage so we are forced to negate
904 // it earlier. Is there a better solution?
905 return CurDAG
->SelectNodeTo(N
, ARM::tADDspr_
, VT
, MVT::Other
, SP
, Size
,
907 } else if (Subtarget
->isThumb2()) {
908 if (isC
&& Predicate_t2_so_imm(Size
.getNode())) {
910 SDValue Ops
[] = { SP
, CurDAG
->getTargetConstant(C
, MVT::i32
), Chain
};
911 return CurDAG
->SelectNodeTo(N
, ARM::t2SUBrSPi_
, VT
, MVT::Other
, Ops
, 3);
912 } else if (isC
&& Predicate_imm0_4095(Size
.getNode())) {
914 SDValue Ops
[] = { SP
, CurDAG
->getTargetConstant(C
, MVT::i32
), Chain
};
915 return CurDAG
->SelectNodeTo(N
, ARM::t2SUBrSPi12_
, VT
, MVT::Other
, Ops
, 3);
918 SDValue Ops
[] = { SP
, Size
,
919 getI32Imm(ARM_AM::getSORegOpc(ARM_AM::lsl
,0)), Chain
};
920 return CurDAG
->SelectNodeTo(N
, ARM::t2SUBrSPs_
, VT
, MVT::Other
, Ops
, 4);
924 // FIXME: Add ADD / SUB sp instructions for ARM.
928 SDNode
*ARMDAGToDAGISel::Select(SDValue Op
) {
929 SDNode
*N
= Op
.getNode();
930 DebugLoc dl
= N
->getDebugLoc();
932 if (N
->isMachineOpcode())
933 return NULL
; // Already selected.
935 switch (N
->getOpcode()) {
937 case ISD::Constant
: {
938 unsigned Val
= cast
<ConstantSDNode
>(N
)->getZExtValue();
940 if (Subtarget
->isThumb()) {
941 if (Subtarget
->hasThumb2())
942 // Thumb2 has the MOVT instruction, so all immediates can
943 // be done with MOV + MOVT, at worst.
946 UseCP
= (Val
> 255 && // MOV
947 ~Val
> 255 && // MOV + MVN
948 !ARM_AM::isThumbImmShiftedVal(Val
)); // MOV + LSL
950 UseCP
= (ARM_AM::getSOImmVal(Val
) == -1 && // MOV
951 ARM_AM::getSOImmVal(~Val
) == -1 && // MVN
952 !ARM_AM::isSOImmTwoPartVal(Val
)); // two instrs.
955 CurDAG
->getTargetConstantPool(ConstantInt::get(Type::Int32Ty
, Val
),
959 if (Subtarget
->isThumb1Only()) {
960 SDValue Pred
= CurDAG
->getTargetConstant(0xEULL
, MVT::i32
);
961 SDValue PredReg
= CurDAG
->getRegister(0, MVT::i32
);
962 SDValue Ops
[] = { CPIdx
, Pred
, PredReg
, CurDAG
->getEntryNode() };
963 ResNode
= CurDAG
->getTargetNode(ARM::tLDRcp
, dl
, MVT::i32
, MVT::Other
,
968 CurDAG
->getRegister(0, MVT::i32
),
969 CurDAG
->getTargetConstant(0, MVT::i32
),
971 CurDAG
->getRegister(0, MVT::i32
),
972 CurDAG
->getEntryNode()
974 ResNode
=CurDAG
->getTargetNode(ARM::LDRcp
, dl
, MVT::i32
, MVT::Other
,
977 ReplaceUses(Op
, SDValue(ResNode
, 0));
981 // Other cases are autogenerated.
984 case ISD::FrameIndex
: {
985 // Selects to ADDri FI, 0 which in turn will become ADDri SP, imm.
986 int FI
= cast
<FrameIndexSDNode
>(N
)->getIndex();
987 SDValue TFI
= CurDAG
->getTargetFrameIndex(FI
, TLI
.getPointerTy());
988 if (Subtarget
->isThumb1Only()) {
989 return CurDAG
->SelectNodeTo(N
, ARM::tADDrSPi
, MVT::i32
, TFI
,
990 CurDAG
->getTargetConstant(0, MVT::i32
));
992 unsigned Opc
= ((Subtarget
->isThumb() && Subtarget
->hasThumb2()) ?
993 ARM::t2ADDri
: ARM::ADDri
);
994 SDValue Ops
[] = { TFI
, CurDAG
->getTargetConstant(0, MVT::i32
),
995 getAL(CurDAG
), CurDAG
->getRegister(0, MVT::i32
),
996 CurDAG
->getRegister(0, MVT::i32
) };
997 return CurDAG
->SelectNodeTo(N
, Opc
, MVT::i32
, Ops
, 5);
1000 case ARMISD::DYN_ALLOC
:
1001 return SelectDYN_ALLOC(Op
);
1003 if (Subtarget
->isThumb1Only())
1005 if (ConstantSDNode
*C
= dyn_cast
<ConstantSDNode
>(Op
.getOperand(1))) {
1006 unsigned RHSV
= C
->getZExtValue();
1008 if (isPowerOf2_32(RHSV
-1)) { // 2^n+1?
1009 unsigned ShImm
= Log2_32(RHSV
-1);
1012 SDValue V
= Op
.getOperand(0);
1013 ShImm
= ARM_AM::getSORegOpc(ARM_AM::lsl
, ShImm
);
1014 SDValue ShImmOp
= CurDAG
->getTargetConstant(ShImm
, MVT::i32
);
1015 SDValue Reg0
= CurDAG
->getRegister(0, MVT::i32
);
1016 if (Subtarget
->isThumb()) {
1017 SDValue Ops
[] = { V
, V
, ShImmOp
, getAL(CurDAG
), Reg0
, Reg0
};
1018 return CurDAG
->SelectNodeTo(N
, ARM::t2ADDrs
, MVT::i32
, Ops
, 6);
1020 SDValue Ops
[] = { V
, V
, Reg0
, ShImmOp
, getAL(CurDAG
), Reg0
, Reg0
};
1021 return CurDAG
->SelectNodeTo(N
, ARM::ADDrs
, MVT::i32
, Ops
, 7);
1024 if (isPowerOf2_32(RHSV
+1)) { // 2^n-1?
1025 unsigned ShImm
= Log2_32(RHSV
+1);
1028 SDValue V
= Op
.getOperand(0);
1029 ShImm
= ARM_AM::getSORegOpc(ARM_AM::lsl
, ShImm
);
1030 SDValue ShImmOp
= CurDAG
->getTargetConstant(ShImm
, MVT::i32
);
1031 SDValue Reg0
= CurDAG
->getRegister(0, MVT::i32
);
1032 if (Subtarget
->isThumb()) {
1033 SDValue Ops
[] = { V
, V
, ShImmOp
, getAL(CurDAG
), Reg0
};
1034 return CurDAG
->SelectNodeTo(N
, ARM::t2RSBrs
, MVT::i32
, Ops
, 5);
1036 SDValue Ops
[] = { V
, V
, Reg0
, ShImmOp
, getAL(CurDAG
), Reg0
, Reg0
};
1037 return CurDAG
->SelectNodeTo(N
, ARM::RSBrs
, MVT::i32
, Ops
, 7);
1043 return CurDAG
->getTargetNode(ARM::FMRRD
, dl
, MVT::i32
, MVT::i32
,
1044 Op
.getOperand(0), getAL(CurDAG
),
1045 CurDAG
->getRegister(0, MVT::i32
));
1046 case ISD::UMUL_LOHI
: {
1047 if (Subtarget
->isThumb1Only())
1049 if (Subtarget
->isThumb()) {
1050 SDValue Ops
[] = { Op
.getOperand(0), Op
.getOperand(1),
1051 getAL(CurDAG
), CurDAG
->getRegister(0, MVT::i32
),
1052 CurDAG
->getRegister(0, MVT::i32
) };
1053 return CurDAG
->getTargetNode(ARM::t2UMULL
, dl
, MVT::i32
, MVT::i32
, Ops
,4);
1055 SDValue Ops
[] = { Op
.getOperand(0), Op
.getOperand(1),
1056 getAL(CurDAG
), CurDAG
->getRegister(0, MVT::i32
),
1057 CurDAG
->getRegister(0, MVT::i32
) };
1058 return CurDAG
->getTargetNode(ARM::UMULL
, dl
, MVT::i32
, MVT::i32
, Ops
, 5);
1061 case ISD::SMUL_LOHI
: {
1062 if (Subtarget
->isThumb1Only())
1064 if (Subtarget
->isThumb()) {
1065 SDValue Ops
[] = { Op
.getOperand(0), Op
.getOperand(1),
1066 getAL(CurDAG
), CurDAG
->getRegister(0, MVT::i32
) };
1067 return CurDAG
->getTargetNode(ARM::t2SMULL
, dl
, MVT::i32
, MVT::i32
, Ops
,4);
1069 SDValue Ops
[] = { Op
.getOperand(0), Op
.getOperand(1),
1070 getAL(CurDAG
), CurDAG
->getRegister(0, MVT::i32
),
1071 CurDAG
->getRegister(0, MVT::i32
) };
1072 return CurDAG
->getTargetNode(ARM::SMULL
, dl
, MVT::i32
, MVT::i32
, Ops
, 5);
1076 SDNode
*ResNode
= 0;
1077 if (Subtarget
->isThumb() && Subtarget
->hasThumb2())
1078 ResNode
= SelectT2IndexedLoad(Op
);
1080 ResNode
= SelectARMIndexedLoad(Op
);
1083 // Other cases are autogenerated.
1086 case ARMISD::BRCOND
: {
1087 // Pattern: (ARMbrcond:void (bb:Other):$dst, (imm:i32):$cc)
1088 // Emits: (Bcc:void (bb:Other):$dst, (imm:i32):$cc)
1089 // Pattern complexity = 6 cost = 1 size = 0
1091 // Pattern: (ARMbrcond:void (bb:Other):$dst, (imm:i32):$cc)
1092 // Emits: (tBcc:void (bb:Other):$dst, (imm:i32):$cc)
1093 // Pattern complexity = 6 cost = 1 size = 0
1095 // Pattern: (ARMbrcond:void (bb:Other):$dst, (imm:i32):$cc)
1096 // Emits: (t2Bcc:void (bb:Other):$dst, (imm:i32):$cc)
1097 // Pattern complexity = 6 cost = 1 size = 0
1099 unsigned Opc
= Subtarget
->isThumb() ?
1100 ((Subtarget
->hasThumb2()) ? ARM::t2Bcc
: ARM::tBcc
) : ARM::Bcc
;
1101 SDValue Chain
= Op
.getOperand(0);
1102 SDValue N1
= Op
.getOperand(1);
1103 SDValue N2
= Op
.getOperand(2);
1104 SDValue N3
= Op
.getOperand(3);
1105 SDValue InFlag
= Op
.getOperand(4);
1106 assert(N1
.getOpcode() == ISD::BasicBlock
);
1107 assert(N2
.getOpcode() == ISD::Constant
);
1108 assert(N3
.getOpcode() == ISD::Register
);
1110 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1111 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1113 SDValue Ops
[] = { N1
, Tmp2
, N3
, Chain
, InFlag
};
1114 SDNode
*ResNode
= CurDAG
->getTargetNode(Opc
, dl
, MVT::Other
,
1116 Chain
= SDValue(ResNode
, 0);
1117 if (Op
.getNode()->getNumValues() == 2) {
1118 InFlag
= SDValue(ResNode
, 1);
1119 ReplaceUses(SDValue(Op
.getNode(), 1), InFlag
);
1121 ReplaceUses(SDValue(Op
.getNode(), 0), SDValue(Chain
.getNode(), Chain
.getResNo()));
1124 case ARMISD::CMOV
: {
1125 EVT VT
= Op
.getValueType();
1126 SDValue N0
= Op
.getOperand(0);
1127 SDValue N1
= Op
.getOperand(1);
1128 SDValue N2
= Op
.getOperand(2);
1129 SDValue N3
= Op
.getOperand(3);
1130 SDValue InFlag
= Op
.getOperand(4);
1131 assert(N2
.getOpcode() == ISD::Constant
);
1132 assert(N3
.getOpcode() == ISD::Register
);
1134 if (!Subtarget
->isThumb1Only() && VT
== MVT::i32
) {
1135 // Pattern: (ARMcmov:i32 GPR:i32:$false, so_reg:i32:$true, (imm:i32):$cc)
1136 // Emits: (MOVCCs:i32 GPR:i32:$false, so_reg:i32:$true, (imm:i32):$cc)
1137 // Pattern complexity = 18 cost = 1 size = 0
1141 if (Subtarget
->isThumb()) {
1142 if (SelectT2ShifterOperandReg(Op
, N1
, CPTmp0
, CPTmp1
)) {
1143 unsigned SOVal
= cast
<ConstantSDNode
>(CPTmp1
)->getZExtValue();
1144 unsigned SOShOp
= ARM_AM::getSORegShOp(SOVal
);
1147 case ARM_AM::lsl
: Opc
= ARM::t2MOVCClsl
; break;
1148 case ARM_AM::lsr
: Opc
= ARM::t2MOVCClsr
; break;
1149 case ARM_AM::asr
: Opc
= ARM::t2MOVCCasr
; break;
1150 case ARM_AM::ror
: Opc
= ARM::t2MOVCCror
; break;
1152 llvm_unreachable("Unknown so_reg opcode!");
1156 CurDAG
->getTargetConstant(ARM_AM::getSORegOffset(SOVal
), MVT::i32
);
1157 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1158 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1160 SDValue Ops
[] = { N0
, CPTmp0
, SOShImm
, Tmp2
, N3
, InFlag
};
1161 return CurDAG
->SelectNodeTo(Op
.getNode(), Opc
, MVT::i32
,Ops
, 6);
1164 if (SelectShifterOperandReg(Op
, N1
, CPTmp0
, CPTmp1
, CPTmp2
)) {
1165 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1166 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1168 SDValue Ops
[] = { N0
, CPTmp0
, CPTmp1
, CPTmp2
, Tmp2
, N3
, InFlag
};
1169 return CurDAG
->SelectNodeTo(Op
.getNode(),
1170 ARM::MOVCCs
, MVT::i32
, Ops
, 7);
1174 // Pattern: (ARMcmov:i32 GPR:i32:$false,
1175 // (imm:i32)<<P:Predicate_so_imm>>:$true,
1177 // Emits: (MOVCCi:i32 GPR:i32:$false,
1178 // (so_imm:i32 (imm:i32):$true), (imm:i32):$cc)
1179 // Pattern complexity = 10 cost = 1 size = 0
1180 if (N3
.getOpcode() == ISD::Constant
) {
1181 if (Subtarget
->isThumb()) {
1182 if (Predicate_t2_so_imm(N3
.getNode())) {
1183 SDValue Tmp1
= CurDAG
->getTargetConstant(((unsigned)
1184 cast
<ConstantSDNode
>(N1
)->getZExtValue()),
1186 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1187 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1189 SDValue Ops
[] = { N0
, Tmp1
, Tmp2
, N3
, InFlag
};
1190 return CurDAG
->SelectNodeTo(Op
.getNode(),
1191 ARM::t2MOVCCi
, MVT::i32
, Ops
, 5);
1194 if (Predicate_so_imm(N3
.getNode())) {
1195 SDValue Tmp1
= CurDAG
->getTargetConstant(((unsigned)
1196 cast
<ConstantSDNode
>(N1
)->getZExtValue()),
1198 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1199 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1201 SDValue Ops
[] = { N0
, Tmp1
, Tmp2
, N3
, InFlag
};
1202 return CurDAG
->SelectNodeTo(Op
.getNode(),
1203 ARM::MOVCCi
, MVT::i32
, Ops
, 5);
1209 // Pattern: (ARMcmov:i32 GPR:i32:$false, GPR:i32:$true, (imm:i32):$cc)
1210 // Emits: (MOVCCr:i32 GPR:i32:$false, GPR:i32:$true, (imm:i32):$cc)
1211 // Pattern complexity = 6 cost = 1 size = 0
1213 // Pattern: (ARMcmov:i32 GPR:i32:$false, GPR:i32:$true, (imm:i32):$cc)
1214 // Emits: (tMOVCCr:i32 GPR:i32:$false, GPR:i32:$true, (imm:i32):$cc)
1215 // Pattern complexity = 6 cost = 11 size = 0
1217 // Also FCPYScc and FCPYDcc.
1218 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1219 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1221 SDValue Ops
[] = { N0
, N1
, Tmp2
, N3
, InFlag
};
1223 switch (VT
.getSimpleVT().SimpleTy
) {
1224 default: assert(false && "Illegal conditional move type!");
1227 Opc
= Subtarget
->isThumb()
1228 ? (Subtarget
->hasThumb2() ? ARM::t2MOVCCr
: ARM::tMOVCCr_pseudo
)
1238 return CurDAG
->SelectNodeTo(Op
.getNode(), Opc
, VT
, Ops
, 5);
1240 case ARMISD::CNEG
: {
1241 EVT VT
= Op
.getValueType();
1242 SDValue N0
= Op
.getOperand(0);
1243 SDValue N1
= Op
.getOperand(1);
1244 SDValue N2
= Op
.getOperand(2);
1245 SDValue N3
= Op
.getOperand(3);
1246 SDValue InFlag
= Op
.getOperand(4);
1247 assert(N2
.getOpcode() == ISD::Constant
);
1248 assert(N3
.getOpcode() == ISD::Register
);
1250 SDValue Tmp2
= CurDAG
->getTargetConstant(((unsigned)
1251 cast
<ConstantSDNode
>(N2
)->getZExtValue()),
1253 SDValue Ops
[] = { N0
, N1
, Tmp2
, N3
, InFlag
};
1255 switch (VT
.getSimpleVT().SimpleTy
) {
1256 default: assert(false && "Illegal conditional move type!");
1265 return CurDAG
->SelectNodeTo(Op
.getNode(), Opc
, VT
, Ops
, 5);
1268 case ISD::DECLARE
: {
1269 SDValue Chain
= Op
.getOperand(0);
1270 SDValue N1
= Op
.getOperand(1);
1271 SDValue N2
= Op
.getOperand(2);
1272 FrameIndexSDNode
*FINode
= dyn_cast
<FrameIndexSDNode
>(N1
);
1273 // FIXME: handle VLAs.
1275 ReplaceUses(Op
.getValue(0), Chain
);
1278 if (N2
.getOpcode() == ARMISD::PIC_ADD
&& isa
<LoadSDNode
>(N2
.getOperand(0)))
1279 N2
= N2
.getOperand(0);
1280 LoadSDNode
*Ld
= dyn_cast
<LoadSDNode
>(N2
);
1282 ReplaceUses(Op
.getValue(0), Chain
);
1285 SDValue BasePtr
= Ld
->getBasePtr();
1286 assert(BasePtr
.getOpcode() == ARMISD::Wrapper
&&
1287 isa
<ConstantPoolSDNode
>(BasePtr
.getOperand(0)) &&
1288 "llvm.dbg.variable should be a constantpool node");
1289 ConstantPoolSDNode
*CP
= cast
<ConstantPoolSDNode
>(BasePtr
.getOperand(0));
1290 GlobalValue
*GV
= 0;
1291 if (CP
->isMachineConstantPoolEntry()) {
1292 ARMConstantPoolValue
*ACPV
= (ARMConstantPoolValue
*)CP
->getMachineCPVal();
1295 GV
= dyn_cast
<GlobalValue
>(CP
->getConstVal());
1297 ReplaceUses(Op
.getValue(0), Chain
);
1301 SDValue Tmp1
= CurDAG
->getTargetFrameIndex(FINode
->getIndex(),
1302 TLI
.getPointerTy());
1303 SDValue Tmp2
= CurDAG
->getTargetGlobalAddress(GV
, TLI
.getPointerTy());
1304 SDValue Ops
[] = { Tmp1
, Tmp2
, Chain
};
1305 return CurDAG
->getTargetNode(TargetInstrInfo::DECLARE
, dl
,
1306 MVT::Other
, Ops
, 3);
1309 case ISD::VECTOR_SHUFFLE
: {
1310 EVT VT
= Op
.getValueType();
1312 // Match 128-bit splat to VDUPLANEQ. (This could be done with a Pat in
1313 // ARMInstrNEON.td but it is awkward because the shuffle mask needs to be
1314 // transformed first into a lane number and then to both a subregister
1315 // index and an adjusted lane number.) If the source operand is a
1316 // SCALAR_TO_VECTOR, leave it so it will be matched later as a VDUP.
1317 ShuffleVectorSDNode
*SVOp
= cast
<ShuffleVectorSDNode
>(N
);
1318 if (VT
.is128BitVector() && SVOp
->isSplat() &&
1319 Op
.getOperand(0).getOpcode() != ISD::SCALAR_TO_VECTOR
&&
1320 Op
.getOperand(1).getOpcode() == ISD::UNDEF
) {
1321 unsigned LaneVal
= SVOp
->getSplatIndex();
1325 switch (VT
.getVectorElementType().getSimpleVT().SimpleTy
) {
1326 default: llvm_unreachable("unhandled VDUP splat type");
1327 case MVT::i8
: Opc
= ARM::VDUPLN8q
; HalfVT
= MVT::v8i8
; break;
1328 case MVT::i16
: Opc
= ARM::VDUPLN16q
; HalfVT
= MVT::v4i16
; break;
1329 case MVT::i32
: Opc
= ARM::VDUPLN32q
; HalfVT
= MVT::v2i32
; break;
1330 case MVT::f32
: Opc
= ARM::VDUPLNfq
; HalfVT
= MVT::v2f32
; break;
1333 // The source operand needs to be changed to a subreg of the original
1334 // 128-bit operand, and the lane number needs to be adjusted accordingly.
1335 unsigned NumElts
= VT
.getVectorNumElements() / 2;
1336 unsigned SRVal
= (LaneVal
< NumElts
? arm_dsubreg_0
: arm_dsubreg_1
);
1337 SDValue SR
= CurDAG
->getTargetConstant(SRVal
, MVT::i32
);
1338 SDValue NewLane
= CurDAG
->getTargetConstant(LaneVal
% NumElts
, MVT::i32
);
1339 SDNode
*SubReg
= CurDAG
->getTargetNode(TargetInstrInfo::EXTRACT_SUBREG
,
1340 dl
, HalfVT
, N
->getOperand(0), SR
);
1341 return CurDAG
->SelectNodeTo(N
, Opc
, VT
, SDValue(SubReg
, 0), NewLane
);
1347 case ARMISD::VLD2D
: {
1348 SDValue MemAddr
, MemUpdate
, MemOpc
;
1349 if (!SelectAddrMode6(Op
, N
->getOperand(1), MemAddr
, MemUpdate
, MemOpc
))
1352 EVT VT
= Op
.getValueType();
1353 switch (VT
.getSimpleVT().SimpleTy
) {
1354 default: llvm_unreachable("unhandled VLD2D type");
1355 case MVT::v8i8
: Opc
= ARM::VLD2d8
; break;
1356 case MVT::v4i16
: Opc
= ARM::VLD2d16
; break;
1358 case MVT::v2i32
: Opc
= ARM::VLD2d32
; break;
1360 SDValue Chain
= N
->getOperand(0);
1361 const SDValue Ops
[] = { MemAddr
, MemUpdate
, MemOpc
, Chain
};
1362 return CurDAG
->getTargetNode(Opc
, dl
, VT
, VT
, MVT::Other
, Ops
, 4);
1365 case ARMISD::VLD3D
: {
1366 SDValue MemAddr
, MemUpdate
, MemOpc
;
1367 if (!SelectAddrMode6(Op
, N
->getOperand(1), MemAddr
, MemUpdate
, MemOpc
))
1370 EVT VT
= Op
.getValueType();
1371 switch (VT
.getSimpleVT().SimpleTy
) {
1372 default: llvm_unreachable("unhandled VLD3D type");
1373 case MVT::v8i8
: Opc
= ARM::VLD3d8
; break;
1374 case MVT::v4i16
: Opc
= ARM::VLD3d16
; break;
1376 case MVT::v2i32
: Opc
= ARM::VLD3d32
; break;
1378 SDValue Chain
= N
->getOperand(0);
1379 const SDValue Ops
[] = { MemAddr
, MemUpdate
, MemOpc
, Chain
};
1380 return CurDAG
->getTargetNode(Opc
, dl
, VT
, VT
, VT
, MVT::Other
, Ops
, 4);
1383 case ARMISD::VLD4D
: {
1384 SDValue MemAddr
, MemUpdate
, MemOpc
;
1385 if (!SelectAddrMode6(Op
, N
->getOperand(1), MemAddr
, MemUpdate
, MemOpc
))
1388 EVT VT
= Op
.getValueType();
1389 switch (VT
.getSimpleVT().SimpleTy
) {
1390 default: llvm_unreachable("unhandled VLD4D type");
1391 case MVT::v8i8
: Opc
= ARM::VLD4d8
; break;
1392 case MVT::v4i16
: Opc
= ARM::VLD4d16
; break;
1394 case MVT::v2i32
: Opc
= ARM::VLD4d32
; break;
1396 SDValue Chain
= N
->getOperand(0);
1397 const SDValue Ops
[] = { MemAddr
, MemUpdate
, MemOpc
, Chain
};
1398 std::vector
<EVT
> ResTys(4, VT
);
1399 ResTys
.push_back(MVT::Other
);
1400 return CurDAG
->getTargetNode(Opc
, dl
, ResTys
, Ops
, 4);
1403 case ARMISD::VST2D
: {
1404 SDValue MemAddr
, MemUpdate
, MemOpc
;
1405 if (!SelectAddrMode6(Op
, N
->getOperand(1), MemAddr
, MemUpdate
, MemOpc
))
1408 switch (N
->getOperand(2).getValueType().getSimpleVT().SimpleTy
) {
1409 default: llvm_unreachable("unhandled VST2D type");
1410 case MVT::v8i8
: Opc
= ARM::VST2d8
; break;
1411 case MVT::v4i16
: Opc
= ARM::VST2d16
; break;
1413 case MVT::v2i32
: Opc
= ARM::VST2d32
; break;
1415 SDValue Chain
= N
->getOperand(0);
1416 const SDValue Ops
[] = { MemAddr
, MemUpdate
, MemOpc
,
1417 N
->getOperand(2), N
->getOperand(3), Chain
};
1418 return CurDAG
->getTargetNode(Opc
, dl
, MVT::Other
, Ops
, 6);
1421 case ARMISD::VST3D
: {
1422 SDValue MemAddr
, MemUpdate
, MemOpc
;
1423 if (!SelectAddrMode6(Op
, N
->getOperand(1), MemAddr
, MemUpdate
, MemOpc
))
1426 switch (N
->getOperand(2).getValueType().getSimpleVT().SimpleTy
) {
1427 default: llvm_unreachable("unhandled VST3D type");
1428 case MVT::v8i8
: Opc
= ARM::VST3d8
; break;
1429 case MVT::v4i16
: Opc
= ARM::VST3d16
; break;
1431 case MVT::v2i32
: Opc
= ARM::VST3d32
; break;
1433 SDValue Chain
= N
->getOperand(0);
1434 const SDValue Ops
[] = { MemAddr
, MemUpdate
, MemOpc
,
1435 N
->getOperand(2), N
->getOperand(3),
1436 N
->getOperand(4), Chain
};
1437 return CurDAG
->getTargetNode(Opc
, dl
, MVT::Other
, Ops
, 7);
1440 case ARMISD::VST4D
: {
1441 SDValue MemAddr
, MemUpdate
, MemOpc
;
1442 if (!SelectAddrMode6(Op
, N
->getOperand(1), MemAddr
, MemUpdate
, MemOpc
))
1445 switch (N
->getOperand(2).getValueType().getSimpleVT().SimpleTy
) {
1446 default: llvm_unreachable("unhandled VST4D type");
1447 case MVT::v8i8
: Opc
= ARM::VST4d8
; break;
1448 case MVT::v4i16
: Opc
= ARM::VST4d16
; break;
1450 case MVT::v2i32
: Opc
= ARM::VST4d32
; break;
1452 SDValue Chain
= N
->getOperand(0);
1453 const SDValue Ops
[] = { MemAddr
, MemUpdate
, MemOpc
,
1454 N
->getOperand(2), N
->getOperand(3),
1455 N
->getOperand(4), N
->getOperand(5), Chain
};
1456 return CurDAG
->getTargetNode(Opc
, dl
, MVT::Other
, Ops
, 8);
1459 case ISD::INTRINSIC_WO_CHAIN
: {
1460 unsigned IntNo
= cast
<ConstantSDNode
>(N
->getOperand(0))->getZExtValue();
1461 EVT VT
= N
->getValueType(0);
1464 // Match intrinsics that return multiple values.
1468 case Intrinsic::arm_neon_vtrn
:
1469 switch (VT
.getSimpleVT().SimpleTy
) {
1470 default: return NULL
;
1471 case MVT::v8i8
: Opc
= ARM::VTRNd8
; break;
1472 case MVT::v4i16
: Opc
= ARM::VTRNd16
; break;
1474 case MVT::v2i32
: Opc
= ARM::VTRNd32
; break;
1475 case MVT::v16i8
: Opc
= ARM::VTRNq8
; break;
1476 case MVT::v8i16
: Opc
= ARM::VTRNq16
; break;
1478 case MVT::v4i32
: Opc
= ARM::VTRNq32
; break;
1480 return CurDAG
->getTargetNode(Opc
, dl
, VT
, VT
, N
->getOperand(1),
1483 case Intrinsic::arm_neon_vuzp
:
1484 switch (VT
.getSimpleVT().SimpleTy
) {
1485 default: return NULL
;
1486 case MVT::v8i8
: Opc
= ARM::VUZPd8
; break;
1487 case MVT::v4i16
: Opc
= ARM::VUZPd16
; break;
1489 case MVT::v2i32
: Opc
= ARM::VUZPd32
; break;
1490 case MVT::v16i8
: Opc
= ARM::VUZPq8
; break;
1491 case MVT::v8i16
: Opc
= ARM::VUZPq16
; break;
1493 case MVT::v4i32
: Opc
= ARM::VUZPq32
; break;
1495 return CurDAG
->getTargetNode(Opc
, dl
, VT
, VT
, N
->getOperand(1),
1498 case Intrinsic::arm_neon_vzip
:
1499 switch (VT
.getSimpleVT().SimpleTy
) {
1500 default: return NULL
;
1501 case MVT::v8i8
: Opc
= ARM::VZIPd8
; break;
1502 case MVT::v4i16
: Opc
= ARM::VZIPd16
; break;
1504 case MVT::v2i32
: Opc
= ARM::VZIPd32
; break;
1505 case MVT::v16i8
: Opc
= ARM::VZIPq8
; break;
1506 case MVT::v8i16
: Opc
= ARM::VZIPq16
; break;
1508 case MVT::v4i32
: Opc
= ARM::VZIPq32
; break;
1510 return CurDAG
->getTargetNode(Opc
, dl
, VT
, VT
, N
->getOperand(1),
1517 return SelectCode(Op
);
1520 bool ARMDAGToDAGISel::
1521 SelectInlineAsmMemoryOperand(const SDValue
&Op
, char ConstraintCode
,
1522 std::vector
<SDValue
> &OutOps
) {
1523 assert(ConstraintCode
== 'm' && "unexpected asm memory constraint");
1525 SDValue Base
, Offset
, Opc
;
1526 if (!SelectAddrMode2(Op
, Op
, Base
, Offset
, Opc
))
1529 OutOps
.push_back(Base
);
1530 OutOps
.push_back(Offset
);
1531 OutOps
.push_back(Opc
);
1535 /// createARMISelDag - This pass converts a legalized DAG into a
1536 /// ARM-specific DAG, ready for instruction scheduling.
1538 FunctionPass
*llvm::createARMISelDag(ARMBaseTargetMachine
&TM
) {
1539 return new ARMDAGToDAGISel(TM
);