LLVM  7.0.0svn
HexagonISelLowering.cpp
Go to the documentation of this file.
1 //===-- HexagonISelLowering.cpp - Hexagon DAG Lowering Implementation -----===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file implements the interfaces that Hexagon uses to lower LLVM code
11 // into a selection DAG.
12 //
13 //===----------------------------------------------------------------------===//
14 
15 #include "HexagonISelLowering.h"
16 #include "Hexagon.h"
18 #include "HexagonRegisterInfo.h"
19 #include "HexagonSubtarget.h"
20 #include "HexagonTargetMachine.h"
22 #include "llvm/ADT/APInt.h"
23 #include "llvm/ADT/ArrayRef.h"
24 #include "llvm/ADT/SmallVector.h"
34 #include "llvm/IR/BasicBlock.h"
35 #include "llvm/IR/CallingConv.h"
36 #include "llvm/IR/DataLayout.h"
37 #include "llvm/IR/DerivedTypes.h"
38 #include "llvm/IR/Function.h"
39 #include "llvm/IR/GlobalValue.h"
40 #include "llvm/IR/InlineAsm.h"
41 #include "llvm/IR/Instructions.h"
42 #include "llvm/IR/Intrinsics.h"
43 #include "llvm/IR/Module.h"
44 #include "llvm/IR/Type.h"
45 #include "llvm/IR/Value.h"
46 #include "llvm/MC/MCRegisterInfo.h"
47 #include "llvm/Support/Casting.h"
48 #include "llvm/Support/CodeGen.h"
50 #include "llvm/Support/Debug.h"
55 #include <algorithm>
56 #include <cassert>
57 #include <cstddef>
58 #include <cstdint>
59 #include <limits>
60 #include <utility>
61 
62 using namespace llvm;
63 
64 #define DEBUG_TYPE "hexagon-lowering"
65 
66 static cl::opt<bool> EmitJumpTables("hexagon-emit-jump-tables",
67  cl::init(true), cl::Hidden,
68  cl::desc("Control jump table emission on Hexagon target"));
69 
70 static cl::opt<bool> EnableHexSDNodeSched("enable-hexagon-sdnode-sched",
72  cl::desc("Enable Hexagon SDNode scheduling"));
73 
74 static cl::opt<bool> EnableFastMath("ffast-math",
76  cl::desc("Enable Fast Math processing"));
77 
78 static cl::opt<int> MinimumJumpTables("minimum-jump-tables",
80  cl::desc("Set minimum jump tables"));
81 
82 static cl::opt<int> MaxStoresPerMemcpyCL("max-store-memcpy",
84  cl::desc("Max #stores to inline memcpy"));
85 
86 static cl::opt<int> MaxStoresPerMemcpyOptSizeCL("max-store-memcpy-Os",
88  cl::desc("Max #stores to inline memcpy"));
89 
90 static cl::opt<int> MaxStoresPerMemmoveCL("max-store-memmove",
92  cl::desc("Max #stores to inline memmove"));
93 
94 static cl::opt<int> MaxStoresPerMemmoveOptSizeCL("max-store-memmove-Os",
96  cl::desc("Max #stores to inline memmove"));
97 
98 static cl::opt<int> MaxStoresPerMemsetCL("max-store-memset",
100  cl::desc("Max #stores to inline memset"));
101 
102 static cl::opt<int> MaxStoresPerMemsetOptSizeCL("max-store-memset-Os",
104  cl::desc("Max #stores to inline memset"));
105 
106 
107 namespace {
108 
109  class HexagonCCState : public CCState {
110  unsigned NumNamedVarArgParams;
111 
112  public:
113  HexagonCCState(CallingConv::ID CC, bool isVarArg, MachineFunction &MF,
115  int NumNamedVarArgParams)
116  : CCState(CC, isVarArg, MF, locs, C),
117  NumNamedVarArgParams(NumNamedVarArgParams) {}
118 
119  unsigned getNumNamedVarArgParams() const { return NumNamedVarArgParams; }
120  };
121 
123  Even = 0,
124  Odd,
125  NoPattern
126  };
127 
128 } // end anonymous namespace
129 
130 // Implement calling convention for Hexagon.
131 
134 static const MVT LegalV128[] = { MVT::v128i8, MVT::v64i16, MVT::v32i32 };
136 
137 static bool
138 CC_Hexagon(unsigned ValNo, MVT ValVT,
139  MVT LocVT, CCValAssign::LocInfo LocInfo,
140  ISD::ArgFlagsTy ArgFlags, CCState &State);
141 
142 static bool
143 CC_Hexagon32(unsigned ValNo, MVT ValVT,
144  MVT LocVT, CCValAssign::LocInfo LocInfo,
145  ISD::ArgFlagsTy ArgFlags, CCState &State);
146 
147 static bool
148 CC_Hexagon64(unsigned ValNo, MVT ValVT,
149  MVT LocVT, CCValAssign::LocInfo LocInfo,
150  ISD::ArgFlagsTy ArgFlags, CCState &State);
151 
152 static bool
153 CC_HexagonVector(unsigned ValNo, MVT ValVT,
154  MVT LocVT, CCValAssign::LocInfo LocInfo,
155  ISD::ArgFlagsTy ArgFlags, CCState &State);
156 
157 static bool
158 RetCC_Hexagon(unsigned ValNo, MVT ValVT,
159  MVT LocVT, CCValAssign::LocInfo LocInfo,
160  ISD::ArgFlagsTy ArgFlags, CCState &State);
161 
162 static bool
163 RetCC_Hexagon32(unsigned ValNo, MVT ValVT,
164  MVT LocVT, CCValAssign::LocInfo LocInfo,
165  ISD::ArgFlagsTy ArgFlags, CCState &State);
166 
167 static bool
168 RetCC_Hexagon64(unsigned ValNo, MVT ValVT,
169  MVT LocVT, CCValAssign::LocInfo LocInfo,
170  ISD::ArgFlagsTy ArgFlags, CCState &State);
171 
172 static bool
173 RetCC_HexagonVector(unsigned ValNo, MVT ValVT,
174  MVT LocVT, CCValAssign::LocInfo LocInfo,
175  ISD::ArgFlagsTy ArgFlags, CCState &State);
176 
177 static bool
178 CC_Hexagon_VarArg (unsigned ValNo, MVT ValVT,
179  MVT LocVT, CCValAssign::LocInfo LocInfo,
180  ISD::ArgFlagsTy ArgFlags, CCState &State) {
181  HexagonCCState &HState = static_cast<HexagonCCState &>(State);
182 
183  if (ValNo < HState.getNumNamedVarArgParams()) {
184  // Deal with named arguments.
185  return CC_Hexagon(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State);
186  }
187 
188  // Deal with un-named arguments.
189  unsigned Offset;
190  if (ArgFlags.isByVal()) {
191  // If pass-by-value, the size allocated on stack is decided
192  // by ArgFlags.getByValSize(), not by the size of LocVT.
193  Offset = State.AllocateStack(ArgFlags.getByValSize(),
194  ArgFlags.getByValAlign());
195  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
196  return false;
197  }
198  if (LocVT == MVT::i1 || LocVT == MVT::i8 || LocVT == MVT::i16) {
199  LocVT = MVT::i32;
200  ValVT = MVT::i32;
201  if (ArgFlags.isSExt())
202  LocInfo = CCValAssign::SExt;
203  else if (ArgFlags.isZExt())
204  LocInfo = CCValAssign::ZExt;
205  else
206  LocInfo = CCValAssign::AExt;
207  }
208  if (LocVT == MVT::i32 || LocVT == MVT::f32) {
209  Offset = State.AllocateStack(4, 4);
210  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
211  return false;
212  }
213  if (LocVT == MVT::i64 || LocVT == MVT::f64) {
214  Offset = State.AllocateStack(8, 8);
215  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
216  return false;
217  }
218  if (LocVT == MVT::v2i64 || LocVT == MVT::v4i32 || LocVT == MVT::v8i16 ||
219  LocVT == MVT::v16i8) {
220  Offset = State.AllocateStack(16, 16);
221  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
222  return false;
223  }
224  if (LocVT == MVT::v4i64 || LocVT == MVT::v8i32 || LocVT == MVT::v16i16 ||
225  LocVT == MVT::v32i8) {
226  Offset = State.AllocateStack(32, 32);
227  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
228  return false;
229  }
230  if (LocVT == MVT::v16i32 || LocVT == MVT::v32i16 ||
231  LocVT == MVT::v64i8 || LocVT == MVT::v512i1) {
232  Offset = State.AllocateStack(64, 64);
233  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
234  return false;
235  }
236  if (LocVT == MVT::v32i32 || LocVT == MVT::v64i16 ||
237  LocVT == MVT::v128i8 || LocVT == MVT::v1024i1) {
238  Offset = State.AllocateStack(128, 128);
239  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
240  return false;
241  }
242  if (LocVT == MVT::v64i32 || LocVT == MVT::v128i16 ||
243  LocVT == MVT::v256i8) {
244  Offset = State.AllocateStack(256, 256);
245  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
246  return false;
247  }
248 
249  llvm_unreachable(nullptr);
250 }
251 
252 static bool CC_Hexagon (unsigned ValNo, MVT ValVT, MVT LocVT,
253  CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags, CCState &State) {
254  if (ArgFlags.isByVal()) {
255  // Passed on stack.
256  unsigned Offset = State.AllocateStack(ArgFlags.getByValSize(),
257  ArgFlags.getByValAlign());
258  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
259  return false;
260  }
261 
262  if (LocVT == MVT::i1) {
263  LocVT = MVT::i32;
264  } else if (LocVT == MVT::i8 || LocVT == MVT::i16) {
265  LocVT = MVT::i32;
266  ValVT = MVT::i32;
267  if (ArgFlags.isSExt())
268  LocInfo = CCValAssign::SExt;
269  else if (ArgFlags.isZExt())
270  LocInfo = CCValAssign::ZExt;
271  else
272  LocInfo = CCValAssign::AExt;
273  } else if (LocVT == MVT::v4i8 || LocVT == MVT::v2i16) {
274  LocVT = MVT::i32;
275  LocInfo = CCValAssign::BCvt;
276  } else if (LocVT == MVT::v8i8 || LocVT == MVT::v4i16 || LocVT == MVT::v2i32) {
277  LocVT = MVT::i64;
278  LocInfo = CCValAssign::BCvt;
279  }
280 
281  if (LocVT == MVT::i32 || LocVT == MVT::f32) {
282  if (!CC_Hexagon32(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State))
283  return false;
284  }
285 
286  if (LocVT == MVT::i64 || LocVT == MVT::f64) {
287  if (!CC_Hexagon64(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State))
288  return false;
289  }
290 
291  if (LocVT == MVT::v8i32 || LocVT == MVT::v16i16 || LocVT == MVT::v32i8) {
292  unsigned Offset = State.AllocateStack(ArgFlags.getByValSize(), 32);
293  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
294  return false;
295  }
296 
297  auto &HST = State.getMachineFunction().getSubtarget<HexagonSubtarget>();
298  if (HST.isHVXVectorType(LocVT)) {
299  if (!CC_HexagonVector(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State))
300  return false;
301  }
302 
303  return true; // CC didn't match.
304 }
305 
306 
307 static bool CC_Hexagon32(unsigned ValNo, MVT ValVT,
308  MVT LocVT, CCValAssign::LocInfo LocInfo,
309  ISD::ArgFlagsTy ArgFlags, CCState &State) {
310  static const MCPhysReg RegList[] = {
311  Hexagon::R0, Hexagon::R1, Hexagon::R2, Hexagon::R3, Hexagon::R4,
312  Hexagon::R5
313  };
314  if (unsigned Reg = State.AllocateReg(RegList)) {
315  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
316  return false;
317  }
318 
319  unsigned Offset = State.AllocateStack(4, 4);
320  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
321  return false;
322 }
323 
324 static bool CC_Hexagon64(unsigned ValNo, MVT ValVT,
325  MVT LocVT, CCValAssign::LocInfo LocInfo,
326  ISD::ArgFlagsTy ArgFlags, CCState &State) {
327  if (unsigned Reg = State.AllocateReg(Hexagon::D0)) {
328  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
329  return false;
330  }
331 
332  static const MCPhysReg RegList1[] = {
333  Hexagon::D1, Hexagon::D2
334  };
335  static const MCPhysReg RegList2[] = {
336  Hexagon::R1, Hexagon::R3
337  };
338  if (unsigned Reg = State.AllocateReg(RegList1, RegList2)) {
339  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
340  return false;
341  }
342 
343  unsigned Offset = State.AllocateStack(8, 8, Hexagon::D2);
344  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
345  return false;
346 }
347 
348 static bool CC_HexagonVector(unsigned ValNo, MVT ValVT,
349  MVT LocVT, CCValAssign::LocInfo LocInfo,
350  ISD::ArgFlagsTy ArgFlags, CCState &State) {
351  static const MCPhysReg VecLstS[] = {
352  Hexagon::V0, Hexagon::V1, Hexagon::V2, Hexagon::V3, Hexagon::V4,
353  Hexagon::V5, Hexagon::V6, Hexagon::V7, Hexagon::V8, Hexagon::V9,
354  Hexagon::V10, Hexagon::V11, Hexagon::V12, Hexagon::V13, Hexagon::V14,
355  Hexagon::V15
356  };
357  static const MCPhysReg VecLstD[] = {
358  Hexagon::W0, Hexagon::W1, Hexagon::W2, Hexagon::W3, Hexagon::W4,
359  Hexagon::W5, Hexagon::W6, Hexagon::W7
360  };
361  auto &MF = State.getMachineFunction();
362  auto &HST = MF.getSubtarget<HexagonSubtarget>();
363 
364  if (HST.useHVX64BOps() &&
365  (LocVT == MVT::v16i32 || LocVT == MVT::v32i16 ||
366  LocVT == MVT::v64i8 || LocVT == MVT::v512i1)) {
367  if (unsigned Reg = State.AllocateReg(VecLstS)) {
368  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
369  return false;
370  }
371  unsigned Offset = State.AllocateStack(64, 64);
372  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
373  return false;
374  }
375  if (HST.useHVX64BOps() && (LocVT == MVT::v32i32 ||
376  LocVT == MVT::v64i16 || LocVT == MVT::v128i8)) {
377  if (unsigned Reg = State.AllocateReg(VecLstD)) {
378  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
379  return false;
380  }
381  unsigned Offset = State.AllocateStack(128, 128);
382  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
383  return false;
384  }
385  // 128B Mode
386  if (HST.useHVX128BOps() && (LocVT == MVT::v64i32 ||
387  LocVT == MVT::v128i16 || LocVT == MVT::v256i8)) {
388  if (unsigned Reg = State.AllocateReg(VecLstD)) {
389  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
390  return false;
391  }
392  unsigned Offset = State.AllocateStack(256, 256);
393  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
394  return false;
395  }
396  if (HST.useHVX128BOps() &&
397  (LocVT == MVT::v32i32 || LocVT == MVT::v64i16 ||
398  LocVT == MVT::v128i8 || LocVT == MVT::v1024i1)) {
399  if (unsigned Reg = State.AllocateReg(VecLstS)) {
400  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
401  return false;
402  }
403  unsigned Offset = State.AllocateStack(128, 128);
404  State.addLoc(CCValAssign::getMem(ValNo, ValVT, Offset, LocVT, LocInfo));
405  return false;
406  }
407  return true;
408 }
409 
410 static bool RetCC_Hexagon(unsigned ValNo, MVT ValVT,
411  MVT LocVT, CCValAssign::LocInfo LocInfo,
412  ISD::ArgFlagsTy ArgFlags, CCState &State) {
413  auto &MF = State.getMachineFunction();
414  auto &HST = MF.getSubtarget<HexagonSubtarget>();
415 
416  if (LocVT == MVT::i1) {
417  // Return values of type MVT::i1 still need to be assigned to R0, but
418  // the value type needs to remain i1. LowerCallResult will deal with it,
419  // but it needs to recognize i1 as the value type.
420  LocVT = MVT::i32;
421  } else if (LocVT == MVT::i8 || LocVT == MVT::i16) {
422  LocVT = MVT::i32;
423  ValVT = MVT::i32;
424  if (ArgFlags.isSExt())
425  LocInfo = CCValAssign::SExt;
426  else if (ArgFlags.isZExt())
427  LocInfo = CCValAssign::ZExt;
428  else
429  LocInfo = CCValAssign::AExt;
430  } else if (LocVT == MVT::v4i8 || LocVT == MVT::v2i16) {
431  LocVT = MVT::i32;
432  LocInfo = CCValAssign::BCvt;
433  } else if (LocVT == MVT::v8i8 || LocVT == MVT::v4i16 || LocVT == MVT::v2i32) {
434  LocVT = MVT::i64;
435  LocInfo = CCValAssign::BCvt;
436  } else if (LocVT == MVT::v64i8 || LocVT == MVT::v32i16 ||
437  LocVT == MVT::v16i32 || LocVT == MVT::v512i1) {
438  LocVT = MVT::v16i32;
439  ValVT = MVT::v16i32;
440  LocInfo = CCValAssign::Full;
441  } else if (LocVT == MVT::v128i8 || LocVT == MVT::v64i16 ||
442  LocVT == MVT::v32i32 ||
443  (LocVT == MVT::v1024i1 && HST.useHVX128BOps())) {
444  LocVT = MVT::v32i32;
445  ValVT = MVT::v32i32;
446  LocInfo = CCValAssign::Full;
447  } else if (LocVT == MVT::v256i8 || LocVT == MVT::v128i16 ||
448  LocVT == MVT::v64i32) {
449  LocVT = MVT::v64i32;
450  ValVT = MVT::v64i32;
451  LocInfo = CCValAssign::Full;
452  }
453  if (LocVT == MVT::i32 || LocVT == MVT::f32) {
454  if (!RetCC_Hexagon32(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State))
455  return false;
456  }
457 
458  if (LocVT == MVT::i64 || LocVT == MVT::f64) {
459  if (!RetCC_Hexagon64(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State))
460  return false;
461  }
462  if (LocVT == MVT::v16i32 || LocVT == MVT::v32i32 || LocVT == MVT::v64i32) {
463  if (!RetCC_HexagonVector(ValNo, ValVT, LocVT, LocInfo, ArgFlags, State))
464  return false;
465  }
466  return true; // CC didn't match.
467 }
468 
469 static bool RetCC_Hexagon32(unsigned ValNo, MVT ValVT,
470  MVT LocVT, CCValAssign::LocInfo LocInfo,
471  ISD::ArgFlagsTy ArgFlags, CCState &State) {
472  if (LocVT == MVT::i32 || LocVT == MVT::f32) {
473  // Note that use of registers beyond R1 is not ABI compliant. However there
474  // are (experimental) IR passes which generate internal functions that
475  // return structs using these additional registers.
476  static const uint16_t RegList[] = { Hexagon::R0, Hexagon::R1,
477  Hexagon::R2, Hexagon::R3,
478  Hexagon::R4, Hexagon::R5 };
479  if (unsigned Reg = State.AllocateReg(RegList)) {
480  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
481  return false;
482  }
483  }
484 
485  return true;
486 }
487 
488 static bool RetCC_Hexagon64(unsigned ValNo, MVT ValVT,
489  MVT LocVT, CCValAssign::LocInfo LocInfo,
490  ISD::ArgFlagsTy ArgFlags, CCState &State) {
491  if (LocVT == MVT::i64 || LocVT == MVT::f64) {
492  if (unsigned Reg = State.AllocateReg(Hexagon::D0)) {
493  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
494  return false;
495  }
496  }
497 
498  return true;
499 }
500 
501 static bool RetCC_HexagonVector(unsigned ValNo, MVT ValVT,
502  MVT LocVT, CCValAssign::LocInfo LocInfo,
503  ISD::ArgFlagsTy ArgFlags, CCState &State) {
504  auto &MF = State.getMachineFunction();
505  auto &HST = MF.getSubtarget<HexagonSubtarget>();
506 
507  if (LocVT == MVT::v16i32) {
508  if (unsigned Reg = State.AllocateReg(Hexagon::V0)) {
509  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
510  return false;
511  }
512  } else if (LocVT == MVT::v32i32) {
513  unsigned Req = HST.useHVX128BOps() ? Hexagon::V0 : Hexagon::W0;
514  if (unsigned Reg = State.AllocateReg(Req)) {
515  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
516  return false;
517  }
518  } else if (LocVT == MVT::v64i32) {
519  if (unsigned Reg = State.AllocateReg(Hexagon::W0)) {
520  State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
521  return false;
522  }
523  }
524 
525  return true;
526 }
527 
528 void HexagonTargetLowering::promoteLdStType(MVT VT, MVT PromotedLdStVT) {
529  if (VT != PromotedLdStVT) {
530  setOperationAction(ISD::LOAD, VT, Promote);
531  AddPromotedToType(ISD::LOAD, VT, PromotedLdStVT);
532 
533  setOperationAction(ISD::STORE, VT, Promote);
534  AddPromotedToType(ISD::STORE, VT, PromotedLdStVT);
535  }
536 }
537 
538 SDValue
540  const {
541  return SDValue();
542 }
543 
544 /// CreateCopyOfByValArgument - Make a copy of an aggregate at address specified
545 /// by "Src" to address "Dst" of size "Size". Alignment information is
546 /// specified by the specific parameter attribute. The copy will be passed as
547 /// a byval function parameter. Sometimes what we are copying is the end of a
548 /// larger object, the part that does not fit in registers.
550  SDValue Chain, ISD::ArgFlagsTy Flags,
551  SelectionDAG &DAG, const SDLoc &dl) {
552  SDValue SizeNode = DAG.getConstant(Flags.getByValSize(), dl, MVT::i32);
553  return DAG.getMemcpy(Chain, dl, Dst, Src, SizeNode, Flags.getByValAlign(),
554  /*isVolatile=*/false, /*AlwaysInline=*/false,
555  /*isTailCall=*/false,
557 }
558 
559 bool
561  CallingConv::ID CallConv, MachineFunction &MF, bool isVarArg,
563  LLVMContext &Context) const {
565  CCState CCInfo(CallConv, isVarArg, MF, RVLocs, Context);
566  return CCInfo.CheckReturn(Outs, RetCC_Hexagon);
567 }
568 
569 // LowerReturn - Lower ISD::RET. If a struct is larger than 8 bytes and is
570 // passed by value, the function prototype is modified to return void and
571 // the value is stored in memory pointed by a pointer passed by caller.
572 SDValue
574  bool isVarArg,
576  const SmallVectorImpl<SDValue> &OutVals,
577  const SDLoc &dl, SelectionDAG &DAG) const {
578  // CCValAssign - represent the assignment of the return value to locations.
580 
581  // CCState - Info about the registers and stack slot.
582  CCState CCInfo(CallConv, isVarArg, DAG.getMachineFunction(), RVLocs,
583  *DAG.getContext());
584 
585  // Analyze return values of ISD::RET
586  CCInfo.AnalyzeReturn(Outs, RetCC_Hexagon);
587 
588  SDValue Flag;
589  SmallVector<SDValue, 4> RetOps(1, Chain);
590 
591  // Copy the result values into the output registers.
592  for (unsigned i = 0; i != RVLocs.size(); ++i) {
593  CCValAssign &VA = RVLocs[i];
594 
595  Chain = DAG.getCopyToReg(Chain, dl, VA.getLocReg(), OutVals[i], Flag);
596 
597  // Guarantee that all emitted copies are stuck together with flags.
598  Flag = Chain.getValue(1);
599  RetOps.push_back(DAG.getRegister(VA.getLocReg(), VA.getLocVT()));
600  }
601 
602  RetOps[0] = Chain; // Update chain.
603 
604  // Add the flag if we have it.
605  if (Flag.getNode())
606  RetOps.push_back(Flag);
607 
608  return DAG.getNode(HexagonISD::RET_FLAG, dl, MVT::Other, RetOps);
609 }
610 
612  // If either no tail call or told not to tail call at all, don't.
613  auto Attr =
614  CI->getParent()->getParent()->getFnAttribute("disable-tail-calls");
615  if (!CI->isTailCall() || Attr.getValueAsString() == "true")
616  return false;
617 
618  return true;
619 }
620 
621 /// LowerCallResult - Lower the result values of an ISD::CALL into the
622 /// appropriate copies out of appropriate physical registers. This assumes that
623 /// Chain/Glue are the input chain/glue to use, and that TheCall is the call
624 /// being lowered. Returns a SDNode with the same number of values as the
625 /// ISD::CALL.
627  SDValue Chain, SDValue Glue, CallingConv::ID CallConv, bool isVarArg,
628  const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &dl,
630  const SmallVectorImpl<SDValue> &OutVals, SDValue Callee) const {
631  // Assign locations to each value returned by this call.
633 
634  CCState CCInfo(CallConv, isVarArg, DAG.getMachineFunction(), RVLocs,
635  *DAG.getContext());
636 
637  CCInfo.AnalyzeCallResult(Ins, RetCC_Hexagon);
638 
639  // Copy all of the result registers out of their specified physreg.
640  for (unsigned i = 0; i != RVLocs.size(); ++i) {
641  SDValue RetVal;
642  if (RVLocs[i].getValVT() == MVT::i1) {
643  // Return values of type MVT::i1 require special handling. The reason
644  // is that MVT::i1 is associated with the PredRegs register class, but
645  // values of that type are still returned in R0. Generate an explicit
646  // copy into a predicate register from R0, and treat the value of the
647  // predicate register as the call result.
648  auto &MRI = DAG.getMachineFunction().getRegInfo();
649  SDValue FR0 = DAG.getCopyFromReg(Chain, dl, RVLocs[i].getLocReg(),
650  MVT::i32, Glue);
651  // FR0 = (Value, Chain, Glue)
652  unsigned PredR = MRI.createVirtualRegister(&Hexagon::PredRegsRegClass);
653  SDValue TPR = DAG.getCopyToReg(FR0.getValue(1), dl, PredR,
654  FR0.getValue(0), FR0.getValue(2));
655  // TPR = (Chain, Glue)
656  // Don't glue this CopyFromReg, because it copies from a virtual
657  // register. If it is glued to the call, InstrEmitter will add it
658  // as an implicit def to the call (EmitMachineNode).
659  RetVal = DAG.getCopyFromReg(TPR.getValue(0), dl, PredR, MVT::i1);
660  Glue = TPR.getValue(1);
661  Chain = TPR.getValue(0);
662  } else {
663  RetVal = DAG.getCopyFromReg(Chain, dl, RVLocs[i].getLocReg(),
664  RVLocs[i].getValVT(), Glue);
665  Glue = RetVal.getValue(2);
666  Chain = RetVal.getValue(1);
667  }
668  InVals.push_back(RetVal.getValue(0));
669  }
670 
671  return Chain;
672 }
673 
674 /// LowerCall - Functions arguments are copied from virtual regs to
675 /// (physical regs)/(stack frame), CALLSEQ_START and CALLSEQ_END are emitted.
676 SDValue
678  SmallVectorImpl<SDValue> &InVals) const {
679  SelectionDAG &DAG = CLI.DAG;
680  SDLoc &dl = CLI.DL;
682  SmallVectorImpl<SDValue> &OutVals = CLI.OutVals;
684  SDValue Chain = CLI.Chain;
685  SDValue Callee = CLI.Callee;
686  bool &IsTailCall = CLI.IsTailCall;
687  CallingConv::ID CallConv = CLI.CallConv;
688  bool IsVarArg = CLI.IsVarArg;
689  bool DoesNotReturn = CLI.DoesNotReturn;
690 
691  bool IsStructRet = (Outs.empty()) ? false : Outs[0].Flags.isSRet();
693  MachineFrameInfo &MFI = MF.getFrameInfo();
694  auto PtrVT = getPointerTy(MF.getDataLayout());
695 
696  // Check for varargs.
697  unsigned NumNamedVarArgParams = -1U;
698  if (GlobalAddressSDNode *GAN = dyn_cast<GlobalAddressSDNode>(Callee)) {
699  const GlobalValue *GV = GAN->getGlobal();
700  Callee = DAG.getTargetGlobalAddress(GV, dl, MVT::i32);
701  if (const Function* F = dyn_cast<Function>(GV)) {
702  // If a function has zero args and is a vararg function, that's
703  // disallowed so it must be an undeclared function. Do not assume
704  // varargs if the callee is undefined.
705  if (F->isVarArg() && F->getFunctionType()->getNumParams() != 0)
706  NumNamedVarArgParams = F->getFunctionType()->getNumParams();
707  }
708  }
709 
710  // Analyze operands of the call, assigning locations to each operand.
712  HexagonCCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), ArgLocs,
713  *DAG.getContext(), NumNamedVarArgParams);
714 
715  if (IsVarArg)
716  CCInfo.AnalyzeCallOperands(Outs, CC_Hexagon_VarArg);
717  else
718  CCInfo.AnalyzeCallOperands(Outs, CC_Hexagon);
719 
720  auto Attr = MF.getFunction().getFnAttribute("disable-tail-calls");
721  if (Attr.getValueAsString() == "true")
722  IsTailCall = false;
723 
724  if (IsTailCall) {
725  bool StructAttrFlag = MF.getFunction().hasStructRetAttr();
726  IsTailCall = IsEligibleForTailCallOptimization(Callee, CallConv,
727  IsVarArg, IsStructRet,
728  StructAttrFlag,
729  Outs, OutVals, Ins, DAG);
730  for (unsigned i = 0, e = ArgLocs.size(); i != e; ++i) {
731  CCValAssign &VA = ArgLocs[i];
732  if (VA.isMemLoc()) {
733  IsTailCall = false;
734  break;
735  }
736  }
737  DEBUG(dbgs() << (IsTailCall ? "Eligible for Tail Call\n"
738  : "Argument must be passed on stack. "
739  "Not eligible for Tail Call\n"));
740  }
741  // Get a count of how many bytes are to be pushed on the stack.
742  unsigned NumBytes = CCInfo.getNextStackOffset();
744  SmallVector<SDValue, 8> MemOpChains;
745 
746  auto &HRI = *Subtarget.getRegisterInfo();
747  SDValue StackPtr =
748  DAG.getCopyFromReg(Chain, dl, HRI.getStackRegister(), PtrVT);
749 
750  bool NeedsArgAlign = false;
751  unsigned LargestAlignSeen = 0;
752  // Walk the register/memloc assignments, inserting copies/loads.
753  for (unsigned i = 0, e = ArgLocs.size(); i != e; ++i) {
754  CCValAssign &VA = ArgLocs[i];
755  SDValue Arg = OutVals[i];
756  ISD::ArgFlagsTy Flags = Outs[i].Flags;
757  // Record if we need > 8 byte alignment on an argument.
758  bool ArgAlign = Subtarget.isHVXVectorType(VA.getValVT());
759  NeedsArgAlign |= ArgAlign;
760 
761  // Promote the value if needed.
762  switch (VA.getLocInfo()) {
763  default:
764  // Loc info must be one of Full, BCvt, SExt, ZExt, or AExt.
765  llvm_unreachable("Unknown loc info!");
766  case CCValAssign::Full:
767  break;
768  case CCValAssign::BCvt:
769  Arg = DAG.getBitcast(VA.getLocVT(), Arg);
770  break;
771  case CCValAssign::SExt:
772  Arg = DAG.getNode(ISD::SIGN_EXTEND, dl, VA.getLocVT(), Arg);
773  break;
774  case CCValAssign::ZExt:
775  Arg = DAG.getNode(ISD::ZERO_EXTEND, dl, VA.getLocVT(), Arg);
776  break;
777  case CCValAssign::AExt:
778  Arg = DAG.getNode(ISD::ANY_EXTEND, dl, VA.getLocVT(), Arg);
779  break;
780  }
781 
782  if (VA.isMemLoc()) {
783  unsigned LocMemOffset = VA.getLocMemOffset();
784  SDValue MemAddr = DAG.getConstant(LocMemOffset, dl,
785  StackPtr.getValueType());
786  MemAddr = DAG.getNode(ISD::ADD, dl, MVT::i32, StackPtr, MemAddr);
787  if (ArgAlign)
788  LargestAlignSeen = std::max(LargestAlignSeen,
789  VA.getLocVT().getStoreSizeInBits() >> 3);
790  if (Flags.isByVal()) {
791  // The argument is a struct passed by value. According to LLVM, "Arg"
792  // is is pointer.
793  MemOpChains.push_back(CreateCopyOfByValArgument(Arg, MemAddr, Chain,
794  Flags, DAG, dl));
795  } else {
797  DAG.getMachineFunction(), LocMemOffset);
798  SDValue S = DAG.getStore(Chain, dl, Arg, MemAddr, LocPI);
799  MemOpChains.push_back(S);
800  }
801  continue;
802  }
803 
804  // Arguments that can be passed on register must be kept at RegsToPass
805  // vector.
806  if (VA.isRegLoc())
807  RegsToPass.push_back(std::make_pair(VA.getLocReg(), Arg));
808  }
809 
810  if (NeedsArgAlign && Subtarget.hasV60TOps()) {
811  DEBUG(dbgs() << "Function needs byte stack align due to call args\n");
812  // V6 vectors passed by value have 64 or 128 byte alignment depending
813  // on whether we are 64 byte vector mode or 128 byte.
814  bool UseHVX128B = Subtarget.useHVX128BOps();
815  assert(Subtarget.useHVXOps());
816  const unsigned ObjAlign = UseHVX128B ? 128 : 64;
817  LargestAlignSeen = std::max(LargestAlignSeen, ObjAlign);
818  MFI.ensureMaxAlignment(LargestAlignSeen);
819  }
820  // Transform all store nodes into one single node because all store
821  // nodes are independent of each other.
822  if (!MemOpChains.empty())
823  Chain = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, MemOpChains);
824 
825  SDValue Glue;
826  if (!IsTailCall) {
827  Chain = DAG.getCALLSEQ_START(Chain, NumBytes, 0, dl);
828  Glue = Chain.getValue(1);
829  }
830 
831  // Build a sequence of copy-to-reg nodes chained together with token
832  // chain and flag operands which copy the outgoing args into registers.
833  // The Glue is necessary since all emitted instructions must be
834  // stuck together.
835  if (!IsTailCall) {
836  for (unsigned i = 0, e = RegsToPass.size(); i != e; ++i) {
837  Chain = DAG.getCopyToReg(Chain, dl, RegsToPass[i].first,
838  RegsToPass[i].second, Glue);
839  Glue = Chain.getValue(1);
840  }
841  } else {
842  // For tail calls lower the arguments to the 'real' stack slot.
843  //
844  // Force all the incoming stack arguments to be loaded from the stack
845  // before any new outgoing arguments are stored to the stack, because the
846  // outgoing stack slots may alias the incoming argument stack slots, and
847  // the alias isn't otherwise explicit. This is slightly more conservative
848  // than necessary, because it means that each store effectively depends
849  // on every argument instead of just those arguments it would clobber.
850  //
851  // Do not flag preceding copytoreg stuff together with the following stuff.
852  Glue = SDValue();
853  for (unsigned i = 0, e = RegsToPass.size(); i != e; ++i) {
854  Chain = DAG.getCopyToReg(Chain, dl, RegsToPass[i].first,
855  RegsToPass[i].second, Glue);
856  Glue = Chain.getValue(1);
857  }
858  Glue = SDValue();
859  }
860 
861  bool LongCalls = MF.getSubtarget<HexagonSubtarget>().useLongCalls();
862  unsigned Flags = LongCalls ? HexagonII::HMOTF_ConstExtended : 0;
863 
864  // If the callee is a GlobalAddress/ExternalSymbol node (quite common, every
865  // direct call is) turn it into a TargetGlobalAddress/TargetExternalSymbol
866  // node so that legalize doesn't hack it.
867  if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
868  Callee = DAG.getTargetGlobalAddress(G->getGlobal(), dl, PtrVT, 0, Flags);
869  } else if (ExternalSymbolSDNode *S =
870  dyn_cast<ExternalSymbolSDNode>(Callee)) {
871  Callee = DAG.getTargetExternalSymbol(S->getSymbol(), PtrVT, Flags);
872  }
873 
874  // Returns a chain & a flag for retval copy to use.
875  SDVTList NodeTys = DAG.getVTList(MVT::Other, MVT::Glue);
877  Ops.push_back(Chain);
878  Ops.push_back(Callee);
879 
880  // Add argument registers to the end of the list so that they are
881  // known live into the call.
882  for (unsigned i = 0, e = RegsToPass.size(); i != e; ++i) {
883  Ops.push_back(DAG.getRegister(RegsToPass[i].first,
884  RegsToPass[i].second.getValueType()));
885  }
886 
887  const uint32_t *Mask = HRI.getCallPreservedMask(MF, CallConv);
888  assert(Mask && "Missing call preserved mask for calling convention");
889  Ops.push_back(DAG.getRegisterMask(Mask));
890 
891  if (Glue.getNode())
892  Ops.push_back(Glue);
893 
894  if (IsTailCall) {
895  MFI.setHasTailCall();
896  return DAG.getNode(HexagonISD::TC_RETURN, dl, NodeTys, Ops);
897  }
898 
899  // Set this here because we need to know this for "hasFP" in frame lowering.
900  // The target-independent code calls getFrameRegister before setting it, and
901  // getFrameRegister uses hasFP to determine whether the function has FP.
902  MFI.setHasCalls(true);
903 
904  unsigned OpCode = DoesNotReturn ? HexagonISD::CALLnr : HexagonISD::CALL;
905  Chain = DAG.getNode(OpCode, dl, NodeTys, Ops);
906  Glue = Chain.getValue(1);
907 
908  // Create the CALLSEQ_END node.
909  Chain = DAG.getCALLSEQ_END(Chain, DAG.getIntPtrConstant(NumBytes, dl, true),
910  DAG.getIntPtrConstant(0, dl, true), Glue, dl);
911  Glue = Chain.getValue(1);
912 
913  // Handle result values, copying them out of physregs into vregs that we
914  // return.
915  return LowerCallResult(Chain, Glue, CallConv, IsVarArg, Ins, dl, DAG,
916  InVals, OutVals, Callee);
917 }
918 
919 static bool getIndexedAddressParts(SDNode *Ptr, EVT VT,
921  bool &IsInc, SelectionDAG &DAG) {
922  if (Ptr->getOpcode() != ISD::ADD)
923  return false;
924 
925  auto &HST = static_cast<const HexagonSubtarget&>(DAG.getSubtarget());
926 
927  bool ValidHVX128BType =
928  HST.useHVX128BOps() && (VT == MVT::v32i32 ||
929  VT == MVT::v64i16 || VT == MVT::v128i8);
930  bool ValidHVXType =
931  HST.useHVX64BOps() && (VT == MVT::v16i32 ||
932  VT == MVT::v32i16 || VT == MVT::v64i8);
933 
934  if (ValidHVX128BType || ValidHVXType || VT == MVT::i64 || VT == MVT::i32 ||
935  VT == MVT::i16 || VT == MVT::i8) {
936  IsInc = (Ptr->getOpcode() == ISD::ADD);
937  Base = Ptr->getOperand(0);
938  Offset = Ptr->getOperand(1);
939  // Ensure that Offset is a constant.
940  return isa<ConstantSDNode>(Offset);
941  }
942 
943  return false;
944 }
945 
946 /// getPostIndexedAddressParts - returns true by value, base pointer and
947 /// offset pointer and addressing mode by reference if this node can be
948 /// combined with a load / store to form a post-indexed load / store.
950  SDValue &Base,
951  SDValue &Offset,
953  SelectionDAG &DAG) const
954 {
955  EVT VT;
956 
957  if (LoadSDNode *LD = dyn_cast<LoadSDNode>(N)) {
958  VT = LD->getMemoryVT();
959  } else if (StoreSDNode *ST = dyn_cast<StoreSDNode>(N)) {
960  VT = ST->getMemoryVT();
961  if (ST->getValue().getValueType() == MVT::i64 && ST->isTruncatingStore())
962  return false;
963  } else {
964  return false;
965  }
966 
967  bool IsInc = false;
968  bool isLegal = getIndexedAddressParts(Op, VT, Base, Offset, IsInc, DAG);
969  if (isLegal) {
970  auto &HII = *Subtarget.getInstrInfo();
971  int32_t OffsetVal = cast<ConstantSDNode>(Offset.getNode())->getSExtValue();
972  if (HII.isValidAutoIncImm(VT, OffsetVal)) {
973  AM = IsInc ? ISD::POST_INC : ISD::POST_DEC;
974  return true;
975  }
976  }
977 
978  return false;
979 }
980 
981 SDValue
984  auto &HMFI = *MF.getInfo<HexagonMachineFunctionInfo>();
985  const HexagonRegisterInfo &HRI = *Subtarget.getRegisterInfo();
986  unsigned LR = HRI.getRARegister();
987 
988  if (Op.getOpcode() != ISD::INLINEASM || HMFI.hasClobberLR())
989  return Op;
990 
991  unsigned NumOps = Op.getNumOperands();
992  if (Op.getOperand(NumOps-1).getValueType() == MVT::Glue)
993  --NumOps; // Ignore the flag operand.
994 
995  for (unsigned i = InlineAsm::Op_FirstOperand; i != NumOps;) {
996  unsigned Flags = cast<ConstantSDNode>(Op.getOperand(i))->getZExtValue();
997  unsigned NumVals = InlineAsm::getNumOperandRegisters(Flags);
998  ++i; // Skip the ID value.
999 
1000  switch (InlineAsm::getKind(Flags)) {
1001  default:
1002  llvm_unreachable("Bad flags!");
1004  case InlineAsm::Kind_Imm:
1005  case InlineAsm::Kind_Mem:
1006  i += NumVals;
1007  break;
1011  for (; NumVals; --NumVals, ++i) {
1012  unsigned Reg = cast<RegisterSDNode>(Op.getOperand(i))->getReg();
1013  if (Reg != LR)
1014  continue;
1015  HMFI.setHasClobberLR(true);
1016  return Op;
1017  }
1018  break;
1019  }
1020  }
1021  }
1022 
1023  return Op;
1024 }
1025 
1026 // Need to transform ISD::PREFETCH into something that doesn't inherit
1027 // all of the properties of ISD::PREFETCH, specifically SDNPMayLoad and
1028 // SDNPMayStore.
1030  SelectionDAG &DAG) const {
1031  SDValue Chain = Op.getOperand(0);
1032  SDValue Addr = Op.getOperand(1);
1033  // Lower it to DCFETCH($reg, #0). A "pat" will try to merge the offset in,
1034  // if the "reg" is fed by an "add".
1035  SDLoc DL(Op);
1036  SDValue Zero = DAG.getConstant(0, DL, MVT::i32);
1037  return DAG.getNode(HexagonISD::DCFETCH, DL, MVT::Other, Chain, Addr, Zero);
1038 }
1039 
1040 // Custom-handle ISD::READCYCLECOUNTER because the target-independent SDNode
1041 // is marked as having side-effects, while the register read on Hexagon does
1042 // not have any. TableGen refuses to accept the direct pattern from that node
1043 // to the A4_tfrcpp.
1045  SelectionDAG &DAG) const {
1046  SDValue Chain = Op.getOperand(0);
1047  SDLoc dl(Op);
1048  SDVTList VTs = DAG.getVTList(MVT::i32, MVT::Other);
1049  return DAG.getNode(HexagonISD::READCYCLE, dl, VTs, Chain);
1050 }
1051 
1053  SelectionDAG &DAG) const {
1054  SDValue Chain = Op.getOperand(0);
1055  unsigned IntNo = cast<ConstantSDNode>(Op.getOperand(1))->getZExtValue();
1056  // Lower the hexagon_prefetch builtin to DCFETCH, as above.
1057  if (IntNo == Intrinsic::hexagon_prefetch) {
1058  SDValue Addr = Op.getOperand(2);
1059  SDLoc DL(Op);
1060  SDValue Zero = DAG.getConstant(0, DL, MVT::i32);
1061  return DAG.getNode(HexagonISD::DCFETCH, DL, MVT::Other, Chain, Addr, Zero);
1062  }
1063  return SDValue();
1064 }
1065 
1066 SDValue
1068  SelectionDAG &DAG) const {
1069  SDValue Chain = Op.getOperand(0);
1070  SDValue Size = Op.getOperand(1);
1071  SDValue Align = Op.getOperand(2);
1072  SDLoc dl(Op);
1073 
1074  ConstantSDNode *AlignConst = dyn_cast<ConstantSDNode>(Align);
1075  assert(AlignConst && "Non-constant Align in LowerDYNAMIC_STACKALLOC");
1076 
1077  unsigned A = AlignConst->getSExtValue();
1078  auto &HFI = *Subtarget.getFrameLowering();
1079  // "Zero" means natural stack alignment.
1080  if (A == 0)
1081  A = HFI.getStackAlignment();
1082 
1083  DEBUG({
1084  dbgs () << __func__ << " Align: " << A << " Size: ";
1085  Size.getNode()->dump(&DAG);
1086  dbgs() << "\n";
1087  });
1088 
1089  SDValue AC = DAG.getConstant(A, dl, MVT::i32);
1090  SDVTList VTs = DAG.getVTList(MVT::i32, MVT::Other);
1091  SDValue AA = DAG.getNode(HexagonISD::ALLOCA, dl, VTs, Chain, Size, AC);
1092 
1093  DAG.ReplaceAllUsesOfValueWith(Op, AA);
1094  return AA;
1095 }
1096 
1098  SDValue Chain, CallingConv::ID CallConv, bool isVarArg,
1099  const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &dl,
1100  SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const {
1101  MachineFunction &MF = DAG.getMachineFunction();
1102  MachineFrameInfo &MFI = MF.getFrameInfo();
1103  MachineRegisterInfo &RegInfo = MF.getRegInfo();
1104  auto &FuncInfo = *MF.getInfo<HexagonMachineFunctionInfo>();
1105 
1106  // Assign locations to all of the incoming arguments.
1108  CCState CCInfo(CallConv, isVarArg, DAG.getMachineFunction(), ArgLocs,
1109  *DAG.getContext());
1110 
1111  CCInfo.AnalyzeFormalArguments(Ins, CC_Hexagon);
1112 
1113  // For LLVM, in the case when returning a struct by value (>8byte),
1114  // the first argument is a pointer that points to the location on caller's
1115  // stack where the return value will be stored. For Hexagon, the location on
1116  // caller's stack is passed only when the struct size is smaller than (and
1117  // equal to) 8 bytes. If not, no address will be passed into callee and
1118  // callee return the result direclty through R0/R1.
1119 
1120  SmallVector<SDValue, 8> MemOps;
1121 
1122  for (unsigned i = 0, e = ArgLocs.size(); i != e; ++i) {
1123  CCValAssign &VA = ArgLocs[i];
1124  ISD::ArgFlagsTy Flags = Ins[i].Flags;
1125  unsigned ObjSize;
1126  unsigned StackLocation;
1127  int FI;
1128 
1129  if ( (VA.isRegLoc() && !Flags.isByVal())
1130  || (VA.isRegLoc() && Flags.isByVal() && Flags.getByValSize() > 8)) {
1131  // Arguments passed in registers
1132  // 1. int, long long, ptr args that get allocated in register.
1133  // 2. Large struct that gets an register to put its address in.
1134  EVT RegVT = VA.getLocVT();
1135  if (RegVT == MVT::i8 || RegVT == MVT::i16 ||
1136  RegVT == MVT::i32 || RegVT == MVT::f32) {
1137  unsigned VReg =
1138  RegInfo.createVirtualRegister(&Hexagon::IntRegsRegClass);
1139  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1140  if (VA.getLocInfo() == CCValAssign::BCvt)
1141  RegVT = VA.getValVT();
1142  SDValue Copy = DAG.getCopyFromReg(Chain, dl, VReg, RegVT);
1143  // Treat values of type MVT::i1 specially: they are passed in
1144  // registers of type i32, but they need to remain as values of
1145  // type i1 for consistency of the argument lowering.
1146  if (VA.getValVT() == MVT::i1) {
1147  // Generate a copy into a predicate register and use the value
1148  // of the register as the "InVal".
1149  unsigned PReg =
1150  RegInfo.createVirtualRegister(&Hexagon::PredRegsRegClass);
1151  SDNode *T = DAG.getMachineNode(Hexagon::C2_tfrrp, dl, MVT::i1,
1152  Copy.getValue(0));
1153  Copy = DAG.getCopyToReg(Copy.getValue(1), dl, PReg, SDValue(T, 0));
1154  Copy = DAG.getCopyFromReg(Copy, dl, PReg, MVT::i1);
1155  }
1156  InVals.push_back(Copy);
1157  Chain = Copy.getValue(1);
1158  } else if (RegVT == MVT::i64 || RegVT == MVT::f64) {
1159  unsigned VReg =
1160  RegInfo.createVirtualRegister(&Hexagon::DoubleRegsRegClass);
1161  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1162  if (VA.getLocInfo() == CCValAssign::BCvt)
1163  RegVT = VA.getValVT();
1164  InVals.push_back(DAG.getCopyFromReg(Chain, dl, VReg, RegVT));
1165 
1166  // Single Vector
1167  } else if ((RegVT == MVT::v16i32 ||
1168  RegVT == MVT::v32i16 || RegVT == MVT::v64i8)) {
1169  unsigned VReg =
1170  RegInfo.createVirtualRegister(&Hexagon::HvxVRRegClass);
1171  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1172  InVals.push_back(DAG.getCopyFromReg(Chain, dl, VReg, RegVT));
1173  } else if (Subtarget.useHVX128BOps() &&
1174  ((RegVT == MVT::v32i32 ||
1175  RegVT == MVT::v64i16 || RegVT == MVT::v128i8))) {
1176  unsigned VReg =
1177  RegInfo.createVirtualRegister(&Hexagon::HvxVRRegClass);
1178  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1179  InVals.push_back(DAG.getCopyFromReg(Chain, dl, VReg, RegVT));
1180 
1181  // Double Vector
1182  } else if ((RegVT == MVT::v32i32 ||
1183  RegVT == MVT::v64i16 || RegVT == MVT::v128i8)) {
1184  unsigned VReg =
1185  RegInfo.createVirtualRegister(&Hexagon::HvxWRRegClass);
1186  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1187  InVals.push_back(DAG.getCopyFromReg(Chain, dl, VReg, RegVT));
1188  } else if (Subtarget.useHVX128BOps() &&
1189  ((RegVT == MVT::v64i32 ||
1190  RegVT == MVT::v128i16 || RegVT == MVT::v256i8))) {
1191  unsigned VReg =
1192  RegInfo.createVirtualRegister(&Hexagon::HvxWRRegClass);
1193  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1194  InVals.push_back(DAG.getCopyFromReg(Chain, dl, VReg, RegVT));
1195  } else if (RegVT == MVT::v512i1 || RegVT == MVT::v1024i1) {
1196  assert(0 && "need to support VecPred regs");
1197  unsigned VReg =
1198  RegInfo.createVirtualRegister(&Hexagon::HvxQRRegClass);
1199  RegInfo.addLiveIn(VA.getLocReg(), VReg);
1200  InVals.push_back(DAG.getCopyFromReg(Chain, dl, VReg, RegVT));
1201  } else {
1202  assert (0);
1203  }
1204  } else if (VA.isRegLoc() && Flags.isByVal() && Flags.getByValSize() <= 8) {
1205  assert (0 && "ByValSize must be bigger than 8 bytes");
1206  } else {
1207  // Sanity check.
1208  assert(VA.isMemLoc());
1209 
1210  if (Flags.isByVal()) {
1211  // If it's a byval parameter, then we need to compute the
1212  // "real" size, not the size of the pointer.
1213  ObjSize = Flags.getByValSize();
1214  } else {
1215  ObjSize = VA.getLocVT().getStoreSizeInBits() >> 3;
1216  }
1217 
1218  StackLocation = HEXAGON_LRFP_SIZE + VA.getLocMemOffset();
1219  // Create the frame index object for this incoming parameter...
1220  FI = MFI.CreateFixedObject(ObjSize, StackLocation, true);
1221 
1222  // Create the SelectionDAG nodes cordl, responding to a load
1223  // from this parameter.
1224  SDValue FIN = DAG.getFrameIndex(FI, MVT::i32);
1225 
1226  if (Flags.isByVal()) {
1227  // If it's a pass-by-value aggregate, then do not dereference the stack
1228  // location. Instead, we should generate a reference to the stack
1229  // location.
1230  InVals.push_back(FIN);
1231  } else {
1232  InVals.push_back(
1233  DAG.getLoad(VA.getValVT(), dl, Chain, FIN, MachinePointerInfo()));
1234  }
1235  }
1236  }
1237 
1238  if (!MemOps.empty())
1239  Chain = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, MemOps);
1240 
1241  if (isVarArg) {
1242  // This will point to the next argument passed via stack.
1245  CCInfo.getNextStackOffset(),
1246  true);
1247  FuncInfo.setVarArgsFrameIndex(FrameIndex);
1248  }
1249 
1250  return Chain;
1251 }
1252 
1253 SDValue
1255  // VASTART stores the address of the VarArgsFrameIndex slot into the
1256  // memory location argument.
1257  MachineFunction &MF = DAG.getMachineFunction();
1259  SDValue Addr = DAG.getFrameIndex(QFI->getVarArgsFrameIndex(), MVT::i32);
1260  const Value *SV = cast<SrcValueSDNode>(Op.getOperand(2))->getValue();
1261  return DAG.getStore(Op.getOperand(0), SDLoc(Op), Addr, Op.getOperand(1),
1262  MachinePointerInfo(SV));
1263 }
1264 
1265 static bool isSExtFree(SDValue N) {
1266  // A sign-extend of a truncate of a sign-extend is free.
1267  if (N.getOpcode() == ISD::TRUNCATE &&
1269  return true;
1270  // We have sign-extended loads.
1271  if (N.getOpcode() == ISD::LOAD)
1272  return true;
1273  return false;
1274 }
1275 
1277  SDLoc dl(Op);
1278 
1279  SDValue LHS = Op.getOperand(0);
1280  SDValue RHS = Op.getOperand(1);
1281  if (Subtarget.useHVXOps() && Subtarget.isHVXVectorType(ty(LHS)))
1282  return LowerHvxSetCC(Op, DAG);
1283 
1284  SDValue Cmp = Op.getOperand(2);
1285  ISD::CondCode CC = cast<CondCodeSDNode>(Cmp)->get();
1286 
1287  EVT VT = Op.getValueType();
1288  EVT LHSVT = LHS.getValueType();
1289  EVT RHSVT = RHS.getValueType();
1290 
1291  if (LHSVT == MVT::v2i16) {
1293  unsigned ExtOpc = ISD::isSignedIntSetCC(CC) ? ISD::SIGN_EXTEND
1294  : ISD::ZERO_EXTEND;
1295  SDValue LX = DAG.getNode(ExtOpc, dl, MVT::v2i32, LHS);
1296  SDValue RX = DAG.getNode(ExtOpc, dl, MVT::v2i32, RHS);
1297  SDValue SC = DAG.getNode(ISD::SETCC, dl, MVT::v2i1, LX, RX, Cmp);
1298  return SC;
1299  }
1300 
1301  // Treat all other vector types as legal.
1302  if (VT.isVector())
1303  return Op;
1304 
1305  // Equals and not equals should use sign-extend, not zero-extend, since
1306  // we can represent small negative values in the compare instructions.
1307  // The LLVM default is to use zero-extend arbitrarily in these cases.
1308  if ((CC == ISD::SETEQ || CC == ISD::SETNE) &&
1309  (RHSVT == MVT::i8 || RHSVT == MVT::i16) &&
1310  (LHSVT == MVT::i8 || LHSVT == MVT::i16)) {
1312  if (C && C->getAPIntValue().isNegative()) {
1313  LHS = DAG.getNode(ISD::SIGN_EXTEND, dl, MVT::i32, LHS);
1314  RHS = DAG.getNode(ISD::SIGN_EXTEND, dl, MVT::i32, RHS);
1315  return DAG.getNode(ISD::SETCC, dl, Op.getValueType(),
1316  LHS, RHS, Op.getOperand(2));
1317  }
1318  if (isSExtFree(LHS) || isSExtFree(RHS)) {
1319  LHS = DAG.getNode(ISD::SIGN_EXTEND, dl, MVT::i32, LHS);
1320  RHS = DAG.getNode(ISD::SIGN_EXTEND, dl, MVT::i32, RHS);
1321  return DAG.getNode(ISD::SETCC, dl, Op.getValueType(),
1322  LHS, RHS, Op.getOperand(2));
1323  }
1324  }
1325  return SDValue();
1326 }
1327 
1328 SDValue
1330  SDValue PredOp = Op.getOperand(0);
1331  SDValue Op1 = Op.getOperand(1), Op2 = Op.getOperand(2);
1332  EVT OpVT = Op1.getValueType();
1333  SDLoc DL(Op);
1334 
1335  if (OpVT == MVT::v2i16) {
1336  SDValue X1 = DAG.getNode(ISD::ZERO_EXTEND, DL, MVT::v2i32, Op1);
1337  SDValue X2 = DAG.getNode(ISD::ZERO_EXTEND, DL, MVT::v2i32, Op2);
1338  SDValue SL = DAG.getNode(ISD::VSELECT, DL, MVT::v2i32, PredOp, X1, X2);
1339  SDValue TR = DAG.getNode(ISD::TRUNCATE, DL, MVT::v2i16, SL);
1340  return TR;
1341  }
1342 
1343  return SDValue();
1344 }
1345 
1346 static Constant *convert_i1_to_i8(const Constant *ConstVal) {
1348  const ConstantVector *CV = dyn_cast<ConstantVector>(ConstVal);
1349  if (!CV)
1350  return nullptr;
1351 
1352  LLVMContext &Ctx = ConstVal->getContext();
1353  IRBuilder<> IRB(Ctx);
1354  unsigned NumVectorElements = CV->getNumOperands();
1355  assert(isPowerOf2_32(NumVectorElements) &&
1356  "conversion only supported for pow2 VectorSize!");
1357 
1358  for (unsigned i = 0; i < NumVectorElements / 8; ++i) {
1359  uint8_t x = 0;
1360  for (unsigned j = 0; j < 8; ++j) {
1361  uint8_t y = CV->getOperand(i * 8 + j)->getUniqueInteger().getZExtValue();
1362  x |= y << (7 - j);
1363  }
1364  assert((x == 0 || x == 255) && "Either all 0's or all 1's expected!");
1365  NewConst.push_back(IRB.getInt8(x));
1366  }
1367  return ConstantVector::get(NewConst);
1368 }
1369 
1370 SDValue
1372  EVT ValTy = Op.getValueType();
1373  ConstantPoolSDNode *CPN = cast<ConstantPoolSDNode>(Op);
1374  Constant *CVal = nullptr;
1375  bool isVTi1Type = false;
1376  if (const Constant *ConstVal = dyn_cast<Constant>(CPN->getConstVal())) {
1377  Type *CValTy = ConstVal->getType();
1378  if (CValTy->isVectorTy() &&
1379  CValTy->getVectorElementType()->isIntegerTy(1)) {
1380  CVal = convert_i1_to_i8(ConstVal);
1381  isVTi1Type = (CVal != nullptr);
1382  }
1383  }
1384  unsigned Align = CPN->getAlignment();
1385  bool IsPositionIndependent = isPositionIndependent();
1386  unsigned char TF = IsPositionIndependent ? HexagonII::MO_PCREL : 0;
1387 
1388  unsigned Offset = 0;
1389  SDValue T;
1390  if (CPN->isMachineConstantPoolEntry())
1391  T = DAG.getTargetConstantPool(CPN->getMachineCPVal(), ValTy, Align, Offset,
1392  TF);
1393  else if (isVTi1Type)
1394  T = DAG.getTargetConstantPool(CVal, ValTy, Align, Offset, TF);
1395  else
1396  T = DAG.getTargetConstantPool(CPN->getConstVal(), ValTy, Align, Offset,
1397  TF);
1398 
1399  assert(cast<ConstantPoolSDNode>(T)->getTargetFlags() == TF &&
1400  "Inconsistent target flag encountered");
1401 
1402  if (IsPositionIndependent)
1403  return DAG.getNode(HexagonISD::AT_PCREL, SDLoc(Op), ValTy, T);
1404  return DAG.getNode(HexagonISD::CP, SDLoc(Op), ValTy, T);
1405 }
1406 
1407 SDValue
1409  EVT VT = Op.getValueType();
1410  int Idx = cast<JumpTableSDNode>(Op)->getIndex();
1411  if (isPositionIndependent()) {
1413  return DAG.getNode(HexagonISD::AT_PCREL, SDLoc(Op), VT, T);
1414  }
1415 
1416  SDValue T = DAG.getTargetJumpTable(Idx, VT);
1417  return DAG.getNode(HexagonISD::JT, SDLoc(Op), VT, T);
1418 }
1419 
1420 SDValue
1422  const HexagonRegisterInfo &HRI = *Subtarget.getRegisterInfo();
1423  MachineFunction &MF = DAG.getMachineFunction();
1424  MachineFrameInfo &MFI = MF.getFrameInfo();
1425  MFI.setReturnAddressIsTaken(true);
1426 
1427  if (verifyReturnAddressArgumentIsConstant(Op, DAG))
1428  return SDValue();
1429 
1430  EVT VT = Op.getValueType();
1431  SDLoc dl(Op);
1432  unsigned Depth = cast<ConstantSDNode>(Op.getOperand(0))->getZExtValue();
1433  if (Depth) {
1434  SDValue FrameAddr = LowerFRAMEADDR(Op, DAG);
1435  SDValue Offset = DAG.getConstant(4, dl, MVT::i32);
1436  return DAG.getLoad(VT, dl, DAG.getEntryNode(),
1437  DAG.getNode(ISD::ADD, dl, VT, FrameAddr, Offset),
1438  MachinePointerInfo());
1439  }
1440 
1441  // Return LR, which contains the return address. Mark it an implicit live-in.
1442  unsigned Reg = MF.addLiveIn(HRI.getRARegister(), getRegClassFor(MVT::i32));
1443  return DAG.getCopyFromReg(DAG.getEntryNode(), dl, Reg, VT);
1444 }
1445 
1446 SDValue
1448  const HexagonRegisterInfo &HRI = *Subtarget.getRegisterInfo();
1450  MFI.setFrameAddressIsTaken(true);
1451 
1452  EVT VT = Op.getValueType();
1453  SDLoc dl(Op);
1454  unsigned Depth = cast<ConstantSDNode>(Op.getOperand(0))->getZExtValue();
1455  SDValue FrameAddr = DAG.getCopyFromReg(DAG.getEntryNode(), dl,
1456  HRI.getFrameRegister(), VT);
1457  while (Depth--)
1458  FrameAddr = DAG.getLoad(VT, dl, DAG.getEntryNode(), FrameAddr,
1459  MachinePointerInfo());
1460  return FrameAddr;
1461 }
1462 
1463 SDValue
1465  SDLoc dl(Op);
1466  return DAG.getNode(HexagonISD::BARRIER, dl, MVT::Other, Op.getOperand(0));
1467 }
1468 
1469 SDValue
1471  SDLoc dl(Op);
1472  auto *GAN = cast<GlobalAddressSDNode>(Op);
1473  auto PtrVT = getPointerTy(DAG.getDataLayout());
1474  auto *GV = GAN->getGlobal();
1475  int64_t Offset = GAN->getOffset();
1476 
1477  auto &HLOF = *HTM.getObjFileLowering();
1478  Reloc::Model RM = HTM.getRelocationModel();
1479 
1480  if (RM == Reloc::Static) {
1481  SDValue GA = DAG.getTargetGlobalAddress(GV, dl, PtrVT, Offset);
1482  const GlobalObject *GO = GV->getBaseObject();
1483  if (GO && HLOF.isGlobalInSmallSection(GO, HTM))
1484  return DAG.getNode(HexagonISD::CONST32_GP, dl, PtrVT, GA);
1485  return DAG.getNode(HexagonISD::CONST32, dl, PtrVT, GA);
1486  }
1487 
1488  bool UsePCRel = getTargetMachine().shouldAssumeDSOLocal(*GV->getParent(), GV);
1489  if (UsePCRel) {
1490  SDValue GA = DAG.getTargetGlobalAddress(GV, dl, PtrVT, Offset,
1492  return DAG.getNode(HexagonISD::AT_PCREL, dl, PtrVT, GA);
1493  }
1494 
1495  // Use GOT index.
1496  SDValue GOT = DAG.getGLOBAL_OFFSET_TABLE(PtrVT);
1497  SDValue GA = DAG.getTargetGlobalAddress(GV, dl, PtrVT, 0, HexagonII::MO_GOT);
1498  SDValue Off = DAG.getConstant(Offset, dl, MVT::i32);
1499  return DAG.getNode(HexagonISD::AT_GOT, dl, PtrVT, GOT, GA, Off);
1500 }
1501 
1502 // Specifies that for loads and stores VT can be promoted to PromotedLdStVT.
1503 SDValue
1505  const BlockAddress *BA = cast<BlockAddressSDNode>(Op)->getBlockAddress();
1506  SDLoc dl(Op);
1507  EVT PtrVT = getPointerTy(DAG.getDataLayout());
1508 
1509  Reloc::Model RM = HTM.getRelocationModel();
1510  if (RM == Reloc::Static) {
1511  SDValue A = DAG.getTargetBlockAddress(BA, PtrVT);
1512  return DAG.getNode(HexagonISD::CONST32_GP, dl, PtrVT, A);
1513  }
1514 
1515  SDValue A = DAG.getTargetBlockAddress(BA, PtrVT, 0, HexagonII::MO_PCREL);
1516  return DAG.getNode(HexagonISD::AT_PCREL, dl, PtrVT, A);
1517 }
1518 
1519 SDValue
1521  const {
1522  EVT PtrVT = getPointerTy(DAG.getDataLayout());
1525  return DAG.getNode(HexagonISD::AT_PCREL, SDLoc(Op), PtrVT, GOTSym);
1526 }
1527 
1528 SDValue
1530  GlobalAddressSDNode *GA, SDValue Glue, EVT PtrVT, unsigned ReturnReg,
1531  unsigned char OperandFlags) const {
1532  MachineFunction &MF = DAG.getMachineFunction();
1533  MachineFrameInfo &MFI = MF.getFrameInfo();
1534  SDVTList NodeTys = DAG.getVTList(MVT::Other, MVT::Glue);
1535  SDLoc dl(GA);
1536  SDValue TGA = DAG.getTargetGlobalAddress(GA->getGlobal(), dl,
1537  GA->getValueType(0),
1538  GA->getOffset(),
1539  OperandFlags);
1540  // Create Operands for the call.The Operands should have the following:
1541  // 1. Chain SDValue
1542  // 2. Callee which in this case is the Global address value.
1543  // 3. Registers live into the call.In this case its R0, as we
1544  // have just one argument to be passed.
1545  // 4. Glue.
1546  // Note: The order is important.
1547 
1548  const auto &HRI = *Subtarget.getRegisterInfo();
1549  const uint32_t *Mask = HRI.getCallPreservedMask(MF, CallingConv::C);
1550  assert(Mask && "Missing call preserved mask for calling convention");
1551  SDValue Ops[] = { Chain, TGA, DAG.getRegister(Hexagon::R0, PtrVT),
1552  DAG.getRegisterMask(Mask), Glue };
1553  Chain = DAG.getNode(HexagonISD::CALL, dl, NodeTys, Ops);
1554 
1555  // Inform MFI that function has calls.
1556  MFI.setAdjustsStack(true);
1557 
1558  Glue = Chain.getValue(1);
1559  return DAG.getCopyFromReg(Chain, dl, ReturnReg, PtrVT, Glue);
1560 }
1561 
1562 //
1563 // Lower using the intial executable model for TLS addresses
1564 //
1565 SDValue
1567  SelectionDAG &DAG) const {
1568  SDLoc dl(GA);
1569  int64_t Offset = GA->getOffset();
1570  auto PtrVT = getPointerTy(DAG.getDataLayout());
1571 
1572  // Get the thread pointer.
1573  SDValue TP = DAG.getCopyFromReg(DAG.getEntryNode(), dl, Hexagon::UGP, PtrVT);
1574 
1575  bool IsPositionIndependent = isPositionIndependent();
1576  unsigned char TF =
1577  IsPositionIndependent ? HexagonII::MO_IEGOT : HexagonII::MO_IE;
1578 
1579  // First generate the TLS symbol address
1580  SDValue TGA = DAG.getTargetGlobalAddress(GA->getGlobal(), dl, PtrVT,
1581  Offset, TF);
1582 
1583  SDValue Sym = DAG.getNode(HexagonISD::CONST32, dl, PtrVT, TGA);
1584 
1585  if (IsPositionIndependent) {
1586  // Generate the GOT pointer in case of position independent code
1587  SDValue GOT = LowerGLOBAL_OFFSET_TABLE(Sym, DAG);
1588 
1589  // Add the TLS Symbol address to GOT pointer.This gives
1590  // GOT relative relocation for the symbol.
1591  Sym = DAG.getNode(ISD::ADD, dl, PtrVT, GOT, Sym);
1592  }
1593 
1594  // Load the offset value for TLS symbol.This offset is relative to
1595  // thread pointer.
1596  SDValue LoadOffset =
1597  DAG.getLoad(PtrVT, dl, DAG.getEntryNode(), Sym, MachinePointerInfo());
1598 
1599  // Address of the thread local variable is the add of thread
1600  // pointer and the offset of the variable.
1601  return DAG.getNode(ISD::ADD, dl, PtrVT, TP, LoadOffset);
1602 }
1603 
1604 //
1605 // Lower using the local executable model for TLS addresses
1606 //
1607 SDValue
1609  SelectionDAG &DAG) const {
1610  SDLoc dl(GA);
1611  int64_t Offset = GA->getOffset();
1612  auto PtrVT = getPointerTy(DAG.getDataLayout());
1613 
1614  // Get the thread pointer.
1615  SDValue TP = DAG.getCopyFromReg(DAG.getEntryNode(), dl, Hexagon::UGP, PtrVT);
1616  // Generate the TLS symbol address
1617  SDValue TGA = DAG.getTargetGlobalAddress(GA->getGlobal(), dl, PtrVT, Offset,
1619  SDValue Sym = DAG.getNode(HexagonISD::CONST32, dl, PtrVT, TGA);
1620 
1621  // Address of the thread local variable is the add of thread
1622  // pointer and the offset of the variable.
1623  return DAG.getNode(ISD::ADD, dl, PtrVT, TP, Sym);
1624 }
1625 
1626 //
1627 // Lower using the general dynamic model for TLS addresses
1628 //
1629 SDValue
1631  SelectionDAG &DAG) const {
1632  SDLoc dl(GA);
1633  int64_t Offset = GA->getOffset();
1634  auto PtrVT = getPointerTy(DAG.getDataLayout());
1635 
1636  // First generate the TLS symbol address
1637  SDValue TGA = DAG.getTargetGlobalAddress(GA->getGlobal(), dl, PtrVT, Offset,
1639 
1640  // Then, generate the GOT pointer
1641  SDValue GOT = LowerGLOBAL_OFFSET_TABLE(TGA, DAG);
1642 
1643  // Add the TLS symbol and the GOT pointer
1644  SDValue Sym = DAG.getNode(HexagonISD::CONST32, dl, PtrVT, TGA);
1645  SDValue Chain = DAG.getNode(ISD::ADD, dl, PtrVT, GOT, Sym);
1646 
1647  // Copy over the argument to R0
1648  SDValue InFlag;
1649  Chain = DAG.getCopyToReg(DAG.getEntryNode(), dl, Hexagon::R0, Chain, InFlag);
1650  InFlag = Chain.getValue(1);
1651 
1652  unsigned Flags =
1653  static_cast<const HexagonSubtarget &>(DAG.getSubtarget()).useLongCalls()
1656 
1657  return GetDynamicTLSAddr(DAG, Chain, GA, InFlag, PtrVT,
1658  Hexagon::R0, Flags);
1659 }
1660 
1661 //
1662 // Lower TLS addresses.
1663 //
1664 // For now for dynamic models, we only support the general dynamic model.
1665 //
1666 SDValue
1668  SelectionDAG &DAG) const {
1669  GlobalAddressSDNode *GA = cast<GlobalAddressSDNode>(Op);
1670 
1671  switch (HTM.getTLSModel(GA->getGlobal())) {
1674  return LowerToTLSGeneralDynamicModel(GA, DAG);
1675  case TLSModel::InitialExec:
1676  return LowerToTLSInitialExecModel(GA, DAG);
1677  case TLSModel::LocalExec:
1678  return LowerToTLSLocalExecModel(GA, DAG);
1679  }
1680  llvm_unreachable("Bogus TLS model");
1681 }
1682 
1683 //===----------------------------------------------------------------------===//
1684 // TargetLowering Implementation
1685 //===----------------------------------------------------------------------===//
1686 
1688  const HexagonSubtarget &ST)
1689  : TargetLowering(TM), HTM(static_cast<const HexagonTargetMachine&>(TM)),
1690  Subtarget(ST) {
1691  bool IsV4 = !Subtarget.hasV5TOps();
1692  auto &HRI = *Subtarget.getRegisterInfo();
1693 
1697  setStackPointerRegisterToSaveRestore(HRI.getStackRegister());
1700 
1703 
1706  else
1708 
1709  // Limits for inline expansion of memcpy/memmove
1716 
1717  //
1718  // Set up register classes.
1719  //
1720 
1721  addRegisterClass(MVT::i1, &Hexagon::PredRegsRegClass);
1722  addRegisterClass(MVT::v2i1, &Hexagon::PredRegsRegClass); // bbbbaaaa
1723  addRegisterClass(MVT::v4i1, &Hexagon::PredRegsRegClass); // ddccbbaa
1724  addRegisterClass(MVT::v8i1, &Hexagon::PredRegsRegClass); // hgfedcba
1725  addRegisterClass(MVT::i32, &Hexagon::IntRegsRegClass);
1726  addRegisterClass(MVT::v2i16, &Hexagon::IntRegsRegClass);
1727  addRegisterClass(MVT::v4i8, &Hexagon::IntRegsRegClass);
1728  addRegisterClass(MVT::i64, &Hexagon::DoubleRegsRegClass);
1729  addRegisterClass(MVT::v8i8, &Hexagon::DoubleRegsRegClass);
1730  addRegisterClass(MVT::v4i16, &Hexagon::DoubleRegsRegClass);
1731  addRegisterClass(MVT::v2i32, &Hexagon::DoubleRegsRegClass);
1732 
1733  if (Subtarget.hasV5TOps()) {
1734  addRegisterClass(MVT::f32, &Hexagon::IntRegsRegClass);
1735  addRegisterClass(MVT::f64, &Hexagon::DoubleRegsRegClass);
1736  }
1737 
1738  if (Subtarget.hasV60TOps()) {
1739  if (Subtarget.useHVX64BOps()) {
1740  addRegisterClass(MVT::v64i8, &Hexagon::HvxVRRegClass);
1741  addRegisterClass(MVT::v32i16, &Hexagon::HvxVRRegClass);
1742  addRegisterClass(MVT::v16i32, &Hexagon::HvxVRRegClass);
1743  addRegisterClass(MVT::v128i8, &Hexagon::HvxWRRegClass);
1744  addRegisterClass(MVT::v64i16, &Hexagon::HvxWRRegClass);
1745  addRegisterClass(MVT::v32i32, &Hexagon::HvxWRRegClass);
1746  // These "short" boolean vector types should be legal because
1747  // they will appear as results of vector compares. If they were
1748  // not legal, type legalization would try to make them legal
1749  // and that would require using operations that do not use or
1750  // produce such types. That, in turn, would imply using custom
1751  // nodes, which would be unoptimizable by the DAG combiner.
1752  // The idea is to rely on target-independent operations as much
1753  // as possible.
1754  addRegisterClass(MVT::v16i1, &Hexagon::HvxQRRegClass);
1755  addRegisterClass(MVT::v32i1, &Hexagon::HvxQRRegClass);
1756  addRegisterClass(MVT::v64i1, &Hexagon::HvxQRRegClass);
1757  addRegisterClass(MVT::v512i1, &Hexagon::HvxQRRegClass);
1758  } else if (Subtarget.useHVX128BOps()) {
1759  addRegisterClass(MVT::v128i8, &Hexagon::HvxVRRegClass);
1760  addRegisterClass(MVT::v64i16, &Hexagon::HvxVRRegClass);
1761  addRegisterClass(MVT::v32i32, &Hexagon::HvxVRRegClass);
1762  addRegisterClass(MVT::v256i8, &Hexagon::HvxWRRegClass);
1763  addRegisterClass(MVT::v128i16, &Hexagon::HvxWRRegClass);
1764  addRegisterClass(MVT::v64i32, &Hexagon::HvxWRRegClass);
1765  addRegisterClass(MVT::v32i1, &Hexagon::HvxQRRegClass);
1766  addRegisterClass(MVT::v64i1, &Hexagon::HvxQRRegClass);
1767  addRegisterClass(MVT::v128i1, &Hexagon::HvxQRRegClass);
1768  addRegisterClass(MVT::v1024i1, &Hexagon::HvxQRRegClass);
1769  }
1770  }
1771 
1772  //
1773  // Handling of scalar operations.
1774  //
1775  // All operations default to "legal", except:
1776  // - indexed loads and stores (pre-/post-incremented),
1777  // - ANY_EXTEND_VECTOR_INREG, ATOMIC_CMP_SWAP_WITH_SUCCESS, CONCAT_VECTORS,
1778  // ConstantFP, DEBUGTRAP, FCEIL, FCOPYSIGN, FEXP, FEXP2, FFLOOR, FGETSIGN,
1779  // FLOG, FLOG2, FLOG10, FMAXNUM, FMINNUM, FNEARBYINT, FRINT, FROUND, TRAP,
1780  // FTRUNC, PREFETCH, SIGN_EXTEND_VECTOR_INREG, ZERO_EXTEND_VECTOR_INREG,
1781  // which default to "expand" for at least one type.
1782 
1783  // Misc operations.
1784  setOperationAction(ISD::ConstantFP, MVT::f32, Legal); // Default: expand
1785  setOperationAction(ISD::ConstantFP, MVT::f64, Legal); // Default: expand
1786 
1799 
1800  // Custom legalize GlobalAddress nodes into CONST32.
1804 
1805  // Hexagon needs to optimize cases with negative constants.
1808 
1809  // VASTART needs to be custom lowered to use the VarArgsFrameIndex.
1813 
1817 
1818  if (EmitJumpTables)
1820  else
1823 
1824  // Hexagon has instructions for add/sub with carry. The problem with
1825  // modeling these instructions is that they produce 2 results: Rdd and Px.
1826  // To model the update of Px, we will have to use Defs[p0..p3] which will
1827  // cause any predicate live range to spill. So, we pretend we dont't have
1828  // these instructions.
1845 
1846  // Only add and sub that detect overflow are the saturating ones.
1847  for (MVT VT : MVT::integer_valuetypes()) {
1852  }
1853 
1858 
1859  // In V5, popcount can count # of 1s in i64 but returns i32.
1860  // On V4 it will be expanded (set later).
1865 
1871 
1872  for (unsigned IntExpOp :
1877  setOperationAction(IntExpOp, MVT::i32, Expand);
1878  setOperationAction(IntExpOp, MVT::i64, Expand);
1879  }
1880 
1881  for (unsigned FPExpOp :
1884  setOperationAction(FPExpOp, MVT::f32, Expand);
1885  setOperationAction(FPExpOp, MVT::f64, Expand);
1886  }
1887 
1888  // No extending loads from i32.
1889  for (MVT VT : MVT::integer_valuetypes()) {
1893  }
1894  // Turn FP truncstore into trunc + store.
1896  // Turn FP extload into load/fpextend.
1897  for (MVT VT : MVT::fp_valuetypes())
1899 
1900  // Expand BR_CC and SELECT_CC for all integer and fp types.
1901  for (MVT VT : MVT::integer_valuetypes()) {
1904  }
1905  for (MVT VT : MVT::fp_valuetypes()) {
1908  }
1910 
1911  //
1912  // Handling of vector operations.
1913  //
1914 
1915  promoteLdStType(MVT::v4i8, MVT::i32);
1916  promoteLdStType(MVT::v2i16, MVT::i32);
1917  promoteLdStType(MVT::v8i8, MVT::i64);
1918  promoteLdStType(MVT::v4i16, MVT::i64);
1919  promoteLdStType(MVT::v2i32, MVT::i64);
1920 
1921  // Set the action for vector operations to "expand", then override it with
1922  // either "custom" or "legal" for specific cases.
1923  static const unsigned VectExpOps[] = {
1924  // Integer arithmetic:
1929  // Logical/bit:
1932  // Floating point arithmetic/math functions:
1939  // Misc:
1941  // Vector:
1946  };
1947 
1948  for (MVT VT : MVT::vector_valuetypes()) {
1949  for (unsigned VectExpOp : VectExpOps)
1950  setOperationAction(VectExpOp, VT, Expand);
1951 
1952  // Expand all extending loads and truncating stores:
1953  for (MVT TargetVT : MVT::vector_valuetypes()) {
1954  if (TargetVT == VT)
1955  continue;
1956  setLoadExtAction(ISD::EXTLOAD, TargetVT, VT, Expand);
1957  setLoadExtAction(ISD::ZEXTLOAD, TargetVT, VT, Expand);
1958  setLoadExtAction(ISD::SEXTLOAD, TargetVT, VT, Expand);
1959  setTruncStoreAction(VT, TargetVT, Expand);
1960  }
1961 
1962  // Normalize all inputs to SELECT to be vectors of i32.
1963  if (VT.getVectorElementType() != MVT::i32) {
1964  MVT VT32 = MVT::getVectorVT(MVT::i32, VT.getSizeInBits()/32);
1966  AddPromotedToType(ISD::SELECT, VT, VT32);
1967  }
1971  }
1972 
1973  // Extending loads from (native) vectors of i8 into (native) vectors of i16
1974  // are legal.
1981 
1982  // Types natively supported:
1983  for (MVT NativeVT : {MVT::v32i1, MVT::v64i1, MVT::v4i8, MVT::v8i8, MVT::v2i16,
1991 
1992  setOperationAction(ISD::ADD, NativeVT, Legal);
1993  setOperationAction(ISD::SUB, NativeVT, Legal);
1994  setOperationAction(ISD::MUL, NativeVT, Legal);
1995  setOperationAction(ISD::AND, NativeVT, Legal);
1996  setOperationAction(ISD::OR, NativeVT, Legal);
1997  setOperationAction(ISD::XOR, NativeVT, Legal);
1998  }
1999 
2002  setOperationAction(ISD::VECTOR_SHUFFLE, MVT::v4i8, Custom);
2003  setOperationAction(ISD::VECTOR_SHUFFLE, MVT::v4i16, Custom);
2004  setOperationAction(ISD::VECTOR_SHUFFLE, MVT::v8i8, Custom);
2005 
2006  auto setPromoteTo = [this] (unsigned Opc, MVT FromTy, MVT ToTy) {
2007  setOperationAction(Opc, FromTy, Promote);
2008  AddPromotedToType(Opc, FromTy, ToTy);
2009  };
2010 
2011  // Subtarget-specific operation actions.
2012  //
2013  if (Subtarget.hasV5TOps()) {
2018 
2021 
2034  } else { // V4
2044 
2049 
2050  // Expand these operations for both f32 and f64:
2051  for (unsigned FPExpOpV4 :
2053  setOperationAction(FPExpOpV4, MVT::f32, Expand);
2054  setOperationAction(FPExpOpV4, MVT::f64, Expand);
2055  }
2056 
2057  for (ISD::CondCode FPExpCCV4 :
2059  ISD::SETUO, ISD::SETO}) {
2060  setCondCodeAction(FPExpCCV4, MVT::f32, Expand);
2061  setCondCodeAction(FPExpCCV4, MVT::f64, Expand);
2062  }
2063  }
2064 
2065  // Handling of indexed loads/stores: default is "expand".
2066  //
2067  for (MVT VT : {MVT::i8, MVT::i16, MVT::i32, MVT::i64}) {
2070  }
2071 
2072  if (Subtarget.useHVXOps()) {
2073  bool Use64b = Subtarget.useHVX64BOps();
2074  ArrayRef<MVT> LegalV = Use64b ? LegalV64 : LegalV128;
2075  ArrayRef<MVT> LegalW = Use64b ? LegalW64 : LegalW128;
2076  MVT ByteV = Use64b ? MVT::v64i8 : MVT::v128i8;
2077  MVT ByteW = Use64b ? MVT::v128i8 : MVT::v256i8;
2078 
2079  setOperationAction(ISD::VECTOR_SHUFFLE, ByteV, Legal);
2080  setOperationAction(ISD::VECTOR_SHUFFLE, ByteW, Legal);
2083  setOperationAction(ISD::OR, ByteV, Legal);
2085 
2086  for (MVT T : LegalV) {
2089 
2092  if (T != ByteV) {
2095  }
2096 
2106  if (T != ByteV)
2108  }
2109 
2110  for (MVT T : LegalV) {
2111  if (T == ByteV)
2112  continue;
2113  // Promote all shuffles and concats to operate on vectors of bytes.
2114  setPromoteTo(ISD::VECTOR_SHUFFLE, T, ByteV);
2115  setPromoteTo(ISD::CONCAT_VECTORS, T, ByteV);
2116  setPromoteTo(ISD::AND, T, ByteV);
2117  setPromoteTo(ISD::OR, T, ByteV);
2118  setPromoteTo(ISD::XOR, T, ByteV);
2119  }
2120 
2121  for (MVT T : LegalW) {
2122  // Custom-lower BUILD_VECTOR for vector pairs. The standard (target-
2123  // independent) handling of it would convert it to a load, which is
2124  // not always the optimal choice.
2126 
2127  if (T == ByteW)
2128  continue;
2129  // Promote all shuffles and concats to operate on vectors of bytes.
2130  setPromoteTo(ISD::VECTOR_SHUFFLE, T, ByteW);
2131  setPromoteTo(ISD::CONCAT_VECTORS, T, ByteW);
2132  }
2133  }
2134 
2136 
2137  //
2138  // Library calls for unsupported operations
2139  //
2140  bool FastMath = EnableFastMath;
2141 
2142  setLibcallName(RTLIB::SDIV_I32, "__hexagon_divsi3");
2143  setLibcallName(RTLIB::SDIV_I64, "__hexagon_divdi3");
2144  setLibcallName(RTLIB::UDIV_I32, "__hexagon_udivsi3");
2145  setLibcallName(RTLIB::UDIV_I64, "__hexagon_udivdi3");
2146  setLibcallName(RTLIB::SREM_I32, "__hexagon_modsi3");
2147  setLibcallName(RTLIB::SREM_I64, "__hexagon_moddi3");
2148  setLibcallName(RTLIB::UREM_I32, "__hexagon_umodsi3");
2149  setLibcallName(RTLIB::UREM_I64, "__hexagon_umoddi3");
2150 
2151  setLibcallName(RTLIB::SINTTOFP_I128_F64, "__hexagon_floattidf");
2152  setLibcallName(RTLIB::SINTTOFP_I128_F32, "__hexagon_floattisf");
2153  setLibcallName(RTLIB::FPTOUINT_F32_I128, "__hexagon_fixunssfti");
2154  setLibcallName(RTLIB::FPTOUINT_F64_I128, "__hexagon_fixunsdfti");
2155  setLibcallName(RTLIB::FPTOSINT_F32_I128, "__hexagon_fixsfti");
2156  setLibcallName(RTLIB::FPTOSINT_F64_I128, "__hexagon_fixdfti");
2157 
2158  if (IsV4) {
2159  // Handle single-precision floating point operations on V4.
2160  if (FastMath) {
2161  setLibcallName(RTLIB::ADD_F32, "__hexagon_fast_addsf3");
2162  setLibcallName(RTLIB::SUB_F32, "__hexagon_fast_subsf3");
2163  setLibcallName(RTLIB::MUL_F32, "__hexagon_fast_mulsf3");
2164  setLibcallName(RTLIB::OGT_F32, "__hexagon_fast_gtsf2");
2165  setLibcallName(RTLIB::OLT_F32, "__hexagon_fast_ltsf2");
2166  // Double-precision compares.
2167  setLibcallName(RTLIB::OGT_F64, "__hexagon_fast_gtdf2");
2168  setLibcallName(RTLIB::OLT_F64, "__hexagon_fast_ltdf2");
2169  } else {
2170  setLibcallName(RTLIB::ADD_F32, "__hexagon_addsf3");
2171  setLibcallName(RTLIB::SUB_F32, "__hexagon_subsf3");
2172  setLibcallName(RTLIB::MUL_F32, "__hexagon_mulsf3");
2173  setLibcallName(RTLIB::OGT_F32, "__hexagon_gtsf2");
2174  setLibcallName(RTLIB::OLT_F32, "__hexagon_ltsf2");
2175  // Double-precision compares.
2176  setLibcallName(RTLIB::OGT_F64, "__hexagon_gtdf2");
2177  setLibcallName(RTLIB::OLT_F64, "__hexagon_ltdf2");
2178  }
2179  }
2180 
2181  // This is the only fast library function for sqrtd.
2182  if (FastMath)
2183  setLibcallName(RTLIB::SQRT_F64, "__hexagon_fast2_sqrtdf2");
2184 
2185  // Prefix is: nothing for "slow-math",
2186  // "fast2_" for V4 fast-math and V5+ fast-math double-precision
2187  // (actually, keep fast-math and fast-math2 separate for now)
2188  if (FastMath) {
2189  setLibcallName(RTLIB::ADD_F64, "__hexagon_fast_adddf3");
2190  setLibcallName(RTLIB::SUB_F64, "__hexagon_fast_subdf3");
2191  setLibcallName(RTLIB::MUL_F64, "__hexagon_fast_muldf3");
2192  setLibcallName(RTLIB::DIV_F64, "__hexagon_fast_divdf3");
2193  // Calling __hexagon_fast2_divsf3 with fast-math on V5 (ok).
2194  setLibcallName(RTLIB::DIV_F32, "__hexagon_fast_divsf3");
2195  } else {
2196  setLibcallName(RTLIB::ADD_F64, "__hexagon_adddf3");
2197  setLibcallName(RTLIB::SUB_F64, "__hexagon_subdf3");
2198  setLibcallName(RTLIB::MUL_F64, "__hexagon_muldf3");
2199  setLibcallName(RTLIB::DIV_F64, "__hexagon_divdf3");
2200  setLibcallName(RTLIB::DIV_F32, "__hexagon_divsf3");
2201  }
2202 
2203  if (Subtarget.hasV5TOps()) {
2204  if (FastMath)
2205  setLibcallName(RTLIB::SQRT_F32, "__hexagon_fast2_sqrtf");
2206  else
2207  setLibcallName(RTLIB::SQRT_F32, "__hexagon_sqrtf");
2208  } else {
2209  // V4
2210  setLibcallName(RTLIB::SINTTOFP_I32_F32, "__hexagon_floatsisf");
2211  setLibcallName(RTLIB::SINTTOFP_I32_F64, "__hexagon_floatsidf");
2212  setLibcallName(RTLIB::SINTTOFP_I64_F32, "__hexagon_floatdisf");
2213  setLibcallName(RTLIB::SINTTOFP_I64_F64, "__hexagon_floatdidf");
2214  setLibcallName(RTLIB::UINTTOFP_I32_F32, "__hexagon_floatunsisf");
2215  setLibcallName(RTLIB::UINTTOFP_I32_F64, "__hexagon_floatunsidf");
2216  setLibcallName(RTLIB::UINTTOFP_I64_F32, "__hexagon_floatundisf");
2217  setLibcallName(RTLIB::UINTTOFP_I64_F64, "__hexagon_floatundidf");
2218  setLibcallName(RTLIB::FPTOUINT_F32_I32, "__hexagon_fixunssfsi");
2219  setLibcallName(RTLIB::FPTOUINT_F32_I64, "__hexagon_fixunssfdi");
2220  setLibcallName(RTLIB::FPTOUINT_F64_I32, "__hexagon_fixunsdfsi");
2221  setLibcallName(RTLIB::FPTOUINT_F64_I64, "__hexagon_fixunsdfdi");
2222  setLibcallName(RTLIB::FPTOSINT_F32_I32, "__hexagon_fixsfsi");
2223  setLibcallName(RTLIB::FPTOSINT_F32_I64, "__hexagon_fixsfdi");
2224  setLibcallName(RTLIB::FPTOSINT_F64_I32, "__hexagon_fixdfsi");
2225  setLibcallName(RTLIB::FPTOSINT_F64_I64, "__hexagon_fixdfdi");
2226  setLibcallName(RTLIB::FPEXT_F32_F64, "__hexagon_extendsfdf2");
2227  setLibcallName(RTLIB::FPROUND_F64_F32, "__hexagon_truncdfsf2");
2228  setLibcallName(RTLIB::OEQ_F32, "__hexagon_eqsf2");
2229  setLibcallName(RTLIB::OEQ_F64, "__hexagon_eqdf2");
2230  setLibcallName(RTLIB::OGE_F32, "__hexagon_gesf2");
2231  setLibcallName(RTLIB::OGE_F64, "__hexagon_gedf2");
2232  setLibcallName(RTLIB::OLE_F32, "__hexagon_lesf2");
2233  setLibcallName(RTLIB::OLE_F64, "__hexagon_ledf2");
2234  setLibcallName(RTLIB::UNE_F32, "__hexagon_nesf2");
2235  setLibcallName(RTLIB::UNE_F64, "__hexagon_nedf2");
2236  setLibcallName(RTLIB::UO_F32, "__hexagon_unordsf2");
2237  setLibcallName(RTLIB::UO_F64, "__hexagon_unorddf2");
2238  setLibcallName(RTLIB::O_F32, "__hexagon_unordsf2");
2239  setLibcallName(RTLIB::O_F64, "__hexagon_unorddf2");
2240  }
2241 
2242  // These cause problems when the shift amount is non-constant.
2243  setLibcallName(RTLIB::SHL_I128, nullptr);
2244  setLibcallName(RTLIB::SRL_I128, nullptr);
2245  setLibcallName(RTLIB::SRA_I128, nullptr);
2246 }
2247 
2248 const char* HexagonTargetLowering::getTargetNodeName(unsigned Opcode) const {
2249  switch ((HexagonISD::NodeType)Opcode) {
2250  case HexagonISD::ALLOCA: return "HexagonISD::ALLOCA";
2251  case HexagonISD::AT_GOT: return "HexagonISD::AT_GOT";
2252  case HexagonISD::AT_PCREL: return "HexagonISD::AT_PCREL";
2253  case HexagonISD::BARRIER: return "HexagonISD::BARRIER";
2254  case HexagonISD::CALL: return "HexagonISD::CALL";
2255  case HexagonISD::CALLnr: return "HexagonISD::CALLnr";
2256  case HexagonISD::CALLR: return "HexagonISD::CALLR";
2257  case HexagonISD::COMBINE: return "HexagonISD::COMBINE";
2258  case HexagonISD::CONST32_GP: return "HexagonISD::CONST32_GP";
2259  case HexagonISD::CONST32: return "HexagonISD::CONST32";
2260  case HexagonISD::CP: return "HexagonISD::CP";
2261  case HexagonISD::DCFETCH: return "HexagonISD::DCFETCH";
2262  case HexagonISD::EH_RETURN: return "HexagonISD::EH_RETURN";
2263  case HexagonISD::EXTRACTU: return "HexagonISD::EXTRACTU";
2264  case HexagonISD::INSERT: return "HexagonISD::INSERT";
2265  case HexagonISD::JT: return "HexagonISD::JT";
2266  case HexagonISD::RET_FLAG: return "HexagonISD::RET_FLAG";
2267  case HexagonISD::TC_RETURN: return "HexagonISD::TC_RETURN";
2268  case HexagonISD::VCOMBINE: return "HexagonISD::VCOMBINE";
2269  case HexagonISD::VPACKE: return "HexagonISD::VPACKE";
2270  case HexagonISD::VPACKO: return "HexagonISD::VPACKO";
2271  case HexagonISD::VASL: return "HexagonISD::VASL";
2272  case HexagonISD::VASR: return "HexagonISD::VASR";
2273  case HexagonISD::VLSR: return "HexagonISD::VLSR";
2274  case HexagonISD::VSPLAT: return "HexagonISD::VSPLAT";
2275  case HexagonISD::VEXTRACTW: return "HexagonISD::VEXTRACTW";
2276  case HexagonISD::VINSERTW0: return "HexagonISD::VINSERTW0";
2277  case HexagonISD::VROR: return "HexagonISD::VROR";
2278  case HexagonISD::READCYCLE: return "HexagonISD::READCYCLE";
2279  case HexagonISD::VZERO: return "HexagonISD::VZERO";
2280  case HexagonISD::OP_END: break;
2281  }
2282  return nullptr;
2283 }
2284 
2285 /// Given an intrinsic, checks if on the target the intrinsic will need to map
2286 /// to a MemIntrinsicNode (touches memory). If this is the case, it returns
2287 /// true and store the intrinsic information into the IntrinsicInfo that was
2288 /// passed to the function.
2290  const CallInst &I,
2291  MachineFunction &MF,
2292  unsigned Intrinsic) const {
2293  switch (Intrinsic) {
2294  case Intrinsic::hexagon_V6_vgathermw:
2295  case Intrinsic::hexagon_V6_vgathermw_128B:
2296  case Intrinsic::hexagon_V6_vgathermh:
2297  case Intrinsic::hexagon_V6_vgathermh_128B:
2298  case Intrinsic::hexagon_V6_vgathermhw:
2299  case Intrinsic::hexagon_V6_vgathermhw_128B:
2300  case Intrinsic::hexagon_V6_vgathermwq:
2301  case Intrinsic::hexagon_V6_vgathermwq_128B:
2302  case Intrinsic::hexagon_V6_vgathermhq:
2303  case Intrinsic::hexagon_V6_vgathermhq_128B:
2304  case Intrinsic::hexagon_V6_vgathermhwq:
2305  case Intrinsic::hexagon_V6_vgathermhwq_128B: {
2306  const Module &M = *I.getParent()->getParent()->getParent();
2307  Info.opc = ISD::INTRINSIC_W_CHAIN;
2308  Type *VecTy = I.getArgOperand(1)->getType();
2309  Info.memVT = MVT::getVT(VecTy);
2310  Info.ptrVal = I.getArgOperand(0);
2311  Info.offset = 0;
2312  Info.align = M.getDataLayout().getTypeAllocSizeInBits(VecTy) / 8;
2316  return true;
2317  }
2318  default:
2319  break;
2320  }
2321  return false;
2322 }
2323 
2325  EVT MTy1 = EVT::getEVT(Ty1);
2326  EVT MTy2 = EVT::getEVT(Ty2);
2327  if (!MTy1.isSimple() || !MTy2.isSimple())
2328  return false;
2329  return (MTy1.getSimpleVT() == MVT::i64) && (MTy2.getSimpleVT() == MVT::i32);
2330 }
2331 
2333  if (!VT1.isSimple() || !VT2.isSimple())
2334  return false;
2335  return (VT1.getSimpleVT() == MVT::i64) && (VT2.getSimpleVT() == MVT::i32);
2336 }
2337 
2339  return isOperationLegalOrCustom(ISD::FMA, VT);
2340 }
2341 
2342 // Should we expand the build vector with shuffles?
2344  unsigned DefinedValues) const {
2345  return false;
2346 }
2347 
2349  EVT VT) const {
2350  return true;
2351 }
2352 
2355  if (VT.getVectorNumElements() == 1)
2357 
2358  // Always widen vectors of i1.
2359  MVT ElemTy = VT.getSimpleVT().getVectorElementType();
2360  if (ElemTy == MVT::i1)
2362 
2363  if (Subtarget.useHVXOps()) {
2364  // If the size of VT is at least half of the vector length,
2365  // widen the vector. Note: the threshold was not selected in
2366  // any scientific way.
2367  ArrayRef<MVT> Tys = Subtarget.getHVXElementTypes();
2368  if (llvm::find(Tys, ElemTy) != Tys.end()) {
2369  unsigned HwWidth = 8*Subtarget.getVectorLength();
2370  unsigned VecWidth = VT.getSizeInBits();
2371  if (VecWidth >= HwWidth/2 && VecWidth < HwWidth)
2373  }
2374  }
2376 }
2377 
2378 // Lower a vector shuffle (V1, V2, V3). V1 and V2 are the two vectors
2379 // to select data from, V3 is the permutation.
2380 SDValue
2382  const {
2383  const auto *SVN = cast<ShuffleVectorSDNode>(Op);
2384  ArrayRef<int> AM = SVN->getMask();
2385  assert(AM.size() <= 8 && "Unexpected shuffle mask");
2386  unsigned VecLen = AM.size();
2387 
2388  MVT VecTy = ty(Op);
2389  assert(VecTy.getSizeInBits() <= 64 && "Unexpected vector length");
2390 
2391  SDValue Op0 = Op.getOperand(0);
2392  SDValue Op1 = Op.getOperand(1);
2393  // If the inputs are not the same as the output, bail. This is not an
2394  // error situation, but complicates the handling and the default expansion
2395  // (into BUILD_VECTOR) should be adequate.
2396  if (ty(Op0) != VecTy || ty(Op1) != VecTy)
2397  return SDValue();
2398 
2399  // Normalize the mask so that the first non-negative index comes from
2400  // the first operand.
2401  SmallVector<int,8> Mask(AM.begin(), AM.end());
2402  unsigned F = llvm::find_if(AM, [](int M) { return M >= 0; }) - AM.data();
2403  if (F == AM.size())
2404  return DAG.getUNDEF(VecTy);
2405  if (AM[F] >= int(VecLen)) {
2407  std::swap(Op0, Op1);
2408  }
2409 
2410  // Express the shuffle mask in terms of bytes.
2411  SmallVector<int,8> ByteMask;
2412  unsigned ElemBytes = VecTy.getVectorElementType().getSizeInBits() / 8;
2413  for (unsigned i = 0, e = Mask.size(); i != e; ++i) {
2414  int M = Mask[i];
2415  if (M < 0) {
2416  for (unsigned j = 0; j != ElemBytes; ++j)
2417  ByteMask.push_back(-1);
2418  } else {
2419  for (unsigned j = 0; j != ElemBytes; ++j)
2420  ByteMask.push_back(M*ElemBytes + j);
2421  }
2422  }
2423  assert(ByteMask.size() <= 8);
2424 
2425  // All non-undef (non-negative) indexes are well within [0..127], so they
2426  // fit in a single byte. Build two 64-bit words:
2427  // - MaskIdx where each byte is the corresponding index (for non-negative
2428  // indexes), and 0xFF for negative indexes, and
2429  // - MaskUnd that has 0xFF for each negative index.
2430  uint64_t MaskIdx = 0;
2431  uint64_t MaskUnd = 0;
2432  for (unsigned i = 0, e = ByteMask.size(); i != e; ++i) {
2433  unsigned S = 8*i;
2434  uint64_t M = ByteMask[i] & 0xFF;
2435  if (M == 0xFF)
2436  MaskUnd |= M << S;
2437  MaskIdx |= M << S;
2438  }
2439 
2440  const SDLoc &dl(Op);
2441 
2442  if (ByteMask.size() == 4) {
2443  // Identity.
2444  if (MaskIdx == (0x03020100 | MaskUnd))
2445  return Op0;
2446  // Byte swap.
2447  if (MaskIdx == (0x00010203 | MaskUnd)) {
2448  SDValue T0 = DAG.getBitcast(MVT::i32, Op0);
2449  SDValue T1 = DAG.getNode(ISD::BSWAP, dl, MVT::i32, T0);
2450  return DAG.getBitcast(VecTy, T1);
2451  }
2452 
2453  // Byte packs.
2454  SDValue Concat10 = DAG.getNode(HexagonISD::COMBINE, dl,
2455  typeJoin({ty(Op1), ty(Op0)}), {Op1, Op0});
2456  if (MaskIdx == (0x06040200 | MaskUnd))
2457  return getNode(Hexagon::S2_vtrunehb, dl, VecTy, {Concat10}, DAG);
2458  if (MaskIdx == (0x07050301 | MaskUnd))
2459  return getNode(Hexagon::S2_vtrunohb, dl, VecTy, {Concat10}, DAG);
2460 
2461  SDValue Concat01 = DAG.getNode(HexagonISD::COMBINE, dl,
2462  typeJoin({ty(Op0), ty(Op1)}), {Op0, Op1});
2463  if (MaskIdx == (0x02000604 | MaskUnd))
2464  return getNode(Hexagon::S2_vtrunehb, dl, VecTy, {Concat01}, DAG);
2465  if (MaskIdx == (0x03010705 | MaskUnd))
2466  return getNode(Hexagon::S2_vtrunohb, dl, VecTy, {Concat01}, DAG);
2467  }
2468 
2469  if (ByteMask.size() == 8) {
2470  // Identity.
2471  if (MaskIdx == (0x0706050403020100ull | MaskUnd))
2472  return Op0;
2473  // Byte swap.
2474  if (MaskIdx == (0x0001020304050607ull | MaskUnd)) {
2475  SDValue T0 = DAG.getBitcast(MVT::i64, Op0);
2476  SDValue T1 = DAG.getNode(ISD::BSWAP, dl, MVT::i64, T0);
2477  return DAG.getBitcast(VecTy, T1);
2478  }
2479 
2480  // Halfword picks.
2481  if (MaskIdx == (0x0d0c050409080100ull | MaskUnd))
2482  return getNode(Hexagon::S2_shuffeh, dl, VecTy, {Op1, Op0}, DAG);
2483  if (MaskIdx == (0x0f0e07060b0a0302ull | MaskUnd))
2484  return getNode(Hexagon::S2_shuffoh, dl, VecTy, {Op1, Op0}, DAG);
2485  if (MaskIdx == (0x0d0c090805040100ull | MaskUnd))
2486  return getNode(Hexagon::S2_vtrunewh, dl, VecTy, {Op1, Op0}, DAG);
2487  if (MaskIdx == (0x0f0e0b0a07060302ull | MaskUnd))
2488  return getNode(Hexagon::S2_vtrunowh, dl, VecTy, {Op1, Op0}, DAG);
2489  if (MaskIdx == (0x0706030205040100ull | MaskUnd)) {
2490  VectorPair P = opSplit(Op0, dl, DAG);
2491  return getNode(Hexagon::S2_packhl, dl, VecTy, {P.second, P.first}, DAG);
2492  }
2493 
2494  // Byte packs.
2495  if (MaskIdx == (0x0e060c040a020800ull | MaskUnd))
2496  return getNode(Hexagon::S2_shuffeb, dl, VecTy, {Op1, Op0}, DAG);
2497  if (MaskIdx == (0x0f070d050b030901ull | MaskUnd))
2498  return getNode(Hexagon::S2_shuffob, dl, VecTy, {Op1, Op0}, DAG);
2499  }
2500 
2501  return SDValue();
2502 }
2503 
2504 // If BUILD_VECTOR has same base element repeated several times,
2505 // report true.
2507  unsigned NElts = BVN->getNumOperands();
2508  SDValue V0 = BVN->getOperand(0);
2509 
2510  for (unsigned i = 1, e = NElts; i != e; ++i) {
2511  if (BVN->getOperand(i) != V0)
2512  return false;
2513  }
2514  return true;
2515 }
2516 
2517 // Lower a vector shift. Try to convert
2518 // <VT> = SHL/SRA/SRL <VT> by <VT> to Hexagon specific
2519 // <VT> = SHL/SRA/SRL <VT> by <IT/i32>.
2520 SDValue
2522  BuildVectorSDNode *BVN = nullptr;
2523  SDValue V1 = Op.getOperand(0);
2524  SDValue V2 = Op.getOperand(1);
2525  SDValue V3;
2526  SDLoc dl(Op);
2527  EVT VT = Op.getValueType();
2528 
2529  if ((BVN = dyn_cast<BuildVectorSDNode>(V1.getNode())) &&
2530  isCommonSplatElement(BVN))
2531  V3 = V2;
2532  else if ((BVN = dyn_cast<BuildVectorSDNode>(V2.getNode())) &&
2533  isCommonSplatElement(BVN))
2534  V3 = V1;
2535  else
2536  return SDValue();
2537 
2538  SDValue CommonSplat = BVN->getOperand(0);
2539  SDValue Result;
2540 
2541  if (VT.getSimpleVT() == MVT::v4i16) {
2542  switch (Op.getOpcode()) {
2543  case ISD::SRA:
2544  Result = DAG.getNode(HexagonISD::VASR, dl, VT, V3, CommonSplat);
2545  break;
2546  case ISD::SHL:
2547  Result = DAG.getNode(HexagonISD::VASL, dl, VT, V3, CommonSplat);
2548  break;
2549  case ISD::SRL:
2550  Result = DAG.getNode(HexagonISD::VLSR, dl, VT, V3, CommonSplat);
2551  break;
2552  default:
2553  return SDValue();
2554  }
2555  } else if (VT.getSimpleVT() == MVT::v2i32) {
2556  switch (Op.getOpcode()) {
2557  case ISD::SRA:
2558  Result = DAG.getNode(HexagonISD::VASR, dl, VT, V3, CommonSplat);
2559  break;
2560  case ISD::SHL:
2561  Result = DAG.getNode(HexagonISD::VASL, dl, VT, V3, CommonSplat);
2562  break;
2563  case ISD::SRL:
2564  Result = DAG.getNode(HexagonISD::VLSR, dl, VT, V3, CommonSplat);
2565  break;
2566  default:
2567  return SDValue();
2568  }
2569  } else {
2570  return SDValue();
2571  }
2572 
2573  return DAG.getNode(ISD::BITCAST, dl, VT, Result);
2574 }
2575 
2576 bool
2577 HexagonTargetLowering::getBuildVectorConstInts(ArrayRef<SDValue> Values,
2578  MVT VecTy, SelectionDAG &DAG,
2579  MutableArrayRef<ConstantInt*> Consts) const {
2580  MVT ElemTy = VecTy.getVectorElementType();
2581  unsigned ElemWidth = ElemTy.getSizeInBits();
2582  IntegerType *IntTy = IntegerType::get(*DAG.getContext(), ElemWidth);
2583  bool AllConst = true;
2584 
2585  for (unsigned i = 0, e = Values.size(); i != e; ++i) {
2586  SDValue V = Values[i];
2587  if (V.isUndef()) {
2588  Consts[i] = ConstantInt::get(IntTy, 0);
2589  continue;
2590  }
2591  // Make sure to always cast to IntTy.
2592  if (auto *CN = dyn_cast<ConstantSDNode>(V.getNode())) {
2593  const ConstantInt *CI = CN->getConstantIntValue();
2594  Consts[i] = ConstantInt::get(IntTy, CI->getValue().getSExtValue());
2595  } else if (auto *CN = dyn_cast<ConstantFPSDNode>(V.getNode())) {
2596  const ConstantFP *CF = CN->getConstantFPValue();
2597  APInt A = CF->getValueAPF().bitcastToAPInt();
2598  Consts[i] = ConstantInt::get(IntTy, A.getZExtValue());
2599  } else {
2600  AllConst = false;
2601  }
2602  }
2603  return AllConst;
2604 }
2605 
2606 SDValue
2607 HexagonTargetLowering::buildVector32(ArrayRef<SDValue> Elem, const SDLoc &dl,
2608  MVT VecTy, SelectionDAG &DAG) const {
2609  MVT ElemTy = VecTy.getVectorElementType();
2610  assert(VecTy.getVectorNumElements() == Elem.size());
2611 
2612  SmallVector<ConstantInt*,4> Consts(Elem.size());
2613  bool AllConst = getBuildVectorConstInts(Elem, VecTy, DAG, Consts);
2614 
2615  unsigned First, Num = Elem.size();
2616  for (First = 0; First != Num; ++First)
2617  if (!isUndef(Elem[First]))
2618  break;
2619  if (First == Num)
2620  return DAG.getUNDEF(VecTy);
2621 
2622  if (AllConst &&
2623  llvm::all_of(Consts, [](ConstantInt *CI) { return CI->isZero(); }))
2624  return getZero(dl, VecTy, DAG);
2625 
2626  if (ElemTy == MVT::i16) {
2627  assert(Elem.size() == 2);
2628  if (AllConst) {
2629  uint32_t V = (Consts[0]->getZExtValue() & 0xFFFF) |
2630  Consts[1]->getZExtValue() << 16;
2631  return DAG.getBitcast(MVT::v2i16, DAG.getConstant(V, dl, MVT::i32));
2632  }
2633  SDValue N = getNode(Hexagon::A2_combine_ll, dl, MVT::i32,
2634  {Elem[1], Elem[0]}, DAG);
2635  return DAG.getBitcast(MVT::v2i16, N);
2636  }
2637 
2638  if (ElemTy == MVT::i8) {
2639  // First try generating a constant.
2640  if (AllConst) {
2641  int32_t V = (Consts[0]->getZExtValue() & 0xFF) |
2642  (Consts[1]->getZExtValue() & 0xFF) << 8 |
2643  (Consts[1]->getZExtValue() & 0xFF) << 16 |
2644  Consts[2]->getZExtValue() << 24;
2645  return DAG.getBitcast(MVT::v4i8, DAG.getConstant(V, dl, MVT::i32));
2646  }
2647 
2648  // Then try splat.
2649  bool IsSplat = true;
2650  for (unsigned i = 0; i != Num; ++i) {
2651  if (i == First)
2652  continue;
2653  if (Elem[i] == Elem[First] || isUndef(Elem[i]))
2654  continue;
2655  IsSplat = false;
2656  break;
2657  }
2658  if (IsSplat) {
2659  // Legalize the operand to VSPLAT.
2660  SDValue Ext = DAG.getZExtOrTrunc(Elem[First], dl, MVT::i32);
2661  return DAG.getNode(HexagonISD::VSPLAT, dl, VecTy, Ext);
2662  }
2663 
2664  // Generate
2665  // (zxtb(Elem[0]) | (zxtb(Elem[1]) << 8)) |
2666  // (zxtb(Elem[2]) | (zxtb(Elem[3]) << 8)) << 16
2667  assert(Elem.size() == 4);
2668  SDValue Vs[4];
2669  for (unsigned i = 0; i != 4; ++i) {
2670  Vs[i] = DAG.getZExtOrTrunc(Elem[i], dl, MVT::i32);
2671  Vs[i] = DAG.getZeroExtendInReg(Vs[i], dl, MVT::i8);
2672  }
2673  SDValue S8 = DAG.getConstant(8, dl, MVT::i32);
2674  SDValue T0 = DAG.getNode(ISD::SHL, dl, MVT::i32, {Vs[1], S8});
2675  SDValue T1 = DAG.getNode(ISD::SHL, dl, MVT::i32, {Vs[3], S8});
2676  SDValue B0 = DAG.getNode(ISD::OR, dl, MVT::i32, {Vs[0], T0});
2677  SDValue B1 = DAG.getNode(ISD::OR, dl, MVT::i32, {Vs[2], T1});
2678 
2679  SDValue R = getNode(Hexagon::A2_combine_ll, dl, MVT::i32, {B1, B0}, DAG);
2680  return DAG.getBitcast(MVT::v4i8, R);
2681  }
2682 
2683 #ifndef NDEBUG
2684  dbgs() << "VecTy: " << EVT(VecTy).getEVTString() << '\n';
2685 #endif
2686  llvm_unreachable("Unexpected vector element type");
2687 }
2688 
2689 SDValue
2690 HexagonTargetLowering::buildVector64(ArrayRef<SDValue> Elem, const SDLoc &dl,
2691  MVT VecTy, SelectionDAG &DAG) const {
2692  MVT ElemTy = VecTy.getVectorElementType();
2693  assert(VecTy.getVectorNumElements() == Elem.size());
2694 
2695  SmallVector<ConstantInt*,8> Consts(Elem.size());
2696  bool AllConst = getBuildVectorConstInts(Elem, VecTy, DAG, Consts);
2697 
2698  unsigned First, Num = Elem.size();
2699  for (First = 0; First != Num; ++First)
2700  if (!isUndef(Elem[First]))
2701  break;
2702  if (First == Num)
2703  return DAG.getUNDEF(VecTy);
2704 
2705  if (AllConst &&
2706  llvm::all_of(Consts, [](ConstantInt *CI) { return CI->isZero(); }))
2707  return getZero(dl, VecTy, DAG);
2708 
2709  // First try splat if possible.
2710  if (ElemTy == MVT::i16) {
2711  bool IsSplat = true;
2712  for (unsigned i = 0; i != Num; ++i) {
2713  if (i == First)
2714  continue;
2715  if (Elem[i] == Elem[First] || isUndef(Elem[i]))
2716  continue;
2717  IsSplat = false;
2718  break;
2719  }
2720  if (IsSplat) {
2721  // Legalize the operand to VSPLAT.
2722  SDValue Ext = DAG.getZExtOrTrunc(Elem[First], dl, MVT::i32);
2723  return DAG.getNode(HexagonISD::VSPLAT, dl, VecTy, Ext);
2724  }
2725  }
2726 
2727  // Then try constant.
2728  if (AllConst) {
2729  uint64_t Val = 0;
2730  unsigned W = ElemTy.getSizeInBits();
2731  uint64_t Mask = (ElemTy == MVT::i8) ? 0xFFull
2732  : (ElemTy == MVT::i16) ? 0xFFFFull : 0xFFFFFFFFull;
2733  for (unsigned i = 0; i != Num; ++i)
2734  Val = (Val << W) | (Consts[Num-1-i]->getZExtValue() & Mask);
2735  SDValue V0 = DAG.getConstant(Val, dl, MVT::i64);
2736  return DAG.getBitcast(VecTy, V0);
2737  }
2738 
2739  // Build two 32-bit vectors and concatenate.
2740  MVT HalfTy = MVT::getVectorVT(ElemTy, Num/2);
2741  SDValue L = (ElemTy == MVT::i32)
2742  ? Elem[0]
2743  : buildVector32(Elem.take_front(Num/2), dl, HalfTy, DAG);
2744  SDValue H = (ElemTy == MVT::i32)
2745  ? Elem[1]
2746  : buildVector32(Elem.drop_front(Num/2), dl, HalfTy, DAG);
2747  return DAG.getNode(HexagonISD::COMBINE, dl, VecTy, {H, L});
2748 }
2749 
2750 SDValue
2751 HexagonTargetLowering::extractVector(SDValue VecV, SDValue IdxV,
2752  const SDLoc &dl, MVT ValTy, MVT ResTy,
2753  SelectionDAG &DAG) const {
2754  MVT VecTy = ty(VecV);
2755  assert(!ValTy.isVector() ||
2756  VecTy.getVectorElementType() == ValTy.getVectorElementType());
2757  unsigned VecWidth = VecTy.getSizeInBits();
2758  unsigned ValWidth = ValTy.getSizeInBits();
2759  unsigned ElemWidth = VecTy.getVectorElementType().getSizeInBits();
2760  assert(VecWidth == 32 || VecWidth == 64);
2761  assert((VecWidth % ElemWidth) == 0);
2762 
2763  // Cast everything to scalar integer types.
2764  MVT ScalarTy = tyScalar(VecTy);
2765  VecV = DAG.getBitcast(ScalarTy, VecV);
2766 
2767  SDValue WidthV = DAG.getConstant(ValWidth, dl, MVT::i32);
2768  SDValue ExtV;
2769 
2770  if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(IdxV)) {
2771  unsigned Off = C->getZExtValue() * ElemWidth;
2772  if (VecWidth == 64 && ValWidth == 32) {
2773  assert(Off == 0 || Off == 32);
2774  unsigned SubIdx = Off == 0 ? Hexagon::isub_lo : Hexagon::isub_hi;
2775  ExtV = DAG.getTargetExtractSubreg(SubIdx, dl, MVT::i32, VecV);
2776  } else if (Off == 0 && (ValWidth % 8) == 0) {
2777  ExtV = DAG.getZeroExtendInReg(VecV, dl, tyScalar(ValTy));
2778  } else {
2779  SDValue OffV = DAG.getConstant(Off, dl, MVT::i32);
2780  // The return type of EXTRACTU must be the same as the type of the
2781  // input vector.
2782  ExtV = DAG.getNode(HexagonISD::EXTRACTU, dl, ScalarTy,
2783  {VecV, WidthV, OffV});
2784  }
2785  } else {
2786  if (ty(IdxV) != MVT::i32)
2787  IdxV = DAG.getZExtOrTrunc(IdxV, dl, MVT::i32);
2788  SDValue OffV = DAG.getNode(ISD::MUL, dl, MVT::i32, IdxV,
2789  DAG.getConstant(ElemWidth, dl, MVT::i32));
2790  ExtV = DAG.getNode(HexagonISD::EXTRACTU, dl, ScalarTy,
2791  {VecV, WidthV, OffV});
2792  }
2793 
2794  // Cast ExtV to the requested result type.
2795  ExtV = DAG.getZExtOrTrunc(ExtV, dl, tyScalar(ResTy));
2796  ExtV = DAG.getBitcast(ResTy, ExtV);
2797  return ExtV;
2798 }
2799 
2800 SDValue
2801 HexagonTargetLowering::insertVector(SDValue VecV, SDValue ValV, SDValue IdxV,
2802  const SDLoc &dl, MVT ValTy,
2803  SelectionDAG &DAG) const {
2804  MVT VecTy = ty(VecV);
2805  unsigned VecWidth = VecTy.getSizeInBits();
2806  unsigned ValWidth = ValTy.getSizeInBits();
2807  assert(VecWidth == 32 || VecWidth == 64);
2808  assert((VecWidth % ValWidth) == 0);
2809 
2810  // Cast everything to scalar integer types.
2811  MVT ScalarTy = MVT::getIntegerVT(VecWidth);
2812  // The actual type of ValV may be different than ValTy (which is related
2813  // to the vector type).
2814  unsigned VW = ty(ValV).getSizeInBits();
2815  ValV = DAG.getBitcast(MVT::getIntegerVT(VW), ValV);
2816  VecV = DAG.getBitcast(ScalarTy, VecV);
2817  if (VW != VecWidth)
2818  ValV = DAG.getAnyExtOrTrunc(ValV, dl, ScalarTy);
2819 
2820  SDValue WidthV = DAG.getConstant(ValWidth, dl, MVT::i32);
2821  SDValue InsV;
2822 
2823  if (ConstantSDNode *C = dyn_cast<ConstantSDNode>(IdxV)) {
2824  unsigned W = C->getZExtValue() * ValWidth;
2825  SDValue OffV = DAG.getConstant(W, dl, MVT::i32);
2826  InsV = DAG.getNode(HexagonISD::INSERT, dl, ScalarTy,
2827  {VecV, ValV, WidthV, OffV});
2828  } else {
2829  if (ty(IdxV) != MVT::i32)
2830  IdxV = DAG.getZExtOrTrunc(IdxV, dl, MVT::i32);
2831  SDValue OffV = DAG.getNode(ISD::MUL, dl, MVT::i32, IdxV, WidthV);
2832  InsV = DAG.getNode(HexagonISD::INSERT, dl, ScalarTy,
2833  {VecV, ValV, WidthV, OffV});
2834  }
2835 
2836  return DAG.getNode(ISD::BITCAST, dl, VecTy, InsV);
2837 }
2838 
2839 SDValue
2840 HexagonTargetLowering::getZero(const SDLoc &dl, MVT Ty, SelectionDAG &DAG)
2841  const {
2842  if (Ty.isVector()) {
2843  assert(Ty.isInteger() && "Only integer vectors are supported here");
2844  unsigned W = Ty.getSizeInBits();
2845  if (W <= 64)
2846  return DAG.getBitcast(Ty, DAG.getConstant(0, dl, MVT::getIntegerVT(W)));
2847  return DAG.getNode(HexagonISD::VZERO, dl, Ty);
2848  }
2849 
2850  if (Ty.isInteger())
2851  return DAG.getConstant(0, dl, Ty);
2852  if (Ty.isFloatingPoint())
2853  return DAG.getConstantFP(0.0, dl, Ty);
2854  llvm_unreachable("Invalid type for zero");
2855 }
2856 
2857 SDValue
2859  MVT VecTy = ty(Op);
2860  unsigned BW = VecTy.getSizeInBits();
2861 
2862  if (Subtarget.useHVXOps() && Subtarget.isHVXVectorType(VecTy, true))
2863  return LowerHvxBuildVector(Op, DAG);
2864 
2865  if (BW == 32 || BW == 64) {
2866  const SDLoc &dl(Op);
2868  for (unsigned i = 0, e = Op.getNumOperands(); i != e; ++i)
2869  Ops.push_back(Op.getOperand(i));
2870  if (BW == 32)
2871  return buildVector32(Ops, dl, VecTy, DAG);
2872  return buildVector64(Ops, dl, VecTy, DAG);
2873  }
2874 
2875  return SDValue();
2876 }
2877 
2878 SDValue
2880  SelectionDAG &DAG) const {
2881  MVT VecTy = ty(Op);
2882  assert(!Subtarget.useHVXOps() || !Subtarget.isHVXVectorType(VecTy));
2883 
2884  if (VecTy.getSizeInBits() == 64) {
2885  assert(Op.getNumOperands() == 2);
2886  return DAG.getNode(HexagonISD::COMBINE, SDLoc(Op), VecTy, Op.getOperand(1),
2887  Op.getOperand(0));
2888  }
2889 
2890  return SDValue();
2891 }
2892 
2893 SDValue
2895  SelectionDAG &DAG) const {
2896  SDValue Vec = Op.getOperand(0);
2897  MVT VecTy = ty(Vec);
2898  if (Subtarget.useHVXOps() && Subtarget.isHVXVectorType(VecTy))
2899  return LowerHvxExtractElement(Op, DAG);
2900 
2901  MVT ElemTy = ty(Vec).getVectorElementType();
2902  return extractVector(Vec, Op.getOperand(1), SDLoc(Op), ElemTy, ty(Op), DAG);
2903 }
2904 
2905 SDValue
2907  SelectionDAG &DAG) const {
2908  SDValue Vec = Op.getOperand(0);
2909  MVT VecTy = ty(Vec);
2910  if (Subtarget.useHVXOps() && Subtarget.isHVXVectorType(VecTy))
2911  return LowerHvxExtractSubvector(Op, DAG);
2912 
2913  return extractVector(Vec, Op.getOperand(1), SDLoc(Op), ty(Op), ty(Op), DAG);
2914 }
2915 
2916 SDValue
2918  SelectionDAG &DAG) const {
2919  MVT VecTy = ty(Op);
2920  if (Subtarget.useHVXOps() && Subtarget.isHVXVectorType(VecTy))
2921  return LowerHvxInsertElement(Op, DAG);
2922 
2923  return insertVector(Op.getOperand(0), Op.getOperand(1), Op.getOperand(2),
2924  SDLoc(Op), VecTy.getVectorElementType(), DAG);
2925 }
2926 
2927 SDValue
2929  SelectionDAG &DAG) const {
2930  if (Subtarget.useHVXOps() && Subtarget.isHVXVectorType(ty(Op)))
2931  return LowerHvxInsertSubvector(Op, DAG);
2932 
2933  SDValue ValV = Op.getOperand(1);
2934  return insertVector(Op.getOperand(0), ValV, Op.getOperand(2),
2935  SDLoc(Op), ty(ValV), DAG);
2936 }
2937 
2938 bool
2940  // Assuming the caller does not have either a signext or zeroext modifier, and
2941  // only one value is accepted, any reasonable truncation is allowed.
2942  if (!Ty1->isIntegerTy() || !Ty2->isIntegerTy())
2943  return false;
2944 
2945  // FIXME: in principle up to 64-bit could be made safe, but it would be very
2946  // fragile at the moment: any support for multiple value returns would be
2947  // liable to disallow tail calls involving i64 -> iN truncation in many cases.
2948  return Ty1->getPrimitiveSizeInBits() <= 32;
2949 }
2950 
2951 SDValue
2953  SDValue Chain = Op.getOperand(0);
2954  SDValue Offset = Op.getOperand(1);
2955  SDValue Handler = Op.getOperand(2);
2956  SDLoc dl(Op);
2957  auto PtrVT = getPointerTy(DAG.getDataLayout());
2958 
2959  // Mark function as containing a call to EH_RETURN.
2960  HexagonMachineFunctionInfo *FuncInfo =
2962  FuncInfo->setHasEHReturn();
2963 
2964  unsigned OffsetReg = Hexagon::R28;
2965 
2966  SDValue StoreAddr =
2967  DAG.getNode(ISD::ADD, dl, PtrVT, DAG.getRegister(Hexagon::R30, PtrVT),
2968  DAG.getIntPtrConstant(4, dl));
2969  Chain = DAG.getStore(Chain, dl, Handler, StoreAddr, MachinePointerInfo());
2970  Chain = DAG.getCopyToReg(Chain, dl, OffsetReg, Offset);
2971 
2972  // Not needed we already use it as explict input to EH_RETURN.
2973  // MF.getRegInfo().addLiveOut(OffsetReg);
2974 
2975  return DAG.getNode(HexagonISD::EH_RETURN, dl, MVT::Other, Chain);
2976 }
2977 
2978 SDValue
2980  unsigned Opc = Op.getOpcode();
2981  switch (Opc) {
2982  default:
2983 #ifndef NDEBUG
2984  Op.getNode()->dumpr(&DAG);
2985  if (Opc > HexagonISD::OP_BEGIN && Opc < HexagonISD::OP_END)
2986  errs() << "Error: check for a non-legal type in this operation\n";
2987 #endif
2988  llvm_unreachable("Should not custom lower this!");
2989  case ISD::CONCAT_VECTORS: return LowerCONCAT_VECTORS(Op, DAG);
2990  case ISD::INSERT_SUBVECTOR: return LowerINSERT_SUBVECTOR(Op, DAG);
2991  case ISD::INSERT_VECTOR_ELT: return LowerINSERT_VECTOR_ELT(Op, DAG);
2992  case ISD::EXTRACT_SUBVECTOR: return LowerEXTRACT_SUBVECTOR(Op, DAG);
2993  case ISD::EXTRACT_VECTOR_ELT: return LowerEXTRACT_VECTOR_ELT(Op, DAG);
2994  case ISD::BUILD_VECTOR: return LowerBUILD_VECTOR(Op, DAG);
2995  case ISD::VECTOR_SHUFFLE: return LowerVECTOR_SHUFFLE(Op, DAG);
2996  case ISD::SRA:
2997  case ISD::SHL:
2998  case ISD::SRL: return LowerVECTOR_SHIFT(Op, DAG);
2999  case ISD::ConstantPool: return LowerConstantPool(Op, DAG);
3000  case ISD::JumpTable: return LowerJumpTable(Op, DAG);
3001  case ISD::EH_RETURN: return LowerEH_RETURN(Op, DAG);
3002  // Frame & Return address. Currently unimplemented.
3003  case ISD::RETURNADDR: return LowerRETURNADDR(Op, DAG);
3004  case ISD::FRAMEADDR: return LowerFRAMEADDR(Op, DAG);
3005  case ISD::GlobalTLSAddress: return LowerGlobalTLSAddress(Op, DAG);
3006  case ISD::ATOMIC_FENCE: return LowerATOMIC_FENCE(Op, DAG);
3007  case ISD::GlobalAddress: return LowerGLOBALADDRESS(Op, DAG);
3008  case ISD::BlockAddress: return LowerBlockAddress(Op, DAG);
3009  case ISD::GLOBAL_OFFSET_TABLE: return LowerGLOBAL_OFFSET_TABLE(Op, DAG);
3010  case ISD::VASTART: return LowerVASTART(Op, DAG);
3011  case ISD::DYNAMIC_STACKALLOC: return LowerDYNAMIC_STACKALLOC(Op, DAG);
3012  case ISD::SETCC: return LowerSETCC(Op, DAG);
3013  case ISD::VSELECT: return LowerVSELECT(Op, DAG);
3014  case ISD::INTRINSIC_WO_CHAIN: return LowerINTRINSIC_WO_CHAIN(Op, DAG);
3015  case ISD::INTRINSIC_VOID: return LowerINTRINSIC_VOID(Op, DAG);
3016  case ISD::INLINEASM: return LowerINLINEASM(Op, DAG);
3017  case ISD::PREFETCH: return LowerPREFETCH(Op, DAG);
3018  case ISD::READCYCLECOUNTER: return LowerREADCYCLECOUNTER(Op, DAG);
3019  case ISD::MUL:
3020  if (Subtarget.useHVXOps())
3021  return LowerHvxMul(Op, DAG);
3022  break;
3023  case ISD::MULHS:
3024  case ISD::MULHU:
3025  if (Subtarget.useHVXOps())
3026  return LowerHvxMulh(Op, DAG);
3027  break;
3028  }
3029  return SDValue();
3030 }
3031 
3032 /// Returns relocation base for the given PIC jumptable.
3033 SDValue
3035  SelectionDAG &DAG) const {
3036  int Idx = cast<JumpTableSDNode>(Table)->getIndex();
3037  EVT VT = Table.getValueType();
3039  return DAG.getNode(HexagonISD::AT_PCREL, SDLoc(Table), VT, T);
3040 }
3041 
3042 //===----------------------------------------------------------------------===//
3043 // Inline Assembly Support
3044 //===----------------------------------------------------------------------===//
3045 
3048  if (Constraint.size() == 1) {
3049  switch (Constraint[0]) {
3050  case 'q':
3051  case 'v':
3052  if (Subtarget.useHVXOps())
3053  return C_RegisterClass;
3054  break;
3055  case 'a':
3056  return C_RegisterClass;
3057  default:
3058  break;
3059  }
3060  }
3061  return TargetLowering::getConstraintType(Constraint);
3062 }
3063 
3064 std::pair<unsigned, const TargetRegisterClass*>
3066  const TargetRegisterInfo *TRI, StringRef Constraint, MVT VT) const {
3067 
3068  if (Constraint.size() == 1) {
3069  switch (Constraint[0]) {
3070  case 'r': // R0-R31
3071  switch (VT.SimpleTy) {
3072  default:
3073  return {0u, nullptr};
3074  case MVT::i1:
3075  case MVT::i8:
3076  case MVT::i16:
3077  case MVT::i32:
3078  case MVT::f32:
3079  return {0u, &Hexagon::IntRegsRegClass};
3080  case MVT::i64:
3081  case MVT::f64:
3082  return {0u, &Hexagon::DoubleRegsRegClass};
3083  }
3084  break;
3085  case 'a': // M0-M1
3086  if (VT != MVT::i32)
3087  return {0u, nullptr};
3088  return {0u, &Hexagon::ModRegsRegClass};
3089  case 'q': // q0-q3
3090  switch (VT.getSizeInBits()) {
3091  default:
3092  return {0u, nullptr};
3093  case 512:
3094  case 1024:
3095  return {0u, &Hexagon::HvxQRRegClass};
3096  }
3097  break;
3098  case 'v': // V0-V31
3099  switch (VT.getSizeInBits()) {
3100  default:
3101  return {0u, nullptr};
3102  case 512:
3103  return {0u, &Hexagon::HvxVRRegClass};
3104  case 1024:
3105  if (Subtarget.hasV60TOps() && Subtarget.useHVX128BOps())
3106  return {0u, &Hexagon::HvxVRRegClass};
3107  return {0u, &Hexagon::HvxWRRegClass};
3108  case 2048:
3109  return {0u, &Hexagon::HvxWRRegClass};
3110  }
3111  break;
3112  default:
3113  return {0u, nullptr};
3114  }
3115  }
3116 
3117  return TargetLowering::getRegForInlineAsmConstraint(TRI, Constraint, VT);
3118 }
3119 
3120 /// isFPImmLegal - Returns true if the target can instruction select the
3121 /// specified FP immediate natively. If false, the legalizer will
3122 /// materialize the FP immediate as a load from a constant pool.
3124  return Subtarget.hasV5TOps();
3125 }
3126 
3127 /// isLegalAddressingMode - Return true if the addressing mode represented by
3128 /// AM is legal for this target, for a load/store of the specified type.
3130  const AddrMode &AM, Type *Ty,
3131  unsigned AS, Instruction *I) const {
3132  if (Ty->isSized()) {
3133  // When LSR detects uses of the same base address to access different
3134  // types (e.g. unions), it will assume a conservative type for these
3135  // uses:
3136  // LSR Use: Kind=Address of void in addrspace(4294967295), ...
3137  // The type Ty passed here would then be "void". Skip the alignment
3138  // checks, but do not return false right away, since that confuses
3139  // LSR into crashing.
3140  unsigned A = DL.getABITypeAlignment(Ty);
3141  // The base offset must be a multiple of the alignment.
3142  if ((AM.BaseOffs % A) != 0)
3143  return false;
3144  // The shifted offset must fit in 11 bits.
3145  if (!isInt<11>(AM.BaseOffs >> Log2_32(A)))
3146  return false;
3147  }
3148 
3149  // No global is ever allowed as a base.
3150  if (AM.BaseGV)
3151  return false;
3152 
3153  int Scale = AM.Scale;
3154  if (Scale < 0)
3155  Scale = -Scale;
3156  switch (Scale) {
3157  case 0: // No scale reg, "r+i", "r", or just "i".
3158  break;
3159  default: // No scaled addressing mode.
3160  return false;
3161  }
3162  return true;
3163 }
3164 
3165 /// Return true if folding a constant offset with the given GlobalAddress is
3166 /// legal. It is frequently not legal in PIC relocation models.
3168  const {
3169  return HTM.getRelocationModel() == Reloc::Static;
3170 }
3171 
3172 /// isLegalICmpImmediate - Return true if the specified immediate is legal
3173 /// icmp immediate, that is the target has icmp instructions which can compare
3174 /// a register against the immediate without having to materialize the
3175 /// immediate into a register.
3177  return Imm >= -512 && Imm <= 511;
3178 }
3179 
3180 /// IsEligibleForTailCallOptimization - Check whether the call is eligible
3181 /// for tail call optimization. Targets which want to do tail call
3182 /// optimization should implement this function.
3184  SDValue Callee,
3185  CallingConv::ID CalleeCC,
3186  bool isVarArg,
3187  bool isCalleeStructRet,
3188  bool isCallerStructRet,
3189  const SmallVectorImpl<ISD::OutputArg> &Outs,
3190  const SmallVectorImpl<SDValue> &OutVals,
3192  SelectionDAG& DAG) const {
3193  const Function &CallerF = DAG.getMachineFunction().getFunction();
3194  CallingConv::ID CallerCC = CallerF.getCallingConv();
3195  bool CCMatch = CallerCC == CalleeCC;
3196 
3197  // ***************************************************************************
3198  // Look for obvious safe cases to perform tail call optimization that do not
3199  // require ABI changes.
3200  // ***************************************************************************
3201 
3202  // If this is a tail call via a function pointer, then don't do it!
3203  if (!isa<GlobalAddressSDNode>(Callee) &&
3204  !isa<ExternalSymbolSDNode>(Callee)) {
3205  return false;
3206  }
3207 
3208  // Do not optimize if the calling conventions do not match and the conventions
3209  // used are not C or Fast.
3210  if (!CCMatch) {
3211  bool R = (CallerCC == CallingConv::C || CallerCC == CallingConv::Fast);
3212  bool E = (CalleeCC == CallingConv::C || CalleeCC == CallingConv::Fast);
3213  // If R & E, then ok.
3214  if (!R || !E)
3215  return false;
3216  }
3217 
3218  // Do not tail call optimize vararg calls.
3219  if (isVarArg)
3220  return false;
3221 
3222  // Also avoid tail call optimization if either caller or callee uses struct
3223  // return semantics.
3224  if (isCalleeStructRet || isCallerStructRet)
3225  return false;
3226 
3227  // In addition to the cases above, we also disable Tail Call Optimization if
3228  // the calling convention code that at least one outgoing argument needs to
3229  // go on the stack. We cannot check that here because at this point that
3230  // information is not available.
3231  return true;
3232 }
3233 
3234 /// Returns the target specific optimal type for load and store operations as
3235 /// a result of memset, memcpy, and memmove lowering.
3236 ///
3237 /// If DstAlign is zero that means it's safe to destination alignment can
3238 /// satisfy any constraint. Similarly if SrcAlign is zero it means there isn't
3239 /// a need to check it against alignment requirement, probably because the
3240 /// source does not need to be loaded. If 'IsMemset' is true, that means it's
3241 /// expanding a memset. If 'ZeroMemset' is true, that means it's a memset of
3242 /// zero. 'MemcpyStrSrc' indicates whether the memcpy source is constant so it
3243 /// does not need to be loaded. It returns EVT::Other if the type should be
3244 /// determined using generic target-independent logic.
3246  unsigned DstAlign, unsigned SrcAlign, bool IsMemset, bool ZeroMemset,
3247  bool MemcpyStrSrc, MachineFunction &MF) const {
3248 
3249  auto Aligned = [](unsigned GivenA, unsigned MinA) -> bool {
3250  return (GivenA % MinA) == 0;
3251  };
3252 
3253  if (Size >= 8 && Aligned(DstAlign, 8) && (IsMemset || Aligned(SrcAlign, 8)))
3254  return MVT::i64;
3255  if (Size >= 4 && Aligned(DstAlign, 4) && (IsMemset || Aligned(SrcAlign, 4)))
3256  return MVT::i32;
3257  if (Size >= 2 && Aligned(DstAlign, 2) && (IsMemset || Aligned(SrcAlign, 2)))
3258  return MVT::i16;
3259 
3260  return MVT::Other;
3261 }
3262 
3264  unsigned AS, unsigned Align, bool *Fast) const {
3265  if (Fast)
3266  *Fast = false;
3267 
3268  switch (VT.getSimpleVT().SimpleTy) {
3269  default:
3270  return false;
3271  case MVT::v64i8:
3272  case MVT::v128i8:
3273  case MVT::v256i8:
3274  case MVT::v32i16:
3275  case MVT::v64i16:
3276  case MVT::v128i16:
3277  case MVT::v16i32:
3278  case MVT::v32i32:
3279  case MVT::v64i32:
3280  return true;
3281  }
3282  return false;
3283 }
3284 
3285 std::pair<const TargetRegisterClass*, uint8_t>
3286 HexagonTargetLowering::findRepresentativeClass(const TargetRegisterInfo *TRI,
3287  MVT VT) const {
3288  const TargetRegisterClass *RRC = nullptr;
3289 
3290  uint8_t Cost = 1;
3291  switch (VT.SimpleTy) {
3292  default:
3294  case MVT::v64i8:
3295  case MVT::v32i16:
3296  case MVT::v16i32:
3297  RRC = &Hexagon::HvxVRRegClass;
3298  break;
3299  case MVT::v128i8:
3300  case MVT::v64i16:
3301  case MVT::v32i32:
3302  if (Subtarget.hasV60TOps() && Subtarget.useHVXOps() &&
3303  Subtarget.useHVX128BOps())
3304  RRC = &Hexagon::HvxVRRegClass;
3305  else
3306  RRC = &Hexagon::HvxWRRegClass;
3307  break;
3308  case MVT::v256i8:
3309  case MVT::v128i16:
3310  case MVT::v64i32:
3311  RRC = &Hexagon::HvxWRRegClass;
3312  break;
3313  }
3314  return std::make_pair(RRC, Cost);
3315 }
3316 
3318  AtomicOrdering Ord) const {
3319  BasicBlock *BB = Builder.GetInsertBlock();
3320  Module *M = BB->getParent()->getParent();
3321  Type *Ty = cast<PointerType>(Addr->getType())->getElementType();
3322  unsigned SZ = Ty->getPrimitiveSizeInBits();
3323  assert((SZ == 32 || SZ == 64) && "Only 32/64-bit atomic loads supported");
3324  Intrinsic::ID IntID = (SZ == 32) ? Intrinsic::hexagon_L2_loadw_locked
3325  : Intrinsic::hexagon_L4_loadd_locked;
3326  Value *Fn = Intrinsic::getDeclaration(M, IntID);
3327  return Builder.CreateCall(Fn, Addr, "larx");
3328 }
3329 
3330 /// Perform a store-conditional operation to Addr. Return the status of the
3331 /// store. This should be 0 if the store succeeded, non-zero otherwise.
3333  Value *Val, Value *Addr, AtomicOrdering Ord) const {
3334  BasicBlock *BB = Builder.GetInsertBlock();
3335  Module *M = BB->getParent()->getParent();
3336  Type *Ty = Val->getType();
3337  unsigned SZ = Ty->getPrimitiveSizeInBits();
3338  assert((SZ == 32 || SZ == 64) && "Only 32/64-bit atomic stores supported");
3339  Intrinsic::ID IntID = (SZ == 32) ? Intrinsic::hexagon_S2_storew_locked
3340  : Intrinsic::hexagon_S4_stored_locked;
3341  Value *Fn = Intrinsic::getDeclaration(M, IntID);
3342  Value *Call = Builder.CreateCall(Fn, {Addr, Val}, "stcx");
3343  Value *Cmp = Builder.CreateICmpEQ(Call, Builder.getInt32(0), "");
3344  Value *Ext = Builder.CreateZExt(Cmp, Type::getInt32Ty(M->getContext()));
3345  return Ext;
3346 }
3347 
3350  // Do not expand loads and stores that don't exceed 64 bits.
3351  return LI->getType()->getPrimitiveSizeInBits() > 64
3354 }
3355 
3357  // Do not expand loads and stores that don't exceed 64 bits.
3358  return SI->getValueOperand()->getType()->getPrimitiveSizeInBits() > 64;
3359 }
3360 
3362  AtomicCmpXchgInst *AI) const {
3363  const DataLayout &DL = AI->getModule()->getDataLayout();
3364  unsigned Size = DL.getTypeStoreSize(AI->getCompareOperand()->getType());
3365  return Size >= 4 && Size <= 8;
3366 }
virtual std::pair< const TargetRegisterClass *, uint8_t > findRepresentativeClass(const TargetRegisterInfo *TRI, MVT VT) const
Return the largest legal super-reg register class of the register class for the specified type and it...
SDValue getStore(SDValue Chain, const SDLoc &dl, SDValue Val, SDValue Ptr, MachinePointerInfo PtrInfo, unsigned Alignment=0, MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes())
Helper function to build ISD::STORE nodes.
bool isMachineConstantPoolEntry() const
Type * getVectorElementType() const
Definition: Type.h:368
void setFrameAddressIsTaken(bool T)
uint64_t CallInst * C
SDValue LowerINSERT_VECTOR_ELT(SDValue Op, SelectionDAG &DAG) const
BITCAST - This operator converts between integer, vector and FP values, as if the value was stored to...
Definition: ISDOpcodes.h:546
X = FP_ROUND(Y, TRUNC) - Rounding &#39;Y&#39; from a larger floating point type down to the precision of the ...
Definition: ISDOpcodes.h:513
bool isFPImmLegal(const APFloat &Imm, EVT VT) const override
isFPImmLegal - Returns true if the target can instruction select the specified FP immediate natively...
Value * getValueOperand()
Definition: Instructions.h:395
static MVT getIntegerVT(unsigned BitWidth)
void AnalyzeCallResult(const SmallVectorImpl< ISD::InputArg > &Ins, CCAssignFn Fn)
AnalyzeCallResult - Analyze the return values of a call, incorporating info about the passed values i...
static SDValue LowerCallResult(SDValue Chain, SDValue InFlag, const SmallVectorImpl< CCValAssign > &RVLocs, const SDLoc &dl, SelectionDAG &DAG, SmallVectorImpl< SDValue > &InVals)
LowerCallResult - Lower the result values of a call into the appropriate copies out of appropriate ph...
Fast - This calling convention attempts to make calls as fast as possible (e.g.
Definition: CallingConv.h:43
A parsed version of the target data layout string in and methods for querying it. ...
Definition: DataLayout.h:109
constexpr char Align[]
Key for Kernel::Arg::Metadata::mAlign.
FMINNUM/FMAXNUM - Perform floating-point minimum or maximum on two values.
Definition: ISDOpcodes.h:570
EVT getValueType() const
Return the ValueType of the referenced return value.
This represents an addressing mode of: BaseGV + BaseOffs + BaseReg + Scale*ScaleReg If BaseGV is null...
bool isInteger() const
Return true if this is an integer or a vector integer type.
static void commuteMask(MutableArrayRef< int > Mask)
Change values in a shuffle permute mask assuming the two vector operands have swapped position...
bool getTgtMemIntrinsic(IntrinsicInfo &Info, const CallInst &I, MachineFunction &MF, unsigned Intrinsic) const override
Given an intrinsic, checks if on the target the intrinsic will need to map to a MemIntrinsicNode (tou...
void setLoadExtAction(unsigned ExtType, MVT ValVT, MVT MemVT, LegalizeAction Action)
Indicate that the specified load with extension does not work with the specified type and indicate wh...
bool isUndef() const
raw_ostream & errs()
This returns a reference to a raw_ostream for standard error.
SDValue LowerVECTOR_SHUFFLE(SDValue Op, SelectionDAG &DAG) const
const GlobalValue * getGlobal() const
uint64_t getZExtValue() const
Get zero extended value.
Definition: APInt.h:1542
ArrayRef< T > take_front(size_t N=1) const
Return a copy of *this with only the first N elements.
Definition: ArrayRef.h:213
#define R4(n)
std::pair< unsigned, const TargetRegisterClass * > getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, StringRef Constraint, MVT VT) const override
Given a physical register constraint (e.g.
GCNRegPressure max(const GCNRegPressure &P1, const GCNRegPressure &P2)
unsigned getOpcode() const
Return the SelectionDAG opcode value for this node.
LLVMContext & Context
void setMinimumJumpTableEntries(unsigned Val)
Indicate the minimum number of blocks to generate jump tables.
SDValue getCALLSEQ_END(SDValue Chain, SDValue Op1, SDValue Op2, SDValue InGlue, const SDLoc &DL)
Return a new CALLSEQ_END node, which always must have a glue result (to ensure it&#39;s not CSE&#39;d)...
Definition: SelectionDAG.h:835
unsigned getFrameRegister(const MachineFunction &MF) const override
bool isLegalICmpImmediate(int64_t Imm) const override
isLegalICmpImmediate - Return true if the specified immediate is legal icmp immediate, that is the target has icmp instructions which can compare a register against the immediate without having to materialize the immediate into a register.
ConstraintType getConstraintType(StringRef Constraint) const override
Given a constraint, return the type of constraint it is for this target.
EXTRACT_SUBVECTOR(VECTOR, IDX) - Returns a subvector from VECTOR (an vector value) starting with the ...
Definition: ISDOpcodes.h:334
BR_CC - Conditional branch.
Definition: ISDOpcodes.h:618
Compute iterated dominance frontiers using a linear time algorithm.
Definition: AllocatorList.h:24
static MVT getVectorVT(MVT VT, unsigned NumElements)
VECTOR_SHUFFLE(VEC1, VEC2) - Returns a vector, of the same type as VEC1/VEC2.
Definition: ISDOpcodes.h:343
A Module instance is used to store all the information related to an LLVM module. ...
Definition: Module.h:63
bool isSized(SmallPtrSetImpl< Type *> *Visited=nullptr) const
Return true if it makes sense to take the size of this type.
Definition: Type.h:262
LLVM_ATTRIBUTE_ALWAYS_INLINE size_type size() const
Definition: SmallVector.h:136
an instruction that atomically checks whether a specified value is in a memory location, and, if it is, stores a new value there.
Definition: Instructions.h:514
ZERO_EXTEND_VECTOR_INREG(Vector) - This operator represents an in-register zero-extension of the low ...
Definition: ISDOpcodes.h:495
bool isVector() const
Return true if this is a vector value type.
unsigned createVirtualRegister(const TargetRegisterClass *RegClass)
createVirtualRegister - Create and return a new virtual register in the function with the specified r...
bool getPostIndexedAddressParts(SDNode *N, SDNode *Op, SDValue &Base, SDValue &Offset, ISD::MemIndexedMode &AM, SelectionDAG &DAG) const override
getPostIndexedAddressParts - returns true by value, base pointer and offset pointer and addressing mo...
void addLiveIn(unsigned Reg, unsigned vreg=0)
addLiveIn - Add the specified register as a live-in.
Carry-setting nodes for multiple precision addition and subtraction.
Definition: ISDOpcodes.h:223
static cl::opt< bool > EmitJumpTables("hexagon-emit-jump-tables", cl::init(true), cl::Hidden, cl::desc("Control jump table emission on Hexagon target"))
EVT getValueType(unsigned ResNo) const
Return the type of a specified result.
bool isFMAFasterThanFMulAndFAdd(EVT) const override
Return true if an FMA operation is faster than a pair of mul and add instructions.
unsigned addLiveIn(unsigned PReg, const TargetRegisterClass *RC)
addLiveIn - Add the specified physical register as a live-in value and create a corresponding virtual...
void AnalyzeFormalArguments(const SmallVectorImpl< ISD::InputArg > &Ins, CCAssignFn Fn)
AnalyzeFormalArguments - Analyze an array of argument values, incorporating info about the formals in...
SDValue LowerFRAMEADDR(SDValue Op, SelectionDAG &DAG) const
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE size_t size() const
size - Get the string size.
Definition: StringRef.h:138
static const MVT LegalW64[]
Y = RRC X, rotate right via carry.
static const MVT LegalW128[]
STACKRESTORE has two operands, an input chain and a pointer to restore to it returns an output chain...
Definition: ISDOpcodes.h:667
This class represents a function call, abstracting a target machine&#39;s calling convention.
MVT getSimpleVT() const
Return the SimpleValueType held in the specified simple EVT.
Definition: ValueTypes.h:253
RESULT, BOOL = [SU]ADDO(LHS, RHS) - Overflow-aware nodes for addition.
Definition: ISDOpcodes.h:251
unsigned getVectorNumElements() const
ArrayRef< MVT > getHVXElementTypes() const
unsigned getStoreSizeInBits() const
Return the number of bits overwritten by a store of the specified value type.
LLVMContext & getContext() const
All values hold a context through their type.
Definition: Value.cpp:738
SDValue LowerDYNAMIC_STACKALLOC(SDValue Op, SelectionDAG &DAG) const
static bool RetCC_Hexagon64(unsigned ValNo, MVT ValVT, MVT LocVT, CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags, CCState &State)
virtual std::pair< unsigned, const TargetRegisterClass * > getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI, StringRef Constraint, MVT VT) const
Given a physical register constraint (e.g.
Hexagon target-specific information for each MachineFunction.
SDValue LowerVSELECT(SDValue Op, SelectionDAG &DAG) const
unsigned second
void setBooleanVectorContents(BooleanContent Ty)
Specify how the target extends the result of a vector boolean value from a vector of i1 to a wider ty...
bool all_of(R &&range, UnaryPredicate P)
Provide wrappers to std::all_of which take ranges instead of having to pass begin/end explicitly...
Definition: STLExtras.h:814
SDValue LowerATOMIC_FENCE(SDValue Op, SelectionDAG &DAG) const
F(f)
SDValue LowerEXTRACT_SUBVECTOR(SDValue Op, SelectionDAG &DAG) const
An instruction for reading from memory.
Definition: Instructions.h:164
SIGN_EXTEND_VECTOR_INREG(Vector) - This operator represents an in-register sign-extension of the low ...
Definition: ISDOpcodes.h:486
MachineFunction & getMachineFunction() const
SDNode * getNode() const
get the SDNode which holds the desired result
#define R2(n)
SDValue getTargetExternalSymbol(const char *Sym, EVT VT, unsigned char TargetFlags=0)
SDValue getNode(unsigned Opcode, const SDLoc &DL, EVT VT, ArrayRef< SDUse > Ops)
Gets or creates the specified node.
bool isVectorTy() const
True if this is an instance of VectorType.
Definition: Type.h:227
bool CheckReturn(const SmallVectorImpl< ISD::OutputArg > &ArgsFlags, CCAssignFn Fn)
CheckReturn - Analyze the return values of a function, returning true if the return can be performed ...
AtomicExpansionKind
Enum that specifies what an atomic load/AtomicRMWInst is expanded to, if at all.
Same for subtraction.
Definition: ISDOpcodes.h:254
bool isOperationLegalOrCustom(unsigned Op, EVT VT) const
Return true if the specified operation is legal on this target or can be made legal with custom lower...
INSERT_SUBVECTOR(VECTOR1, VECTOR2, IDX) - Returns a vector with VECTOR2 inserted into VECTOR1 at the ...
Definition: ISDOpcodes.h:329
The address of the GOT.
Definition: ISDOpcodes.h:66
OUTCHAIN = ATOMIC_FENCE(INCHAIN, ordering, scope) This corresponds to the fence instruction.
Definition: ISDOpcodes.h:749
SDValue LowerToTLSLocalExecModel(GlobalAddressSDNode *GA, SelectionDAG &DAG) const
Select with condition operator - This selects between a true value and a false value (ops #2 and #3) ...
Definition: ISDOpcodes.h:405
bool isUnsignedIntSetCC(CondCode Code)
Return true if this is a setcc instruction that performs an unsigned comparison when used with intege...
Definition: ISDOpcodes.h:956
void setTruncStoreAction(MVT ValVT, MVT MemVT, LegalizeAction Action)
Indicate that the specified truncating store does not work with the specified type and indicate what ...
RESULT,OUTCHAIN = INTRINSIC_W_CHAIN(INCHAIN, INTRINSICID, arg1, ...) This node represents a target in...
Definition: ISDOpcodes.h:159
bool isMemLoc() const
bool hasStructRetAttr() const
Determine if the function returns a structure through first or second pointer argument.
Definition: Function.h:525
SDIVREM/UDIVREM - Divide two integers and produce both a quotient and remainder result.
Definition: ISDOpcodes.h:210
SHL_PARTS/SRA_PARTS/SRL_PARTS - These operators are used for expanded integer shift operations...
Definition: ISDOpcodes.h:434
SDValue getIntPtrConstant(uint64_t Val, const SDLoc &DL, bool isTarget=false)
The address of a basic block.
Definition: Constants.h:813
void setMaxAtomicSizeInBitsSupported(unsigned SizeInBits)
Set the maximum atomic operation size supported by the backend.
Value * emitStoreConditional(IRBuilder<> &Builder, Value *Val, Value *Addr, AtomicOrdering Ord) const override
Perform a store-conditional operation to Addr.
const DataLayout & getDataLayout() const
Get the data layout for the module&#39;s target platform.
Definition: Module.cpp:361
SDValue LowerBUILD_VECTOR(SDValue Op, SelectionDAG &DAG) const
static const MVT LegalV128[]
Shift and rotation operations.
Definition: ISDOpcodes.h:380
LLVMContext & getContext() const
Get the global data context.
Definition: Module.h:237
bool shouldExpandBuildVectorWithShuffles(EVT VT, unsigned DefinedValues) const override
SDValue getTargetExtractSubreg(int SRIdx, const SDLoc &DL, EVT VT, SDValue Operand)
A convenience function for creating TargetInstrInfo::EXTRACT_SUBREG nodes.
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), MachineInstr opcode, and operands.
const HexagonRegisterInfo * getRegisterInfo() const override
BUILD_PAIR - This is the opposite of EXTRACT_ELEMENT in some ways.
Definition: ISDOpcodes.h:191
This class consists of common code factored out of the SmallVector class to reduce code duplication b...
Definition: APFloat.h:42
void addLoc(const CCValAssign &V)
bool isIntegerTy() const
True if this is an instance of IntegerType.
Definition: Type.h:197
SDValue LowerConstantPool(SDValue Op, SelectionDAG &DAG) const
This provides a uniform API for creating instructions and inserting them into a basic block: either a...
Definition: IRBuilder.h:668
SDValue LowerEH_RETURN(SDValue Op, SelectionDAG &DAG) const
Reg
All possible values of the reg field in the ModR/M byte.
void setCondCodeAction(ISD::CondCode CC, MVT VT, LegalizeAction Action)
Indicate that the specified condition code is or isn&#39;t supported on the target and indicate what to d...
SimpleValueType SimpleTy
#define Hexagon_PointerSize
Definition: Hexagon.h:20
The MachineFrameInfo class represents an abstract stack frame until prolog/epilog code is inserted...
SDValue getEntryNode() const
Return the token chain corresponding to the entry of the function.
Definition: SelectionDAG.h:449
void setOperationAction(unsigned Op, MVT VT, LegalizeAction Action)
Indicate that the specified operation does not work with the specified type and indicate what to do a...
const DataLayout & getDataLayout() const
Definition: SelectionDAG.h:390
SDVTList getVTList(EVT VT)
Return an SDVTList that represents the list of values specified.
FRAMEADDR, RETURNADDR - These nodes represent llvm.frameaddress and llvm.returnaddress on the DAG...
Definition: ISDOpcodes.h:73
LocInfo getLocInfo() const
This class defines information used to lower LLVM code to legal SelectionDAG operators that the targe...
This file implements a class to represent arbitrary precision integral constant values and operations...
INLINEASM - Represents an inline asm block.
Definition: ISDOpcodes.h:635
This represents a list of ValueType&#39;s that has been intern&#39;d by a SelectionDAG.
bool isShuffleMaskLegal(ArrayRef< int > Mask, EVT VT) const override
Targets can use this to indicate that they only support some VECTOR_SHUFFLE operations, those with specific masks.
SmallVector< ISD::InputArg, 32 > Ins
AtomicOrdering
Atomic ordering for LLVM&#39;s memory model.
STACKSAVE - STACKSAVE has one operand, an input chain.
Definition: ISDOpcodes.h:663
unsigned getSizeInBits() const
int64_t getSExtValue() const
unsigned getSizeInBits() const
Return the size of the specified value type in bits.
Definition: ValueTypes.h:292
int64_t getSExtValue() const
Get sign extended value.
Definition: APInt.h:1554
Type * getType() const
All values are typed, get the type of this value.
Definition: Value.h:245
MachineFunction & getMachineFunction() const
Definition: SelectionDAG.h:387
void computeRegisterProperties(const TargetRegisterInfo *TRI)
Once all of the register classes are added, this allows us to compute derived properties we expose...
[SU]INT_TO_FP - These operators convert integers (whose interpreted sign depends on the first letter)...
Definition: ISDOpcodes.h:456
SDValue getRegisterMask(const uint32_t *RegMask)
SDValue LowerVECTOR_SHIFT(SDValue Op, SelectionDAG &DAG) const
#define T
BasicBlock * GetInsertBlock() const
Definition: IRBuilder.h:122
Select with a vector condition (op #0) and two vector operands (ops #1 and #2), returning a vector re...
Definition: ISDOpcodes.h:399
Simple integer binary arithmetic operators.
Definition: ISDOpcodes.h:201
static bool CC_Hexagon32(unsigned ValNo, MVT ValVT, MVT LocVT, CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags, CCState &State)
SmallVector< ISD::OutputArg, 32 > Outs
ArrayRef - Represent a constant reference to an array (0 or more elements consecutively in memory)...
Definition: APInt.h:33
const APInt & getValue() const
Return the constant as an APInt value reference.
Definition: Constants.h:138
SDValue LowerSETCC(SDValue Op, SelectionDAG &DAG) const
SDValue getUNDEF(EVT VT)
Return an UNDEF node. UNDEF does not have a useful SDLoc.
Definition: SelectionDAG.h:851
Reloc::Model getRelocationModel() const
Returns the code generation relocation model.
An instruction for storing to memory.
Definition: Instructions.h:306
bool mayBeEmittedAsTailCall(const CallInst *CI) const override
Return true if the target may be able emit the call instruction as a tail call.
CondCode
ISD::CondCode enum - These are ordered carefully to make the bitfields below work out...
Definition: ISDOpcodes.h:917
Value * CreateZExt(Value *V, Type *DestTy, const Twine &Name="")
Definition: IRBuilder.h:1387
READCYCLECOUNTER - This corresponds to the readcyclecounter intrinsic.
Definition: ISDOpcodes.h:715
ANY_EXTEND_VECTOR_INREG(Vector) - This operator represents an in-register any-extension of the low la...
Definition: ISDOpcodes.h:473
void setMinCmpXchgSizeInBits(unsigned SizeInBits)
Sets the minimum cmpxchg or ll/sc size supported by the backend.
bool allowTruncateForTailCall(Type *Ty1, Type *Ty2) const override
Return true if a truncation from FromTy to ToTy is permitted when deciding whether a call is in tail ...
bool isSignedIntSetCC(CondCode Code)
Return true if this is a setcc instruction that performs a signed comparison when used with integer o...
Definition: ISDOpcodes.h:950
static cl::opt< int > MinimumJumpTables("minimum-jump-tables", cl::Hidden, cl::ZeroOrMore, cl::init(5), cl::desc("Set minimum jump tables"))
RESULT = INTRINSIC_WO_CHAIN(INTRINSICID, arg1, arg2, ...) This node represents a target intrinsic fun...
Definition: ISDOpcodes.h:151
amdgpu Simplify well known AMD library false Value * Callee
Function * getDeclaration(Module *M, ID id, ArrayRef< Type *> Tys=None)
Create or insert an LLVM Function declaration for an intrinsic, and return it.
Definition: Function.cpp:979
MVT getVectorElementType() const
SDValue LowerToTLSInitialExecModel(GlobalAddressSDNode *GA, SelectionDAG &DAG) const
Value * getOperand(unsigned i) const
Definition: User.h:154
const DataLayout & getDataLayout() const
Return the DataLayout attached to the Module associated to this MF.
unsigned getByValSize() const
This class is used to represent ISD::STORE nodes.
bool isLegalAddressingMode(const DataLayout &DL, const AddrMode &AM, Type *Ty, unsigned AS, Instruction *I=nullptr) const override
isLegalAddressingMode - Return true if the addressing mode represented by AM is legal for this target...
FP_TO_[US]INT - Convert a floating point value to a signed or unsigned integer.
Definition: ISDOpcodes.h:499
uint16_t MCPhysReg
An unsigned integer type large enough to represent all physical registers, but not necessarily virtua...
static CCValAssign getReg(unsigned ValNo, MVT ValVT, unsigned RegNo, MVT LocVT, LocInfo HTP)
Flag
These should be considered private to the implementation of the MCInstrDesc class.
Definition: MCInstrDesc.h:121
BUILD_VECTOR(ELT0, ELT1, ELT2, ELT3,...) - Return a vector with the specified, possibly variable...
Definition: ISDOpcodes.h:303
The memory access is volatile.
SDValue LowerINTRINSIC_VOID(SDValue Op, SelectionDAG &DAG) const
bool isNegative() const
Determine sign of this APInt.
Definition: APInt.h:357
#define P(N)
initializer< Ty > init(const Ty &Val)
Definition: CommandLine.h:406
OUTCHAIN = INTRINSIC_VOID(INCHAIN, INTRINSICID, arg1, arg2, ...) This node represents a target intrin...
Definition: ISDOpcodes.h:166
unsigned const MachineRegisterInfo * MRI
MutableArrayRef - Represent a mutable reference to an array (0 or more elements consecutively in memo...
Definition: ArrayRef.h:292
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...
constexpr bool isPowerOf2_32(uint32_t Value)
Return true if the argument is a power of two > 0.
Definition: MathExtras.h:421
Machine Value Type.
TargetLoweringBase::LegalizeTypeAction getPreferredVectorAction(EVT VT) const override
Return the preferred vector type legalization action.
LLVM Basic Block Representation.
Definition: BasicBlock.h:59
The instances of the Type class are immutable: once they are created, they are never changed...
Definition: Type.h:46
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
This is an important class for using LLVM in a threaded context.
Definition: LLVMContext.h:69
void addRegisterClass(MVT VT, const TargetRegisterClass *RC)
Add the specified register class as an available regclass for the specified value type...
virtual ConstraintType getConstraintType(StringRef Constraint) const
Given a constraint, return the type of constraint it is for this target.
Simple binary floating point operators.
Definition: ISDOpcodes.h:260
static bool getIndexedAddressParts(SDNode *Ptr, EVT VT, SDValue &Base, SDValue &Offset, bool &IsInc, SelectionDAG &DAG)
MachineFrameInfo & getFrameInfo()
getFrameInfo - Return the frame info object for the current function.
unsigned getVectorNumElements() const
Given a vector type, return the number of elements it contains.
Definition: ValueTypes.h:273
size_t size() const
size - Get the array size.
Definition: ArrayRef.h:150
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
This is an important base class in LLVM.
Definition: Constant.h:42
VAEND, VASTART - VAEND and VASTART have three operands: an input chain, pointer, and a SRCVALUE...
Definition: ISDOpcodes.h:696
const SDValue & getOperand(unsigned Num) const
static bool CC_Hexagon(unsigned ValNo, MVT ValVT, MVT LocVT, CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags, CCState &State)
static cl::opt< int > MaxStoresPerMemmoveOptSizeCL("max-store-memmove-Os", cl::Hidden, cl::ZeroOrMore, cl::init(4), cl::desc("Max #stores to inline memmove"))
INSERT_VECTOR_ELT(VECTOR, VAL, IDX) - Returns VECTOR with the element at IDX replaced with VAL...
Definition: ISDOpcodes.h:308
#define H(x, y, z)
Definition: MD5.cpp:57
Carry-using nodes for multiple precision addition and subtraction.
Definition: ISDOpcodes.h:232
bool shouldExpandAtomicStoreInIR(StoreInst *SI) const override
Returns true if the given (atomic) store should be expanded by the IR-level AtomicExpand pass into an...
SDValue LowerToTLSGeneralDynamicModel(GlobalAddressSDNode *GA, SelectionDAG &DAG) const
OperandFlags
These are flags set on operands, but should be considered private, all access should go through the M...
Definition: MCInstrDesc.h:41
ConstantFP - Floating Point Values [float, double].
Definition: Constants.h:264
SDValue getCALLSEQ_START(SDValue Chain, uint64_t InSize, uint64_t OutSize, const SDLoc &DL)
Return a new CALLSEQ_START node, that starts new call frame, in which InSize bytes are set up inside ...
Definition: SelectionDAG.h:823
void setBooleanContents(BooleanContent Ty)
Specify how the target extends the result of integer and floating point boolean values from i1 to a w...
bool isTruncateFree(Type *Ty1, Type *Ty2) const override
Return true if it&#39;s free to truncate a value of type FromTy to type ToTy.
static mvt_range fp_valuetypes()
static unsigned getNumOperandRegisters(unsigned Flag)
getNumOperandRegisters - Extract the number of registers field from the inline asm operand flag...
Definition: InlineAsm.h:336
SDValue LowerEXTRACT_VECTOR_ELT(SDValue Op, SelectionDAG &DAG) const
static SDValue LowerFRAMEADDR(SDValue Op, SelectionDAG &DAG, const SparcSubtarget *Subtarget)
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
const APInt & getAPIntValue() const
static unsigned getKind(unsigned Flags)
Definition: InlineAsm.h:325
std::string getEVTString() const
This function returns value type as a string, e.g. "i32".
Definition: ValueTypes.cpp:119
void setPrefFunctionAlignment(unsigned Align)
Set the target&#39;s preferred function alignment.
AssertSext, AssertZext - These nodes record if a register contains a value that has already been zero...
Definition: ISDOpcodes.h:57
static mvt_range vector_valuetypes()
Value * CreateICmpEQ(Value *LHS, Value *RHS, const Twine &Name="")
Definition: IRBuilder.h:1550
Class to represent integer types.
Definition: DerivedTypes.h:40
static MVT getVT(Type *Ty, bool HandleUnknown=false)
Return the value type corresponding to the specified type.
Definition: ValueTypes.cpp:284
Constant Vector Declarations.
Definition: Constants.h:491
VAARG - VAARG has four operands: an input chain, a pointer, a SRCVALUE, and the alignment.
Definition: ISDOpcodes.h:687
auto find_if(R &&Range, UnaryPredicate P) -> decltype(adl_begin(Range))
Provide wrappers to std::find_if which take ranges instead of having to pass begin/end explicitly...
Definition: STLExtras.h:842
void AddPromotedToType(unsigned Opc, MVT OrigVT, MVT DestVT)
If Opc/OrigVT is specified as being promoted, the promotion code defaults to trying a larger integer/...
unsigned MaxStoresPerMemmove
Specify maximum bytes of store instructions per memmove call.
X = FP_EXTEND(Y) - Extend a smaller FP type into a larger FP type.
Definition: ISDOpcodes.h:531
Extended Value Type.
Definition: ValueTypes.h:34
const AMDGPUAS & AS
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
This structure contains all information that is necessary for lowering calls.
static SDValue CreateCopyOfByValArgument(SDValue Src, SDValue Dst, SDValue Chain, ISD::ArgFlagsTy Flags, SelectionDAG &DAG, const SDLoc &dl)
CreateCopyOfByValArgument - Make a copy of an aggregate at address specified by "Src" to address "Dst...
auto find(R &&Range, const T &Val) -> decltype(adl_begin(Range))
Provide wrappers to std::find which take ranges instead of having to pass begin/end explicitly...
Definition: STLExtras.h:835
static bool isSExtFree(SDValue N)
This class contains a discriminated union of information about pointers in memory operands...
unsigned getNumOperands() const
Return the number of values used by this operation.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
SDValue LowerCallResult(SDValue Chain, SDValue InFlag, CallingConv::ID CallConv, bool isVarArg, const SmallVectorImpl< ISD::InputArg > &Ins, const SDLoc &dl, SelectionDAG &DAG, SmallVectorImpl< SDValue > &InVals, const SmallVectorImpl< SDValue > &OutVals, SDValue Callee) const
LowerCallResult - Lower the result values of an ISD::CALL into the appropriate copies out of appropri...
SDValue getPICJumpTableRelocBase(SDValue Table, SelectionDAG &DAG) const override
Returns relocation base for the given PIC jumptable.
static bool CC_HexagonVector(unsigned ValNo, MVT ValVT, MVT LocVT, CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags, CCState &State)
SDValue getLoad(EVT VT, const SDLoc &dl, SDValue Chain, SDValue Ptr, MachinePointerInfo PtrInfo, unsigned Alignment=0, MachineMemOperand::Flags MMOFlags=MachineMemOperand::MONone, const AAMDNodes &AAInfo=AAMDNodes(), const MDNode *Ranges=nullptr)
Loads are not normal binary operators: their result type is not determined by their operands...
unsigned first
SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override
This callback is invoked for operations that are unsupported by the target, which are registered to u...
SDValue LowerReturn(SDValue Chain, CallingConv::ID CallConv, bool isVarArg, const SmallVectorImpl< ISD::OutputArg > &Outs, const SmallVectorImpl< SDValue > &OutVals, const SDLoc &dl, SelectionDAG &DAG) const override
This hook must be implemented to lower outgoing return values, described by the Outs array...
The memory access writes data.
const APFloat & getValueAPF() const
Definition: Constants.h:294
SDValue getBitcast(EVT VT, SDValue V)
Return a bitcast using the SDLoc of the value operand, and casting to the provided type...
bool isFloatingPoint() const
Return true if this is a FP or a vector FP type.
SDValue getTargetConstantPool(const Constant *C, EVT VT, unsigned Align=0, int Offset=0, unsigned char TargetFlags=0)
Definition: SelectionDAG.h:620
SDValue getTargetJumpTable(int JTI, EVT VT, unsigned char TargetFlags=0)
Definition: SelectionDAG.h:614
TokenFactor - This node takes multiple tokens as input and produces a single token result...
Definition: ISDOpcodes.h:50
const char * getTargetNodeName(unsigned Opcode) const override
This method returns the name of a target specific DAG node.
void dump() const
Dump this node, for debugging.
static IntegerType * get(LLVMContext &C, unsigned NumBits)
This static method is the primary way of constructing an IntegerType.
Definition: Type.cpp:240
bool isHVXVectorType(MVT VecTy, bool IncludeBool=false) const
#define HEXAGON_LRFP_SIZE
Definition: Hexagon.h:27
unsigned getNumOperands() const
Definition: User.h:176
CCState - This class holds information needed while lowering arguments and return values...
This is the shared class of boolean and integer constants.
Definition: Constants.h:84
SDValue LowerCONCAT_VECTORS(SDValue Op, SelectionDAG &DAG) const
EXTRACT_VECTOR_ELT(VECTOR, IDX) - Returns a single element from VECTOR identified by the (potentially...
Definition: ISDOpcodes.h:315
SDValue LowerGLOBAL_OFFSET_TABLE(SDValue Op, SelectionDAG &DAG) const
#define HEXAGON_GOT_SYM_NAME
Definition: Hexagon.h:43
CallingConv::ID getCallingConv() const
getCallingConv()/setCallingConv(CC) - These method get and set the calling convention of this functio...
Definition: Function.h:194
This is used to represent a portion of an LLVM function in a low-level Data Dependence DAG representa...
Definition: SelectionDAG.h:210
SDValue getZExtOrTrunc(SDValue Op, const SDLoc &DL, EVT VT)
Convert Op, which must be of integer type, to the integer type VT, by either zero-extending or trunca...
SDValue LowerINTRINSIC_WO_CHAIN(SDValue Op, SelectionDAG &DAG) const
This is a &#39;vector&#39; (really, a variable-sized array), optimized for the case when the array is small...
Definition: SmallVector.h:862
Module.h This file contains the declarations for the Module class.
CCValAssign - Represent assignment of one arg/retval to a location.
SDValue LowerFormalArguments(SDValue Chain, CallingConv::ID CallConv, bool isVarArg, const SmallVectorImpl< ISD::InputArg > &Ins, const SDLoc &dl, SelectionDAG &DAG, SmallVectorImpl< SDValue > &InVals) const override
This hook must be implemented to lower the incoming (formal) arguments, described by the Ins array...
SDValue getMemcpy(SDValue Chain, const SDLoc &dl, SDValue Dst, SDValue Src, SDValue Size, unsigned Align, bool isVol, bool AlwaysInline, bool isTailCall, MachinePointerInfo DstPtrInfo, MachinePointerInfo SrcPtrInfo)
iterator end() const
Definition: ArrayRef.h:139
unsigned getABITypeAlignment(Type *Ty) const
Returns the minimum ABI-required alignment for the specified type.
Definition: DataLayout.cpp:682
const DataFlowGraph & G
Definition: RDFGraph.cpp:211
Byte Swap and Counting operators.
Definition: ISDOpcodes.h:383
MO_PCREL - On a symbol operand, indicates a PC-relative relocation Used for computing a global addres...
bool shouldExpandAtomicCmpXchgInIR(AtomicCmpXchgInst *AI) const override
Returns true if the given atomic cmpxchg should be expanded by the IR-level AtomicExpand pass into a ...
CHAIN = SC CHAIN, Imm128 - System call.
ConstantInt * getInt32(uint32_t C)
Get a constant 32-bit value.
Definition: IRBuilder.h:308
int CreateFixedObject(uint64_t Size, int64_t SPOffset, bool IsImmutable, bool isAliased=false)
Create a new object at a fixed location on the stack.
SDValue LowerGLOBALADDRESS(SDValue Op, SelectionDAG &DAG) const
const Constant * getConstVal() const
Wrapper class for IR location info (IR ordering and DebugLoc) to be passed into SDNode creation funct...
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:559
Represents one node in the SelectionDAG.
SDValue getCopyToReg(SDValue Chain, const SDLoc &dl, unsigned Reg, SDValue N)
Definition: SelectionDAG.h:660
const Function & getFunction() const
Return the LLVM function that this machine code represents.
raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition: Debug.cpp:132
static mvt_range integer_valuetypes()
unsigned Log2_32(uint32_t Value)
Return the floor log base 2 of the specified value, -1 if the value is zero.
Definition: MathExtras.h:531
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition: BitVector.h:923
SDValue LowerINLINEASM(SDValue Op, SelectionDAG &DAG) const
const Module * getModule() const
Return the module owning the function this instruction belongs to or nullptr it the function does not...
Definition: Instruction.cpp:55
void setIndexedLoadAction(unsigned IdxMode, MVT VT, LegalizeAction Action)
Indicate that the specified indexed load does or does not work with the specified type and indicate w...
Class for arbitrary precision integers.
Definition: APInt.h:69
unsigned getByValAlign() const
SDValue LowerGlobalTLSAddress(SDValue Op, SelectionDAG &DAG) const
SDValue getConstantFP(double Val, const SDLoc &DL, EVT VT, bool isTarget=false)
Create a ConstantFPSDNode wrapping a constant value.
static unsigned getReg(const void *D, unsigned RC, unsigned RegNo)
A "pseudo-class" with methods for operating on BUILD_VECTORs.
Select(COND, TRUEVAL, FALSEVAL).
Definition: ISDOpcodes.h:390
void setMinFunctionAlignment(unsigned Align)
Set the target&#39;s minimum function alignment (in log2(bytes))
void setPrefLoopAlignment(unsigned Align)
Set the target&#39;s preferred loop alignment.
ZERO_EXTEND - Used for integer types, zeroing the new bits.
Definition: ISDOpcodes.h:446
ANY_EXTEND - Used for integer types. The high bits are undefined.
Definition: ISDOpcodes.h:449
bool isTailCall() const