LLVM 17.0.0git
MipsSEISelDAGToDAG.cpp
Go to the documentation of this file.
1//===-- MipsSEISelDAGToDAG.cpp - A Dag to Dag Inst Selector for MipsSE ----===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// Subclass of MipsDAGToDAGISel specialized for mips32/64.
10//
11//===----------------------------------------------------------------------===//
12
13#include "MipsSEISelDAGToDAG.h"
15#include "Mips.h"
17#include "MipsMachineFunction.h"
18#include "MipsRegisterInfo.h"
25#include "llvm/IR/CFG.h"
26#include "llvm/IR/Dominators.h"
27#include "llvm/IR/GlobalValue.h"
29#include "llvm/IR/Intrinsics.h"
30#include "llvm/IR/IntrinsicsMips.h"
31#include "llvm/IR/Type.h"
32#include "llvm/Support/Debug.h"
36using namespace llvm;
37
38#define DEBUG_TYPE "mips-isel"
39
40bool MipsSEDAGToDAGISel::runOnMachineFunction(MachineFunction &MF) {
43 return false;
45}
46
47void MipsSEDAGToDAGISel::getAnalysisUsage(AnalysisUsage &AU) const {
50}
51
52void MipsSEDAGToDAGISel::addDSPCtrlRegOperands(bool IsDef, MachineInstr &MI,
53 MachineFunction &MF) {
55 unsigned Mask = MI.getOperand(1).getImm();
56 unsigned Flag =
58
59 if (Mask & 1)
60 MIB.addReg(Mips::DSPPos, Flag);
61
62 if (Mask & 2)
63 MIB.addReg(Mips::DSPSCount, Flag);
64
65 if (Mask & 4)
66 MIB.addReg(Mips::DSPCarry, Flag);
67
68 if (Mask & 8)
69 MIB.addReg(Mips::DSPOutFlag, Flag);
70
71 if (Mask & 16)
72 MIB.addReg(Mips::DSPCCond, Flag);
73
74 if (Mask & 32)
75 MIB.addReg(Mips::DSPEFI, Flag);
76}
77
78unsigned MipsSEDAGToDAGISel::getMSACtrlReg(const SDValue RegIdx) const {
79 uint64_t RegNum = cast<ConstantSDNode>(RegIdx)->getZExtValue();
80 return Mips::MSACtrlRegClass.getRegister(RegNum);
81}
82
83bool MipsSEDAGToDAGISel::replaceUsesWithZeroReg(MachineRegisterInfo *MRI,
84 const MachineInstr& MI) {
85 unsigned DstReg = 0, ZeroReg = 0;
86
87 // Check if MI is "addiu $dst, $zero, 0" or "daddiu $dst, $zero, 0".
88 if ((MI.getOpcode() == Mips::ADDiu) &&
89 (MI.getOperand(1).getReg() == Mips::ZERO) &&
90 (MI.getOperand(2).isImm()) &&
91 (MI.getOperand(2).getImm() == 0)) {
92 DstReg = MI.getOperand(0).getReg();
93 ZeroReg = Mips::ZERO;
94 } else if ((MI.getOpcode() == Mips::DADDiu) &&
95 (MI.getOperand(1).getReg() == Mips::ZERO_64) &&
96 (MI.getOperand(2).isImm()) &&
97 (MI.getOperand(2).getImm() == 0)) {
98 DstReg = MI.getOperand(0).getReg();
99 ZeroReg = Mips::ZERO_64;
100 }
101
102 if (!DstReg)
103 return false;
104
105 // Replace uses with ZeroReg.
106 for (MachineRegisterInfo::use_iterator U = MRI->use_begin(DstReg),
107 E = MRI->use_end(); U != E;) {
108 MachineOperand &MO = *U;
109 unsigned OpNo = U.getOperandNo();
110 MachineInstr *MI = MO.getParent();
111 ++U;
112
113 // Do not replace if it is a phi's operand or is tied to def operand.
114 if (MI->isPHI() || MI->isRegTiedToDefOperand(OpNo) || MI->isPseudo())
115 continue;
116
117 // Also, we have to check that the register class of the operand
118 // contains the zero register.
119 if (!MRI->getRegClass(MO.getReg())->contains(ZeroReg))
120 continue;
121
122 MO.setReg(ZeroReg);
123 }
124
125 return true;
126}
127
128void MipsSEDAGToDAGISel::emitMCountABI(MachineInstr &MI, MachineBasicBlock &MBB,
129 MachineFunction &MF) {
131 if (!Subtarget->isABI_O32()) { // N32, N64
132 // Save current return address.
133 BuildMI(MBB, &MI, MI.getDebugLoc(), TII->get(Mips::OR64))
134 .addDef(Mips::AT_64)
135 .addUse(Mips::RA_64, RegState::Undef)
136 .addUse(Mips::ZERO_64);
137 // Stops instruction above from being removed later on.
138 MIB.addUse(Mips::AT_64, RegState::Implicit);
139 } else { // O32
140 // Save current return address.
141 BuildMI(MBB, &MI, MI.getDebugLoc(), TII->get(Mips::OR))
142 .addDef(Mips::AT)
143 .addUse(Mips::RA, RegState::Undef)
144 .addUse(Mips::ZERO);
145 // _mcount pops 2 words from stack.
146 BuildMI(MBB, &MI, MI.getDebugLoc(), TII->get(Mips::ADDiu))
147 .addDef(Mips::SP)
148 .addUse(Mips::SP)
149 .addImm(-8);
150 // Stops first instruction above from being removed later on.
151 MIB.addUse(Mips::AT, RegState::Implicit);
152 }
153}
154
155void MipsSEDAGToDAGISel::processFunctionAfterISel(MachineFunction &MF) {
156 MF.getInfo<MipsFunctionInfo>()->initGlobalBaseReg(MF);
157
159
160 for (auto &MBB: MF) {
161 for (auto &MI: MBB) {
162 switch (MI.getOpcode()) {
163 case Mips::RDDSP:
164 addDSPCtrlRegOperands(false, MI, MF);
165 break;
166 case Mips::WRDSP:
167 addDSPCtrlRegOperands(true, MI, MF);
168 break;
169 case Mips::BuildPairF64_64:
170 case Mips::ExtractElementF64_64:
171 if (!Subtarget->useOddSPReg()) {
172 MI.addOperand(MachineOperand::CreateReg(Mips::SP, false, true));
173 break;
174 }
175 [[fallthrough]];
176 case Mips::BuildPairF64:
177 case Mips::ExtractElementF64:
179 MI.addOperand(MachineOperand::CreateReg(Mips::SP, false, true));
180 break;
181 case Mips::JAL:
182 case Mips::JAL_MM:
183 if (MI.getOperand(0).isGlobal() &&
184 MI.getOperand(0).getGlobal()->getGlobalIdentifier() == "_mcount")
185 emitMCountABI(MI, MBB, MF);
186 break;
187 case Mips::JALRPseudo:
188 case Mips::JALR64Pseudo:
189 case Mips::JALR16_MM:
190 if (MI.getOperand(2).isMCSymbol() &&
191 MI.getOperand(2).getMCSymbol()->getName() == "_mcount")
192 emitMCountABI(MI, MBB, MF);
193 break;
194 case Mips::JALR:
195 if (MI.getOperand(3).isMCSymbol() &&
196 MI.getOperand(3).getMCSymbol()->getName() == "_mcount")
197 emitMCountABI(MI, MBB, MF);
198 break;
199 default:
200 replaceUsesWithZeroReg(MRI, MI);
201 }
202 }
203 }
204}
205
206void MipsSEDAGToDAGISel::selectAddE(SDNode *Node, const SDLoc &DL) const {
207 SDValue InGlue = Node->getOperand(2);
208 unsigned Opc = InGlue.getOpcode();
209 SDValue LHS = Node->getOperand(0), RHS = Node->getOperand(1);
210 EVT VT = LHS.getValueType();
211
212 // In the base case, we can rely on the carry bit from the addsc
213 // instruction.
214 if (Opc == ISD::ADDC) {
215 SDValue Ops[3] = {LHS, RHS, InGlue};
216 CurDAG->SelectNodeTo(Node, Mips::ADDWC, VT, MVT::Glue, Ops);
217 return;
218 }
219
220 assert(Opc == ISD::ADDE && "ISD::ADDE not in a chain of ADDE nodes!");
221
222 // The more complex case is when there is a chain of ISD::ADDE nodes like:
223 // (adde (adde (adde (addc a b) c) d) e).
224 //
225 // The addwc instruction does not write to the carry bit, instead it writes
226 // to bit 20 of the dsp control register. To match this series of nodes, each
227 // intermediate adde node must be expanded to write the carry bit before the
228 // addition.
229
230 // Start by reading the overflow field for addsc and moving the value to the
231 // carry field. The usage of 1 here with MipsISD::RDDSP / Mips::WRDSP
232 // corresponds to reading/writing the entire control register to/from a GPR.
233
234 SDValue CstOne = CurDAG->getTargetConstant(1, DL, MVT::i32);
235
236 SDValue OuFlag = CurDAG->getTargetConstant(20, DL, MVT::i32);
237
238 SDNode *DSPCtrlField = CurDAG->getMachineNode(Mips::RDDSP, DL, MVT::i32,
239 MVT::Glue, CstOne, InGlue);
240
241 SDNode *Carry = CurDAG->getMachineNode(
242 Mips::EXT, DL, MVT::i32, SDValue(DSPCtrlField, 0), OuFlag, CstOne);
243
244 SDValue Ops[4] = {SDValue(DSPCtrlField, 0),
245 CurDAG->getTargetConstant(6, DL, MVT::i32), CstOne,
246 SDValue(Carry, 0)};
247 SDNode *DSPCFWithCarry = CurDAG->getMachineNode(Mips::INS, DL, MVT::i32, Ops);
248
249 // My reading of the MIPS DSP 3.01 specification isn't as clear as I
250 // would like about whether bit 20 always gets overwritten by addwc.
251 // Hence take an extremely conservative view and presume it's sticky. We
252 // therefore need to clear it.
253
254 SDValue Zero = CurDAG->getRegister(Mips::ZERO, MVT::i32);
255
256 SDValue InsOps[4] = {Zero, OuFlag, CstOne, SDValue(DSPCFWithCarry, 0)};
257 SDNode *DSPCtrlFinal =
258 CurDAG->getMachineNode(Mips::INS, DL, MVT::i32, InsOps);
259
260 SDNode *WrDSP = CurDAG->getMachineNode(Mips::WRDSP, DL, MVT::Glue,
261 SDValue(DSPCtrlFinal, 0), CstOne);
262
263 SDValue Operands[3] = {LHS, RHS, SDValue(WrDSP, 0)};
264 CurDAG->SelectNodeTo(Node, Mips::ADDWC, VT, MVT::Glue, Operands);
265}
266
267/// Match frameindex
268bool MipsSEDAGToDAGISel::selectAddrFrameIndex(SDValue Addr, SDValue &Base,
269 SDValue &Offset) const {
270 if (FrameIndexSDNode *FIN = dyn_cast<FrameIndexSDNode>(Addr)) {
271 EVT ValTy = Addr.getValueType();
272
273 Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), ValTy);
275 return true;
276 }
277 return false;
278}
279
280/// Match frameindex+offset and frameindex|offset
281bool MipsSEDAGToDAGISel::selectAddrFrameIndexOffset(
282 SDValue Addr, SDValue &Base, SDValue &Offset, unsigned OffsetBits,
283 unsigned ShiftAmount = 0) const {
285 auto *CN = cast<ConstantSDNode>(Addr.getOperand(1));
286 if (isIntN(OffsetBits + ShiftAmount, CN->getSExtValue())) {
287 EVT ValTy = Addr.getValueType();
288
289 // If the first operand is a FI, get the TargetFI Node
290 if (FrameIndexSDNode *FIN =
291 dyn_cast<FrameIndexSDNode>(Addr.getOperand(0)))
292 Base = CurDAG->getTargetFrameIndex(FIN->getIndex(), ValTy);
293 else {
294 Base = Addr.getOperand(0);
295 // If base is a FI, additional offset calculation is done in
296 // eliminateFrameIndex, otherwise we need to check the alignment
297 const Align Alignment(1ULL << ShiftAmount);
298 if (!isAligned(Alignment, CN->getZExtValue()))
299 return false;
300 }
301
302 Offset = CurDAG->getTargetConstant(CN->getZExtValue(), SDLoc(Addr),
303 ValTy);
304 return true;
305 }
306 }
307 return false;
308}
309
310/// ComplexPattern used on MipsInstrInfo
311/// Used on Mips Load/Store instructions
312bool MipsSEDAGToDAGISel::selectAddrRegImm(SDValue Addr, SDValue &Base,
313 SDValue &Offset) const {
314 // if Address is FI, get the TargetFrameIndex.
315 if (selectAddrFrameIndex(Addr, Base, Offset))
316 return true;
317
318 // on PIC code Load GA
319 if (Addr.getOpcode() == MipsISD::Wrapper) {
320 Base = Addr.getOperand(0);
321 Offset = Addr.getOperand(1);
322 return true;
323 }
324
325 if (!TM.isPositionIndependent()) {
326 if ((Addr.getOpcode() == ISD::TargetExternalSymbol ||
327 Addr.getOpcode() == ISD::TargetGlobalAddress))
328 return false;
329 }
330
331 // Addresses of the form FI+const or FI|const
332 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 16))
333 return true;
334
335 // Operand is a result from an ADD.
336 if (Addr.getOpcode() == ISD::ADD) {
337 // When loading from constant pools, load the lower address part in
338 // the instruction itself. Example, instead of:
339 // lui $2, %hi($CPI1_0)
340 // addiu $2, $2, %lo($CPI1_0)
341 // lwc1 $f0, 0($2)
342 // Generate:
343 // lui $2, %hi($CPI1_0)
344 // lwc1 $f0, %lo($CPI1_0)($2)
345 if (Addr.getOperand(1).getOpcode() == MipsISD::Lo ||
346 Addr.getOperand(1).getOpcode() == MipsISD::GPRel) {
347 SDValue Opnd0 = Addr.getOperand(1).getOperand(0);
348 if (isa<ConstantPoolSDNode>(Opnd0) || isa<GlobalAddressSDNode>(Opnd0) ||
349 isa<JumpTableSDNode>(Opnd0)) {
350 Base = Addr.getOperand(0);
351 Offset = Opnd0;
352 return true;
353 }
354 }
355 }
356
357 return false;
358}
359
360/// ComplexPattern used on MipsInstrInfo
361/// Used on Mips Load/Store instructions
362bool MipsSEDAGToDAGISel::selectAddrDefault(SDValue Addr, SDValue &Base,
363 SDValue &Offset) const {
364 Base = Addr;
365 Offset = CurDAG->getTargetConstant(0, SDLoc(Addr), Addr.getValueType());
366 return true;
367}
368
369bool MipsSEDAGToDAGISel::selectIntAddr(SDValue Addr, SDValue &Base,
370 SDValue &Offset) const {
371 return selectAddrRegImm(Addr, Base, Offset) ||
372 selectAddrDefault(Addr, Base, Offset);
373}
374
375bool MipsSEDAGToDAGISel::selectAddrRegImm9(SDValue Addr, SDValue &Base,
376 SDValue &Offset) const {
377 if (selectAddrFrameIndex(Addr, Base, Offset))
378 return true;
379
380 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 9))
381 return true;
382
383 return false;
384}
385
386/// Used on microMIPS LWC2, LDC2, SWC2 and SDC2 instructions (11-bit offset)
387bool MipsSEDAGToDAGISel::selectAddrRegImm11(SDValue Addr, SDValue &Base,
388 SDValue &Offset) const {
389 if (selectAddrFrameIndex(Addr, Base, Offset))
390 return true;
391
392 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 11))
393 return true;
394
395 return false;
396}
397
398/// Used on microMIPS Load/Store unaligned instructions (12-bit offset)
399bool MipsSEDAGToDAGISel::selectAddrRegImm12(SDValue Addr, SDValue &Base,
400 SDValue &Offset) const {
401 if (selectAddrFrameIndex(Addr, Base, Offset))
402 return true;
403
404 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 12))
405 return true;
406
407 return false;
408}
409
410bool MipsSEDAGToDAGISel::selectAddrRegImm16(SDValue Addr, SDValue &Base,
411 SDValue &Offset) const {
412 if (selectAddrFrameIndex(Addr, Base, Offset))
413 return true;
414
415 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 16))
416 return true;
417
418 return false;
419}
420
421bool MipsSEDAGToDAGISel::selectIntAddr11MM(SDValue Addr, SDValue &Base,
422 SDValue &Offset) const {
423 return selectAddrRegImm11(Addr, Base, Offset) ||
424 selectAddrDefault(Addr, Base, Offset);
425}
426
427bool MipsSEDAGToDAGISel::selectIntAddr12MM(SDValue Addr, SDValue &Base,
428 SDValue &Offset) const {
429 return selectAddrRegImm12(Addr, Base, Offset) ||
430 selectAddrDefault(Addr, Base, Offset);
431}
432
433bool MipsSEDAGToDAGISel::selectIntAddr16MM(SDValue Addr, SDValue &Base,
434 SDValue &Offset) const {
435 return selectAddrRegImm16(Addr, Base, Offset) ||
436 selectAddrDefault(Addr, Base, Offset);
437}
438
439bool MipsSEDAGToDAGISel::selectIntAddrLSL2MM(SDValue Addr, SDValue &Base,
440 SDValue &Offset) const {
441 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 7)) {
442 if (isa<FrameIndexSDNode>(Base))
443 return false;
444
445 if (ConstantSDNode *CN = dyn_cast<ConstantSDNode>(Offset)) {
446 unsigned CnstOff = CN->getZExtValue();
447 return (CnstOff == (CnstOff & 0x3c));
448 }
449
450 return false;
451 }
452
453 // For all other cases where "lw" would be selected, don't select "lw16"
454 // because it would result in additional instructions to prepare operands.
455 if (selectAddrRegImm(Addr, Base, Offset))
456 return false;
457
458 return selectAddrDefault(Addr, Base, Offset);
459}
460
461bool MipsSEDAGToDAGISel::selectIntAddrSImm10(SDValue Addr, SDValue &Base,
462 SDValue &Offset) const {
463
464 if (selectAddrFrameIndex(Addr, Base, Offset))
465 return true;
466
467 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 10))
468 return true;
469
470 return selectAddrDefault(Addr, Base, Offset);
471}
472
473bool MipsSEDAGToDAGISel::selectIntAddrSImm10Lsl1(SDValue Addr, SDValue &Base,
474 SDValue &Offset) const {
475 if (selectAddrFrameIndex(Addr, Base, Offset))
476 return true;
477
478 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 10, 1))
479 return true;
480
481 return selectAddrDefault(Addr, Base, Offset);
482}
483
484bool MipsSEDAGToDAGISel::selectIntAddrSImm10Lsl2(SDValue Addr, SDValue &Base,
485 SDValue &Offset) const {
486 if (selectAddrFrameIndex(Addr, Base, Offset))
487 return true;
488
489 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 10, 2))
490 return true;
491
492 return selectAddrDefault(Addr, Base, Offset);
493}
494
495bool MipsSEDAGToDAGISel::selectIntAddrSImm10Lsl3(SDValue Addr, SDValue &Base,
496 SDValue &Offset) const {
497 if (selectAddrFrameIndex(Addr, Base, Offset))
498 return true;
499
500 if (selectAddrFrameIndexOffset(Addr, Base, Offset, 10, 3))
501 return true;
502
503 return selectAddrDefault(Addr, Base, Offset);
504}
505
506// Select constant vector splats.
507//
508// Returns true and sets Imm if:
509// * MSA is enabled
510// * N is a ISD::BUILD_VECTOR representing a constant splat
511bool MipsSEDAGToDAGISel::selectVSplat(SDNode *N, APInt &Imm,
512 unsigned MinSizeInBits) const {
513 if (!Subtarget->hasMSA())
514 return false;
515
516 BuildVectorSDNode *Node = dyn_cast<BuildVectorSDNode>(N);
517
518 if (!Node)
519 return false;
520
521 APInt SplatValue, SplatUndef;
522 unsigned SplatBitSize;
523 bool HasAnyUndefs;
524
525 if (!Node->isConstantSplat(SplatValue, SplatUndef, SplatBitSize, HasAnyUndefs,
526 MinSizeInBits, !Subtarget->isLittle()))
527 return false;
528
529 Imm = SplatValue;
530
531 return true;
532}
533
534// Select constant vector splats.
535//
536// In addition to the requirements of selectVSplat(), this function returns
537// true and sets Imm if:
538// * The splat value is the same width as the elements of the vector
539// * The splat value fits in an integer with the specified signed-ness and
540// width.
541//
542// This function looks through ISD::BITCAST nodes.
543// TODO: This might not be appropriate for big-endian MSA since BITCAST is
544// sometimes a shuffle in big-endian mode.
545//
546// It's worth noting that this function is not used as part of the selection
547// of ldi.[bhwd] since it does not permit using the wrong-typed ldi.[bhwd]
548// instruction to achieve the desired bit pattern. ldi.[bhwd] is selected in
549// MipsSEDAGToDAGISel::selectNode.
550bool MipsSEDAGToDAGISel::
551selectVSplatCommon(SDValue N, SDValue &Imm, bool Signed,
552 unsigned ImmBitSize) const {
553 APInt ImmValue;
554 EVT EltTy = N->getValueType(0).getVectorElementType();
555
556 if (N->getOpcode() == ISD::BITCAST)
557 N = N->getOperand(0);
558
559 if (selectVSplat(N.getNode(), ImmValue, EltTy.getSizeInBits()) &&
560 ImmValue.getBitWidth() == EltTy.getSizeInBits()) {
561
562 if (( Signed && ImmValue.isSignedIntN(ImmBitSize)) ||
563 (!Signed && ImmValue.isIntN(ImmBitSize))) {
564 Imm = CurDAG->getTargetConstant(ImmValue, SDLoc(N), EltTy);
565 return true;
566 }
567 }
568
569 return false;
570}
571
572// Select constant vector splats.
573bool MipsSEDAGToDAGISel::
574selectVSplatUimm1(SDValue N, SDValue &Imm) const {
575 return selectVSplatCommon(N, Imm, false, 1);
576}
577
578bool MipsSEDAGToDAGISel::
579selectVSplatUimm2(SDValue N, SDValue &Imm) const {
580 return selectVSplatCommon(N, Imm, false, 2);
581}
582
583bool MipsSEDAGToDAGISel::
584selectVSplatUimm3(SDValue N, SDValue &Imm) const {
585 return selectVSplatCommon(N, Imm, false, 3);
586}
587
588// Select constant vector splats.
589bool MipsSEDAGToDAGISel::
590selectVSplatUimm4(SDValue N, SDValue &Imm) const {
591 return selectVSplatCommon(N, Imm, false, 4);
592}
593
594// Select constant vector splats.
595bool MipsSEDAGToDAGISel::
596selectVSplatUimm5(SDValue N, SDValue &Imm) const {
597 return selectVSplatCommon(N, Imm, false, 5);
598}
599
600// Select constant vector splats.
601bool MipsSEDAGToDAGISel::
602selectVSplatUimm6(SDValue N, SDValue &Imm) const {
603 return selectVSplatCommon(N, Imm, false, 6);
604}
605
606// Select constant vector splats.
607bool MipsSEDAGToDAGISel::
608selectVSplatUimm8(SDValue N, SDValue &Imm) const {
609 return selectVSplatCommon(N, Imm, false, 8);
610}
611
612// Select constant vector splats.
613bool MipsSEDAGToDAGISel::
614selectVSplatSimm5(SDValue N, SDValue &Imm) const {
615 return selectVSplatCommon(N, Imm, true, 5);
616}
617
618// Select constant vector splats whose value is a power of 2.
619//
620// In addition to the requirements of selectVSplat(), this function returns
621// true and sets Imm if:
622// * The splat value is the same width as the elements of the vector
623// * The splat value is a power of two.
624//
625// This function looks through ISD::BITCAST nodes.
626// TODO: This might not be appropriate for big-endian MSA since BITCAST is
627// sometimes a shuffle in big-endian mode.
628bool MipsSEDAGToDAGISel::selectVSplatUimmPow2(SDValue N, SDValue &Imm) const {
629 APInt ImmValue;
630 EVT EltTy = N->getValueType(0).getVectorElementType();
631
632 if (N->getOpcode() == ISD::BITCAST)
633 N = N->getOperand(0);
634
635 if (selectVSplat(N.getNode(), ImmValue, EltTy.getSizeInBits()) &&
636 ImmValue.getBitWidth() == EltTy.getSizeInBits()) {
637 int32_t Log2 = ImmValue.exactLogBase2();
638
639 if (Log2 != -1) {
640 Imm = CurDAG->getTargetConstant(Log2, SDLoc(N), EltTy);
641 return true;
642 }
643 }
644
645 return false;
646}
647
648// Select constant vector splats whose value only has a consecutive sequence
649// of left-most bits set (e.g. 0b11...1100...00).
650//
651// In addition to the requirements of selectVSplat(), this function returns
652// true and sets Imm if:
653// * The splat value is the same width as the elements of the vector
654// * The splat value is a consecutive sequence of left-most bits.
655//
656// This function looks through ISD::BITCAST nodes.
657// TODO: This might not be appropriate for big-endian MSA since BITCAST is
658// sometimes a shuffle in big-endian mode.
659bool MipsSEDAGToDAGISel::selectVSplatMaskL(SDValue N, SDValue &Imm) const {
660 APInt ImmValue;
661 EVT EltTy = N->getValueType(0).getVectorElementType();
662
663 if (N->getOpcode() == ISD::BITCAST)
664 N = N->getOperand(0);
665
666 if (selectVSplat(N.getNode(), ImmValue, EltTy.getSizeInBits()) &&
667 ImmValue.getBitWidth() == EltTy.getSizeInBits()) {
668 // Extract the run of set bits starting with bit zero from the bitwise
669 // inverse of ImmValue, and test that the inverse of this is the same
670 // as the original value.
671 if (ImmValue == ~(~ImmValue & ~(~ImmValue + 1))) {
672
673 Imm = CurDAG->getTargetConstant(ImmValue.popcount() - 1, SDLoc(N), EltTy);
674 return true;
675 }
676 }
677
678 return false;
679}
680
681// Select constant vector splats whose value only has a consecutive sequence
682// of right-most bits set (e.g. 0b00...0011...11).
683//
684// In addition to the requirements of selectVSplat(), this function returns
685// true and sets Imm if:
686// * The splat value is the same width as the elements of the vector
687// * The splat value is a consecutive sequence of right-most bits.
688//
689// This function looks through ISD::BITCAST nodes.
690// TODO: This might not be appropriate for big-endian MSA since BITCAST is
691// sometimes a shuffle in big-endian mode.
692bool MipsSEDAGToDAGISel::selectVSplatMaskR(SDValue N, SDValue &Imm) const {
693 APInt ImmValue;
694 EVT EltTy = N->getValueType(0).getVectorElementType();
695
696 if (N->getOpcode() == ISD::BITCAST)
697 N = N->getOperand(0);
698
699 if (selectVSplat(N.getNode(), ImmValue, EltTy.getSizeInBits()) &&
700 ImmValue.getBitWidth() == EltTy.getSizeInBits()) {
701 // Extract the run of set bits starting with bit zero, and test that the
702 // result is the same as the original value
703 if (ImmValue == (ImmValue & ~(ImmValue + 1))) {
704 Imm = CurDAG->getTargetConstant(ImmValue.popcount() - 1, SDLoc(N), EltTy);
705 return true;
706 }
707 }
708
709 return false;
710}
711
712bool MipsSEDAGToDAGISel::selectVSplatUimmInvPow2(SDValue N,
713 SDValue &Imm) const {
714 APInt ImmValue;
715 EVT EltTy = N->getValueType(0).getVectorElementType();
716
717 if (N->getOpcode() == ISD::BITCAST)
718 N = N->getOperand(0);
719
720 if (selectVSplat(N.getNode(), ImmValue, EltTy.getSizeInBits()) &&
721 ImmValue.getBitWidth() == EltTy.getSizeInBits()) {
722 int32_t Log2 = (~ImmValue).exactLogBase2();
723
724 if (Log2 != -1) {
725 Imm = CurDAG->getTargetConstant(Log2, SDLoc(N), EltTy);
726 return true;
727 }
728 }
729
730 return false;
731}
732
733bool MipsSEDAGToDAGISel::trySelect(SDNode *Node) {
734 unsigned Opcode = Node->getOpcode();
735 SDLoc DL(Node);
736
737 ///
738 // Instruction Selection not handled by the auto-generated
739 // tablegen selection should be handled here.
740 ///
741 switch(Opcode) {
742 default: break;
743
744 case Mips::PseudoD_SELECT_I:
745 case Mips::PseudoD_SELECT_I64: {
746 MVT VT = Subtarget->isGP64bit() ? MVT::i64 : MVT::i32;
747 SDValue cond = Node->getOperand(0);
748 SDValue Hi1 = Node->getOperand(1);
749 SDValue Lo1 = Node->getOperand(2);
750 SDValue Hi2 = Node->getOperand(3);
751 SDValue Lo2 = Node->getOperand(4);
752
753 SDValue ops[] = {cond, Hi1, Lo1, Hi2, Lo2};
754 EVT NodeTys[] = {VT, VT};
756 ? Mips::PseudoD_SELECT_I64
757 : Mips::PseudoD_SELECT_I,
758 DL, NodeTys, ops));
759 return true;
760 }
761
762 case ISD::ADDE: {
763 selectAddE(Node, DL);
764 return true;
765 }
766
767 case ISD::ConstantFP: {
768 auto *CN = cast<ConstantFPSDNode>(Node);
769 if (Node->getValueType(0) == MVT::f64 && CN->isExactlyValue(+0.0)) {
770 if (Subtarget->isGP64bit()) {
772 Mips::ZERO_64, MVT::i64);
774 CurDAG->getMachineNode(Mips::DMTC1, DL, MVT::f64, Zero));
775 } else if (Subtarget->isFP64bit()) {
777 Mips::ZERO, MVT::i32);
778 ReplaceNode(Node, CurDAG->getMachineNode(Mips::BuildPairF64_64, DL,
779 MVT::f64, Zero, Zero));
780 } else {
782 Mips::ZERO, MVT::i32);
783 ReplaceNode(Node, CurDAG->getMachineNode(Mips::BuildPairF64, DL,
784 MVT::f64, Zero, Zero));
785 }
786 return true;
787 }
788 break;
789 }
790
791 case ISD::Constant: {
792 auto *CN = cast<ConstantSDNode>(Node);
793 int64_t Imm = CN->getSExtValue();
794 unsigned Size = CN->getValueSizeInBits(0);
795
796 if (isInt<32>(Imm))
797 break;
798
799 MipsAnalyzeImmediate AnalyzeImm;
800
802 AnalyzeImm.Analyze(Imm, Size, false);
803
805 SDLoc DL(CN);
806 SDNode *RegOpnd;
807 SDValue ImmOpnd = CurDAG->getTargetConstant(SignExtend64<16>(Inst->ImmOpnd),
808 DL, MVT::i64);
809
810 // The first instruction can be a LUi which is different from other
811 // instructions (ADDiu, ORI and SLL) in that it does not have a register
812 // operand.
813 if (Inst->Opc == Mips::LUi64)
814 RegOpnd = CurDAG->getMachineNode(Inst->Opc, DL, MVT::i64, ImmOpnd);
815 else
816 RegOpnd =
817 CurDAG->getMachineNode(Inst->Opc, DL, MVT::i64,
818 CurDAG->getRegister(Mips::ZERO_64, MVT::i64),
819 ImmOpnd);
820
821 // The remaining instructions in the sequence are handled here.
822 for (++Inst; Inst != Seq.end(); ++Inst) {
823 ImmOpnd = CurDAG->getTargetConstant(SignExtend64<16>(Inst->ImmOpnd), DL,
824 MVT::i64);
825 RegOpnd = CurDAG->getMachineNode(Inst->Opc, DL, MVT::i64,
826 SDValue(RegOpnd, 0), ImmOpnd);
827 }
828
829 ReplaceNode(Node, RegOpnd);
830 return true;
831 }
832
834 const unsigned IntrinsicOpcode =
835 cast<ConstantSDNode>(Node->getOperand(1))->getZExtValue();
836 switch (IntrinsicOpcode) {
837 default:
838 break;
839
840 case Intrinsic::mips_cfcmsa: {
841 SDValue ChainIn = Node->getOperand(0);
842 SDValue RegIdx = Node->getOperand(2);
843 SDValue Reg = CurDAG->getCopyFromReg(ChainIn, DL,
844 getMSACtrlReg(RegIdx), MVT::i32);
845 ReplaceNode(Node, Reg.getNode());
846 return true;
847 }
848 case Intrinsic::mips_ldr_d:
849 case Intrinsic::mips_ldr_w: {
850 unsigned Op = (IntrinsicOpcode == Intrinsic::mips_ldr_d) ? Mips::LDR_D
851 : Mips::LDR_W;
852
853 SDLoc DL(Node);
854 assert(Node->getNumOperands() == 4 && "Unexpected number of operands.");
855 const SDValue &Chain = Node->getOperand(0);
856 const SDValue &Intrinsic = Node->getOperand(1);
857 const SDValue &Pointer = Node->getOperand(2);
858 const SDValue &Constant = Node->getOperand(3);
859
860 assert(Chain.getValueType() == MVT::Other);
861 (void)Intrinsic;
862 assert(Intrinsic.getOpcode() == ISD::TargetConstant &&
863 Constant.getOpcode() == ISD::Constant &&
864 "Invalid instruction operand.");
865
866 // Convert Constant to TargetConstant.
867 const ConstantInt *Val =
868 cast<ConstantSDNode>(Constant)->getConstantIntValue();
869 SDValue Imm =
870 CurDAG->getTargetConstant(*Val, DL, Constant.getValueType());
871
873
874 assert(Node->getNumValues() == 2);
875 assert(Node->getValueType(0).is128BitVector());
876 assert(Node->getValueType(1) == MVT::Other);
877 SmallVector<EVT, 2> ResTys{Node->getValueType(0), Node->getValueType(1)};
878
879 ReplaceNode(Node, CurDAG->getMachineNode(Op, DL, ResTys, Ops));
880
881 return true;
882 }
883 }
884 break;
885 }
886
888 switch (cast<ConstantSDNode>(Node->getOperand(0))->getZExtValue()) {
889 default:
890 break;
891
892 case Intrinsic::mips_move_v:
893 // Like an assignment but will always produce a move.v even if
894 // unnecessary.
895 ReplaceNode(Node, CurDAG->getMachineNode(Mips::MOVE_V, DL,
896 Node->getValueType(0),
897 Node->getOperand(1)));
898 return true;
899 }
900 break;
901 }
902
903 case ISD::INTRINSIC_VOID: {
904 const unsigned IntrinsicOpcode =
905 cast<ConstantSDNode>(Node->getOperand(1))->getZExtValue();
906 switch (IntrinsicOpcode) {
907 default:
908 break;
909
910 case Intrinsic::mips_ctcmsa: {
911 SDValue ChainIn = Node->getOperand(0);
912 SDValue RegIdx = Node->getOperand(2);
913 SDValue Value = Node->getOperand(3);
914 SDValue ChainOut = CurDAG->getCopyToReg(ChainIn, DL,
915 getMSACtrlReg(RegIdx), Value);
916 ReplaceNode(Node, ChainOut.getNode());
917 return true;
918 }
919 case Intrinsic::mips_str_d:
920 case Intrinsic::mips_str_w: {
921 unsigned Op = (IntrinsicOpcode == Intrinsic::mips_str_d) ? Mips::STR_D
922 : Mips::STR_W;
923
924 SDLoc DL(Node);
925 assert(Node->getNumOperands() == 5 && "Unexpected number of operands.");
926 const SDValue &Chain = Node->getOperand(0);
927 const SDValue &Intrinsic = Node->getOperand(1);
928 const SDValue &Vec = Node->getOperand(2);
929 const SDValue &Pointer = Node->getOperand(3);
930 const SDValue &Constant = Node->getOperand(4);
931
932 assert(Chain.getValueType() == MVT::Other);
933 (void)Intrinsic;
934 assert(Intrinsic.getOpcode() == ISD::TargetConstant &&
935 Constant.getOpcode() == ISD::Constant &&
936 "Invalid instruction operand.");
937
938 // Convert Constant to TargetConstant.
939 const ConstantInt *Val =
940 cast<ConstantSDNode>(Constant)->getConstantIntValue();
941 SDValue Imm =
942 CurDAG->getTargetConstant(*Val, DL, Constant.getValueType());
943
944 SmallVector<SDValue, 4> Ops{Vec, Pointer, Imm, Chain};
945
946 assert(Node->getNumValues() == 1);
947 assert(Node->getValueType(0) == MVT::Other);
948 SmallVector<EVT, 1> ResTys{Node->getValueType(0)};
949
950 ReplaceNode(Node, CurDAG->getMachineNode(Op, DL, ResTys, Ops));
951 return true;
952 }
953 }
954 break;
955 }
956
957 case MipsISD::FAbs: {
958 MVT ResTy = Node->getSimpleValueType(0);
959 assert((ResTy == MVT::f64 || ResTy == MVT::f32) &&
960 "Unsupported float type!");
961 unsigned Opc = 0;
962 if (ResTy == MVT::f64)
963 Opc = (Subtarget->isFP64bit() ? Mips::FABS_D64 : Mips::FABS_D32);
964 else
965 Opc = Mips::FABS_S;
966
967 if (Subtarget->inMicroMipsMode()) {
968 switch (Opc) {
969 case Mips::FABS_D64:
970 Opc = Mips::FABS_D64_MM;
971 break;
972 case Mips::FABS_D32:
973 Opc = Mips::FABS_D32_MM;
974 break;
975 case Mips::FABS_S:
976 Opc = Mips::FABS_S_MM;
977 break;
978 default:
979 llvm_unreachable("Unknown opcode for MIPS floating point abs!");
980 }
981 }
982
984 CurDAG->getMachineNode(Opc, DL, ResTy, Node->getOperand(0)));
985
986 return true;
987 }
988
989 // Manually match MipsISD::Ins nodes to get the correct instruction. It has
990 // to be done in this fashion so that we respect the differences between
991 // dins and dinsm, as the difference is that the size operand has the range
992 // 0 < size <= 32 for dins while dinsm has the range 2 <= size <= 64 which
993 // means SelectionDAGISel would have to test all the operands at once to
994 // match the instruction.
995 case MipsISD::Ins: {
996
997 // Validating the node operands.
998 if (Node->getValueType(0) != MVT::i32 && Node->getValueType(0) != MVT::i64)
999 return false;
1000
1001 if (Node->getNumOperands() != 4)
1002 return false;
1003
1004 if (Node->getOperand(1)->getOpcode() != ISD::Constant ||
1005 Node->getOperand(2)->getOpcode() != ISD::Constant)
1006 return false;
1007
1008 MVT ResTy = Node->getSimpleValueType(0);
1009 uint64_t Pos = Node->getConstantOperandVal(1);
1010 uint64_t Size = Node->getConstantOperandVal(2);
1011
1012 // Size has to be >0 for 'ins', 'dins' and 'dinsu'.
1013 if (!Size)
1014 return false;
1015
1016 if (Pos + Size > 64)
1017 return false;
1018
1019 if (ResTy != MVT::i32 && ResTy != MVT::i64)
1020 return false;
1021
1022 unsigned Opcode = 0;
1023 if (ResTy == MVT::i32) {
1024 if (Pos + Size <= 32)
1025 Opcode = Mips::INS;
1026 } else {
1027 if (Pos + Size <= 32)
1028 Opcode = Mips::DINS;
1029 else if (Pos < 32 && 1 < Size)
1030 Opcode = Mips::DINSM;
1031 else
1032 Opcode = Mips::DINSU;
1033 }
1034
1035 if (Opcode) {
1036 SDValue Ops[4] = {
1037 Node->getOperand(0), CurDAG->getTargetConstant(Pos, DL, MVT::i32),
1038 CurDAG->getTargetConstant(Size, DL, MVT::i32), Node->getOperand(3)};
1039
1040 ReplaceNode(Node, CurDAG->getMachineNode(Opcode, DL, ResTy, Ops));
1041 return true;
1042 }
1043
1044 return false;
1045 }
1046
1049 unsigned RdhwrOpc, DestReg;
1050
1051 if (PtrVT == MVT::i32) {
1052 RdhwrOpc = Mips::RDHWR;
1053 DestReg = Mips::V1;
1054 } else {
1055 RdhwrOpc = Mips::RDHWR64;
1056 DestReg = Mips::V1_64;
1057 }
1058
1059 SDNode *Rdhwr =
1060 CurDAG->getMachineNode(RdhwrOpc, DL, Node->getValueType(0), MVT::Glue,
1061 CurDAG->getRegister(Mips::HWR29, MVT::i32),
1062 CurDAG->getTargetConstant(0, DL, MVT::i32));
1063 SDValue Chain = CurDAG->getCopyToReg(CurDAG->getEntryNode(), DL, DestReg,
1064 SDValue(Rdhwr, 0), SDValue(Rdhwr, 1));
1065 SDValue ResNode = CurDAG->getCopyFromReg(Chain, DL, DestReg, PtrVT,
1066 Chain.getValue(1));
1067 ReplaceNode(Node, ResNode.getNode());
1068 return true;
1069 }
1070
1071 case ISD::BUILD_VECTOR: {
1072 // Select appropriate ldi.[bhwd] instructions for constant splats of
1073 // 128-bit when MSA is enabled. Fixup any register class mismatches that
1074 // occur as a result.
1075 //
1076 // This allows the compiler to use a wider range of immediates than would
1077 // otherwise be allowed. If, for example, v4i32 could only use ldi.h then
1078 // it would not be possible to load { 0x01010101, 0x01010101, 0x01010101,
1079 // 0x01010101 } without using a constant pool. This would be sub-optimal
1080 // when // 'ldi.b wd, 1' is capable of producing that bit-pattern in the
1081 // same set/ of registers. Similarly, ldi.h isn't capable of producing {
1082 // 0x00000000, 0x00000001, 0x00000000, 0x00000001 } but 'ldi.d wd, 1' can.
1083
1084 const MipsABIInfo &ABI =
1085 static_cast<const MipsTargetMachine &>(TM).getABI();
1086
1087 BuildVectorSDNode *BVN = cast<BuildVectorSDNode>(Node);
1088 APInt SplatValue, SplatUndef;
1089 unsigned SplatBitSize;
1090 bool HasAnyUndefs;
1091 unsigned LdiOp;
1092 EVT ResVecTy = BVN->getValueType(0);
1093 EVT ViaVecTy;
1094
1095 if (!Subtarget->hasMSA() || !BVN->getValueType(0).is128BitVector())
1096 return false;
1097
1098 if (!BVN->isConstantSplat(SplatValue, SplatUndef, SplatBitSize,
1099 HasAnyUndefs, 8,
1100 !Subtarget->isLittle()))
1101 return false;
1102
1103 switch (SplatBitSize) {
1104 default:
1105 return false;
1106 case 8:
1107 LdiOp = Mips::LDI_B;
1108 ViaVecTy = MVT::v16i8;
1109 break;
1110 case 16:
1111 LdiOp = Mips::LDI_H;
1112 ViaVecTy = MVT::v8i16;
1113 break;
1114 case 32:
1115 LdiOp = Mips::LDI_W;
1116 ViaVecTy = MVT::v4i32;
1117 break;
1118 case 64:
1119 LdiOp = Mips::LDI_D;
1120 ViaVecTy = MVT::v2i64;
1121 break;
1122 }
1123
1124 SDNode *Res = nullptr;
1125
1126 // If we have a signed 10 bit integer, we can splat it directly.
1127 //
1128 // If we have something bigger we can synthesize the value into a GPR and
1129 // splat from there.
1130 if (SplatValue.isSignedIntN(10)) {
1131 SDValue Imm = CurDAG->getTargetConstant(SplatValue, DL,
1132 ViaVecTy.getVectorElementType());
1133
1134 Res = CurDAG->getMachineNode(LdiOp, DL, ViaVecTy, Imm);
1135 } else if (SplatValue.isSignedIntN(16) &&
1136 ((ABI.IsO32() && SplatBitSize < 64) ||
1137 (ABI.IsN32() || ABI.IsN64()))) {
1138 // Only handle signed 16 bit values when the element size is GPR width.
1139 // MIPS64 can handle all the cases but MIPS32 would need to handle
1140 // negative cases specifically here. Instead, handle those cases as
1141 // 64bit values.
1142
1143 bool Is32BitSplat = ABI.IsO32() || SplatBitSize < 64;
1144 const unsigned ADDiuOp = Is32BitSplat ? Mips::ADDiu : Mips::DADDiu;
1145 const MVT SplatMVT = Is32BitSplat ? MVT::i32 : MVT::i64;
1146 SDValue ZeroVal = CurDAG->getRegister(
1147 Is32BitSplat ? Mips::ZERO : Mips::ZERO_64, SplatMVT);
1148
1149 const unsigned FILLOp =
1150 SplatBitSize == 16
1151 ? Mips::FILL_H
1152 : (SplatBitSize == 32 ? Mips::FILL_W
1153 : (SplatBitSize == 64 ? Mips::FILL_D : 0));
1154
1155 assert(FILLOp != 0 && "Unknown FILL Op for splat synthesis!");
1156 assert((!ABI.IsO32() || (FILLOp != Mips::FILL_D)) &&
1157 "Attempting to use fill.d on MIPS32!");
1158
1159 const unsigned Lo = SplatValue.getLoBits(16).getZExtValue();
1160 SDValue LoVal = CurDAG->getTargetConstant(Lo, DL, SplatMVT);
1161
1162 Res = CurDAG->getMachineNode(ADDiuOp, DL, SplatMVT, ZeroVal, LoVal);
1163 Res = CurDAG->getMachineNode(FILLOp, DL, ViaVecTy, SDValue(Res, 0));
1164
1165 } else if (SplatValue.isSignedIntN(32) && SplatBitSize == 32) {
1166 // Only handle the cases where the splat size agrees with the size
1167 // of the SplatValue here.
1168 const unsigned Lo = SplatValue.getLoBits(16).getZExtValue();
1169 const unsigned Hi = SplatValue.lshr(16).getLoBits(16).getZExtValue();
1170 SDValue ZeroVal = CurDAG->getRegister(Mips::ZERO, MVT::i32);
1171
1172 SDValue LoVal = CurDAG->getTargetConstant(Lo, DL, MVT::i32);
1173 SDValue HiVal = CurDAG->getTargetConstant(Hi, DL, MVT::i32);
1174
1175 if (Hi)
1176 Res = CurDAG->getMachineNode(Mips::LUi, DL, MVT::i32, HiVal);
1177
1178 if (Lo)
1179 Res = CurDAG->getMachineNode(Mips::ORi, DL, MVT::i32,
1180 Hi ? SDValue(Res, 0) : ZeroVal, LoVal);
1181
1182 assert((Hi || Lo) && "Zero case reached 32 bit case splat synthesis!");
1183 Res =
1184 CurDAG->getMachineNode(Mips::FILL_W, DL, MVT::v4i32, SDValue(Res, 0));
1185
1186 } else if (SplatValue.isSignedIntN(32) && SplatBitSize == 64 &&
1187 (ABI.IsN32() || ABI.IsN64())) {
1188 // N32 and N64 can perform some tricks that O32 can't for signed 32 bit
1189 // integers due to having 64bit registers. lui will cause the necessary
1190 // zero/sign extension.
1191 const unsigned Lo = SplatValue.getLoBits(16).getZExtValue();
1192 const unsigned Hi = SplatValue.lshr(16).getLoBits(16).getZExtValue();
1193 SDValue ZeroVal = CurDAG->getRegister(Mips::ZERO, MVT::i32);
1194
1195 SDValue LoVal = CurDAG->getTargetConstant(Lo, DL, MVT::i32);
1196 SDValue HiVal = CurDAG->getTargetConstant(Hi, DL, MVT::i32);
1197
1198 if (Hi)
1199 Res = CurDAG->getMachineNode(Mips::LUi, DL, MVT::i32, HiVal);
1200
1201 if (Lo)
1202 Res = CurDAG->getMachineNode(Mips::ORi, DL, MVT::i32,
1203 Hi ? SDValue(Res, 0) : ZeroVal, LoVal);
1204
1205 Res = CurDAG->getMachineNode(
1206 Mips::SUBREG_TO_REG, DL, MVT::i64,
1207 CurDAG->getTargetConstant(((Hi >> 15) & 0x1), DL, MVT::i64),
1208 SDValue(Res, 0),
1209 CurDAG->getTargetConstant(Mips::sub_32, DL, MVT::i64));
1210
1211 Res =
1212 CurDAG->getMachineNode(Mips::FILL_D, DL, MVT::v2i64, SDValue(Res, 0));
1213
1214 } else if (SplatValue.isSignedIntN(64)) {
1215 // If we have a 64 bit Splat value, we perform a similar sequence to the
1216 // above:
1217 //
1218 // MIPS32: MIPS64:
1219 // lui $res, %highest(val) lui $res, %highest(val)
1220 // ori $res, $res, %higher(val) ori $res, $res, %higher(val)
1221 // lui $res2, %hi(val) lui $res2, %hi(val)
1222 // ori $res2, %res2, %lo(val) ori $res2, %res2, %lo(val)
1223 // $res3 = fill $res2 dinsu $res, $res2, 0, 32
1224 // $res4 = insert.w $res3[1], $res fill.d $res
1225 // splat.d $res4, 0
1226 //
1227 // The ability to use dinsu is guaranteed as MSA requires MIPSR5.
1228 // This saves having to materialize the value by shifts and ors.
1229 //
1230 // FIXME: Implement the preferred sequence for MIPS64R6:
1231 //
1232 // MIPS64R6:
1233 // ori $res, $zero, %lo(val)
1234 // daui $res, $res, %hi(val)
1235 // dahi $res, $res, %higher(val)
1236 // dati $res, $res, %highest(cal)
1237 // fill.d $res
1238 //
1239
1240 const unsigned Lo = SplatValue.getLoBits(16).getZExtValue();
1241 const unsigned Hi = SplatValue.lshr(16).getLoBits(16).getZExtValue();
1242 const unsigned Higher = SplatValue.lshr(32).getLoBits(16).getZExtValue();
1243 const unsigned Highest = SplatValue.lshr(48).getLoBits(16).getZExtValue();
1244
1245 SDValue LoVal = CurDAG->getTargetConstant(Lo, DL, MVT::i32);
1246 SDValue HiVal = CurDAG->getTargetConstant(Hi, DL, MVT::i32);
1247 SDValue HigherVal = CurDAG->getTargetConstant(Higher, DL, MVT::i32);
1248 SDValue HighestVal = CurDAG->getTargetConstant(Highest, DL, MVT::i32);
1249 SDValue ZeroVal = CurDAG->getRegister(Mips::ZERO, MVT::i32);
1250
1251 // Independent of whether we're targeting MIPS64 or not, the basic
1252 // operations are the same. Also, directly use the $zero register if
1253 // the 16 bit chunk is zero.
1254 //
1255 // For optimization purposes we always synthesize the splat value as
1256 // an i32 value, then if we're targetting MIPS64, use SUBREG_TO_REG
1257 // just before combining the values with dinsu to produce an i64. This
1258 // enables SelectionDAG to aggressively share components of splat values
1259 // where possible.
1260 //
1261 // FIXME: This is the general constant synthesis problem. This code
1262 // should be factored out into a class shared between all the
1263 // classes that need it. Specifically, for a splat size of 64
1264 // bits that's a negative number we can do better than LUi/ORi
1265 // for the upper 32bits.
1266
1267 if (Hi)
1268 Res = CurDAG->getMachineNode(Mips::LUi, DL, MVT::i32, HiVal);
1269
1270 if (Lo)
1271 Res = CurDAG->getMachineNode(Mips::ORi, DL, MVT::i32,
1272 Hi ? SDValue(Res, 0) : ZeroVal, LoVal);
1273
1274 SDNode *HiRes;
1275 if (Highest)
1276 HiRes = CurDAG->getMachineNode(Mips::LUi, DL, MVT::i32, HighestVal);
1277
1278 if (Higher)
1279 HiRes = CurDAG->getMachineNode(Mips::ORi, DL, MVT::i32,
1280 Highest ? SDValue(HiRes, 0) : ZeroVal,
1281 HigherVal);
1282
1283
1284 if (ABI.IsO32()) {
1285 Res = CurDAG->getMachineNode(Mips::FILL_W, DL, MVT::v4i32,
1286 (Hi || Lo) ? SDValue(Res, 0) : ZeroVal);
1287
1288 Res = CurDAG->getMachineNode(
1289 Mips::INSERT_W, DL, MVT::v4i32, SDValue(Res, 0),
1290 (Highest || Higher) ? SDValue(HiRes, 0) : ZeroVal,
1291 CurDAG->getTargetConstant(1, DL, MVT::i32));
1292
1294 const TargetRegisterClass *RC =
1295 TLI->getRegClassFor(ViaVecTy.getSimpleVT());
1296
1297 Res = CurDAG->getMachineNode(
1298 Mips::COPY_TO_REGCLASS, DL, ViaVecTy, SDValue(Res, 0),
1299 CurDAG->getTargetConstant(RC->getID(), DL, MVT::i32));
1300
1301 Res = CurDAG->getMachineNode(
1302 Mips::SPLATI_D, DL, MVT::v2i64, SDValue(Res, 0),
1303 CurDAG->getTargetConstant(0, DL, MVT::i32));
1304 } else if (ABI.IsN64() || ABI.IsN32()) {
1305
1306 SDValue Zero64Val = CurDAG->getRegister(Mips::ZERO_64, MVT::i64);
1307 const bool HiResNonZero = Highest || Higher;
1308 const bool ResNonZero = Hi || Lo;
1309
1310 if (HiResNonZero)
1311 HiRes = CurDAG->getMachineNode(
1312 Mips::SUBREG_TO_REG, DL, MVT::i64,
1313 CurDAG->getTargetConstant(((Highest >> 15) & 0x1), DL, MVT::i64),
1314 SDValue(HiRes, 0),
1315 CurDAG->getTargetConstant(Mips::sub_32, DL, MVT::i64));
1316
1317 if (ResNonZero)
1318 Res = CurDAG->getMachineNode(
1319 Mips::SUBREG_TO_REG, DL, MVT::i64,
1320 CurDAG->getTargetConstant(((Hi >> 15) & 0x1), DL, MVT::i64),
1321 SDValue(Res, 0),
1322 CurDAG->getTargetConstant(Mips::sub_32, DL, MVT::i64));
1323
1324 // We have 3 cases:
1325 // The HiRes is nonzero but Res is $zero => dsll32 HiRes, 0
1326 // The Res is nonzero but HiRes is $zero => dinsu Res, $zero, 32, 32
1327 // Both are non zero => dinsu Res, HiRes, 32, 32
1328 //
1329 // The obvious "missing" case is when both are zero, but that case is
1330 // handled by the ldi case.
1331 if (ResNonZero) {
1334 const ConstantInt *Const32 = ConstantInt::get(Int32Ty, 32);
1335 SDValue Ops[4] = {HiResNonZero ? SDValue(HiRes, 0) : Zero64Val,
1336 CurDAG->getConstant(*Const32, DL, MVT::i32),
1337 CurDAG->getConstant(*Const32, DL, MVT::i32),
1338 SDValue(Res, 0)};
1339
1340 Res = CurDAG->getMachineNode(Mips::DINSU, DL, MVT::i64, Ops);
1341 } else if (HiResNonZero) {
1342 Res = CurDAG->getMachineNode(
1343 Mips::DSLL32, DL, MVT::i64, SDValue(HiRes, 0),
1344 CurDAG->getTargetConstant(0, DL, MVT::i32));
1345 } else
1347 "Zero splat value handled by non-zero 64bit splat synthesis!");
1348
1349 Res = CurDAG->getMachineNode(Mips::FILL_D, DL, MVT::v2i64,
1350 SDValue(Res, 0));
1351 } else
1352 llvm_unreachable("Unknown ABI in MipsISelDAGToDAG!");
1353
1354 } else
1355 return false;
1356
1357 if (ResVecTy != ViaVecTy) {
1358 // If LdiOp is writing to a different register class to ResVecTy, then
1359 // fix it up here. This COPY_TO_REGCLASS should never cause a move.v
1360 // since the source and destination register sets contain the same
1361 // registers.
1363 MVT ResVecTySimple = ResVecTy.getSimpleVT();
1364 const TargetRegisterClass *RC = TLI->getRegClassFor(ResVecTySimple);
1365 Res = CurDAG->getMachineNode(Mips::COPY_TO_REGCLASS, DL,
1366 ResVecTy, SDValue(Res, 0),
1368 MVT::i32));
1369 }
1370
1371 ReplaceNode(Node, Res);
1372 return true;
1373 }
1374
1375 }
1376
1377 return false;
1378}
1379
1380bool MipsSEDAGToDAGISel::
1381SelectInlineAsmMemoryOperand(const SDValue &Op, unsigned ConstraintID,
1382 std::vector<SDValue> &OutOps) {
1384
1385 switch(ConstraintID) {
1386 default:
1387 llvm_unreachable("Unexpected asm memory constraint");
1388 // All memory constraints can at least accept raw pointers.
1391 if (selectAddrRegImm16(Op, Base, Offset)) {
1392 OutOps.push_back(Base);
1393 OutOps.push_back(Offset);
1394 return false;
1395 }
1396 OutOps.push_back(Op);
1397 OutOps.push_back(CurDAG->getTargetConstant(0, SDLoc(Op), MVT::i32));
1398 return false;
1400 // The 'R' constraint is supposed to be much more complicated than this.
1401 // However, it's becoming less useful due to architectural changes and
1402 // ought to be replaced by other constraints such as 'ZC'.
1403 // For now, support 9-bit signed offsets which is supportable by all
1404 // subtargets for all instructions.
1405 if (selectAddrRegImm9(Op, Base, Offset)) {
1406 OutOps.push_back(Base);
1407 OutOps.push_back(Offset);
1408 return false;
1409 }
1410 OutOps.push_back(Op);
1411 OutOps.push_back(CurDAG->getTargetConstant(0, SDLoc(Op), MVT::i32));
1412 return false;
1414 // ZC matches whatever the pref, ll, and sc instructions can handle for the
1415 // given subtarget.
1416 if (Subtarget->inMicroMipsMode()) {
1417 // On microMIPS, they can handle 12-bit offsets.
1418 if (selectAddrRegImm12(Op, Base, Offset)) {
1419 OutOps.push_back(Base);
1420 OutOps.push_back(Offset);
1421 return false;
1422 }
1423 } else if (Subtarget->hasMips32r6()) {
1424 // On MIPS32r6/MIPS64r6, they can only handle 9-bit offsets.
1425 if (selectAddrRegImm9(Op, Base, Offset)) {
1426 OutOps.push_back(Base);
1427 OutOps.push_back(Offset);
1428 return false;
1429 }
1430 } else if (selectAddrRegImm16(Op, Base, Offset)) {
1431 // Prior to MIPS32r6/MIPS64r6, they can handle 16-bit offsets.
1432 OutOps.push_back(Base);
1433 OutOps.push_back(Offset);
1434 return false;
1435 }
1436 // In all cases, 0-bit offsets are acceptable.
1437 OutOps.push_back(Op);
1438 OutOps.push_back(CurDAG->getTargetConstant(0, SDLoc(Op), MVT::i32));
1439 return false;
1440 }
1441 return true;
1442}
1443
1446 return new MipsSEDAGToDAGISel(TM, OptLevel);
1447}
unsigned const MachineRegisterInfo * MRI
MachineBasicBlock & MBB
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
uint64_t Addr
uint64_t Size
IRTranslator LLVM IR MI
This file provides various utilities for inspecting and working with the control flow graph in LLVM I...
mir Rename Register Operands
This file declares the MachineConstantPool class which is an abstract constant pool to keep track of ...
IntegerType * Int32Ty
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
Value * RHS
Value * LHS
xray Insert XRay ops
Class for arbitrary precision integers.
Definition: APInt.h:75
APInt getLoBits(unsigned numBits) const
Compute an APInt containing numBits lowbits from this APInt.
Definition: APInt.cpp:605
uint64_t getZExtValue() const
Get zero extended value.
Definition: APInt.h:1498
unsigned popcount() const
Count the number of bits set.
Definition: APInt.h:1627
unsigned getBitWidth() const
Return the number of bits in the APInt.
Definition: APInt.h:1443
int32_t exactLogBase2() const
Definition: APInt.h:1734
bool isSignedIntN(unsigned N) const
Check if this APInt has an N-bits signed integer value.
Definition: APInt.h:427
bool isIntN(unsigned N) const
Check if this APInt has an N-bits unsigned integer value.
Definition: APInt.h:424
APInt lshr(unsigned shiftAmt) const
Logical right-shift function.
Definition: APInt.h:839
Represent the analysis usage information of a pass.
AnalysisUsage & addRequired()
A "pseudo-class" with methods for operating on BUILD_VECTORs.
bool isConstantSplat(APInt &SplatValue, APInt &SplatUndef, unsigned &SplatBitSize, bool &HasAnyUndefs, unsigned MinSplatBits=0, bool isBigEndian=false) const
Check if this is a constant splat, and if so, find the smallest element size that splats the vector.
This is the shared class of boolean and integer constants.
Definition: Constants.h:78
static Constant * get(Type *Ty, uint64_t V, bool IsSigned=false)
If Ty is a vector type, return a Constant with a splat of the given value.
Definition: Constants.cpp:888
This is an important base class in LLVM.
Definition: Constant.h:41
Legacy analysis pass which computes a DominatorTree.
Definition: Dominators.h:314
FunctionPass class - This class is used to implement most global optimizations.
Definition: Pass.h:311
LLVMContext & getContext() const
getContext - Return a reference to the LLVMContext associated with this function.
Definition: Function.cpp:319
Class to represent integer types.
Definition: DerivedTypes.h:40
static IntegerType * get(LLVMContext &C, unsigned NumBits)
This static method is the primary way of constructing an IntegerType.
Definition: Type.cpp:339
const MCInstrDesc & get(unsigned Opcode) const
Return the machine instruction descriptor that corresponds to the specified instruction opcode.
Definition: MCInstrInfo.h:63
Machine Value Type.
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
const MachineInstrBuilder & addUse(Register RegNo, unsigned Flags=0, unsigned SubReg=0) const
Add a virtual register use operand.
const MachineInstrBuilder & addDef(Register RegNo, unsigned Flags=0, unsigned SubReg=0) const
Add a virtual register definition operand.
Representation of each machine instruction.
Definition: MachineInstr.h:68
MachineOperand class - Representation of each machine instruction operand.
void setReg(Register Reg)
Change the register this operand corresponds to.
MachineInstr * getParent()
getParent - Return the instruction that this operand belongs to.
Register getReg() const
getReg - Returns the register number.
static MachineOperand CreateReg(Register Reg, bool isDef, bool isImp=false, bool isKill=false, bool isDead=false, bool isUndef=false, bool isEarlyClobber=false, unsigned SubReg=0, bool isDebug=false, bool isInternalRead=false, bool isRenamable=false)
reg_begin/reg_end - Provide iteration support to walk over all definitions and uses of a register wit...
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
const InstSeq & Analyze(uint64_t Imm, unsigned Size, bool LastInstrIsADDiu)
Analyze - Get an instruction sequence to load immediate Imm.
bool runOnMachineFunction(MachineFunction &MF) override
runOnMachineFunction - This method must be overloaded to perform the desired machine code transformat...
const MipsSubtarget * Subtarget
Keep a pointer to the MipsSubtarget around so that we can make the right decision when generating cod...
MipsFunctionInfo - This class is derived from MachineFunction private Mips target-specific informatio...
bool hasMips32r6() const
bool isFP64bit() const
bool isLittle() const
bool inMicroMipsMode() const
bool useOddSPReg() const
bool inMips16Mode() const
bool isABI_FPXX() const
bool isGP64bit() const
bool hasMSA() const
bool isABI_O32() const
bool hasMTHC1() const
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
Represents one node in the SelectionDAG.
EVT getValueType(unsigned ResNo) const
Return the type of a specified result.
Unlike LLVM values, Selection DAG nodes may return multiple values as the result of a computation.
SDNode * getNode() const
get the SDNode which holds the desired result
SDValue getValue(unsigned R) const
EVT getValueType() const
Return the ValueType of the referenced return value.
unsigned getOpcode() const
CodeGenOpt::Level OptLevel
const TargetLowering * TLI
MachineFunction * MF
const TargetInstrInfo * TII
void ReplaceNode(SDNode *F, SDNode *T)
Replace all uses of F with T, then remove F from the DAG.
void getAnalysisUsage(AnalysisUsage &AU) const override
getAnalysisUsage - Subclasses that override getAnalysisUsage must call this.
const TargetLowering * getTargetLowering() const
MachineSDNode * getMachineNode(unsigned Opcode, const SDLoc &dl, EVT VT)
These are used for target selectors to create a new node with specified return type(s),...
SDNode * SelectNodeTo(SDNode *N, unsigned MachineOpc, EVT VT)
These are used for target selectors to mutate the specified node to have the specified return type,...
const DataLayout & getDataLayout() const
Definition: SelectionDAG.h:472
SDValue getTargetFrameIndex(int FI, EVT VT)
Definition: SelectionDAG.h:726
SDValue getRegister(unsigned Reg, EVT VT)
SDValue getCopyToReg(SDValue Chain, const SDLoc &dl, unsigned Reg, SDValue N)
Definition: SelectionDAG.h:773
SDValue getTargetConstant(uint64_t Val, const SDLoc &DL, EVT VT, bool isOpaque=false)
Definition: SelectionDAG.h:675
bool isBaseWithConstantOffset(SDValue Op) const
Return true if the specified operand is an ISD::ADD with a ConstantSDNode on the right-hand side,...
SDValue getCopyFromReg(SDValue Chain, const SDLoc &dl, unsigned Reg, EVT VT)
Definition: SelectionDAG.h:799
SDValue getEntryNode() const
Return the token chain corresponding to the entry of the function.
Definition: SelectionDAG.h:554
virtual const TargetRegisterClass * getRegClassFor(MVT VT, bool isDivergent=false) const
Return the register class that should be used for the specified value type.
virtual MVT getPointerTy(const DataLayout &DL, uint32_t AS=0) const
Return the pointer type for the given address space, defaults to the pointer type from the data layou...
This class defines information used to lower LLVM code to legal SelectionDAG operators that the targe...
bool isPositionIndependent() const
unsigned getID() const
Return the register class ID number.
LLVM Value Representation.
Definition: Value.h:74
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
Definition: BitmaskEnum.h:119
Level
Code generation optimization level.
Definition: CodeGen.h:57
@ ConstantFP
Definition: ISDOpcodes.h:77
@ ADDC
Carry-setting nodes for multiple precision addition and subtraction.
Definition: ISDOpcodes.h:269
@ ADD
Simple integer binary arithmetic operators.
Definition: ISDOpcodes.h:239
@ INTRINSIC_VOID
OUTCHAIN = INTRINSIC_VOID(INCHAIN, INTRINSICID, arg1, arg2, ...) This node represents a target intrin...
Definition: ISDOpcodes.h:199
@ BITCAST
BITCAST - This operator converts between integer, vector and FP values, as if the value was stored to...
Definition: ISDOpcodes.h:898
@ TargetExternalSymbol
Definition: ISDOpcodes.h:169
@ TargetGlobalAddress
TargetGlobalAddress - Like GlobalAddress, but the DAG does no folding or anything else with this node...
Definition: ISDOpcodes.h:164
@ TargetConstant
TargetConstant* - Like Constant*, but the DAG does not do any folding, simplification,...
Definition: ISDOpcodes.h:158
@ INTRINSIC_WO_CHAIN
RESULT = INTRINSIC_WO_CHAIN(INTRINSICID, arg1, arg2, ...) This node represents a target intrinsic fun...
Definition: ISDOpcodes.h:184
@ ADDE
Carry-using nodes for multiple precision addition and subtraction.
Definition: ISDOpcodes.h:279
@ INTRINSIC_W_CHAIN
RESULT,OUTCHAIN = INTRINSIC_W_CHAIN(INCHAIN, INTRINSICID, arg1, ...) This node represents a target in...
Definition: ISDOpcodes.h:192
@ BUILD_VECTOR
BUILD_VECTOR(ELT0, ELT1, ELT2, ELT3,...) - Return a fixed-width vector with the specified,...
Definition: ISDOpcodes.h:514
Flag
These should be considered private to the implementation of the MCInstrDesc class.
Definition: MCInstrDesc.h:148
@ Implicit
Not emitted register (e.g. carry, or temporary result).
@ Undef
Value of the register doesn't matter.
Reg
All possible values of the reg field in the ModR/M byte.
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
@ Offset
Definition: DWP.cpp:406
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
bool isAligned(Align Lhs, uint64_t SizeInBytes)
Checks that SizeInBytes is a multiple of the alignment.
Definition: Alignment.h:145
bool isIntN(unsigned N, int64_t x)
Checks if an signed integer fits into the given (dynamic) bit width.
Definition: MathExtras.h:261
FunctionPass * createMipsSEISelDag(MipsTargetMachine &TM, CodeGenOpt::Level OptLevel)
unsigned Log2(Align A)
Returns the log2 of the alignment.
Definition: Alignment.h:208
#define N
This struct is a compact representation of a valid (non-zero power of two) alignment.
Definition: Alignment.h:39
Extended Value Type.
Definition: ValueTypes.h:34
TypeSize getSizeInBits() const
Return the size of the specified value type in bits.
Definition: ValueTypes.h:351
MVT getSimpleVT() const
Return the SimpleValueType held in the specified simple EVT.
Definition: ValueTypes.h:299
bool is128BitVector() const
Return true if this is a 128-bit vector type.
Definition: ValueTypes.h:196
EVT getVectorElementType() const
Given a vector type, return the type of each element.
Definition: ValueTypes.h:311