1f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===-- AMDILISelLowering.cpp - AMDIL DAG Lowering Implementation ---------===//
2f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//
3f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//                     The LLVM Compiler Infrastructure
4f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//
5f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// This file is distributed under the University of Illinois Open Source
6f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// License. See LICENSE.TXT for details.
7f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//
8f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//==-----------------------------------------------------------------------===//
9f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//
10f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// This file contains TargetLowering functions borrowed from AMDLI.
11f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//
12f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
13f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
14f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDGPUISelLowering.h"
15f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDGPURegisterInfo.h"
16f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDILDevices.h"
17f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDILIntrinsicInfo.h"
18f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDGPUSubtarget.h"
19f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDILUtilityFunctions.h"
20f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CallingConv.h"
21f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CodeGen/MachineFrameInfo.h"
22f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CodeGen/MachineRegisterInfo.h"
23f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CodeGen/PseudoSourceValue.h"
24f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CodeGen/SelectionDAG.h"
25f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CodeGen/SelectionDAGNodes.h"
26f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/CodeGen/TargetLoweringObjectFileImpl.h"
27f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/DerivedTypes.h"
28f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/Instructions.h"
29f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/Intrinsics.h"
30f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/Support/raw_ostream.h"
31f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/Target/TargetInstrInfo.h"
32f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "llvm/Target/TargetOptions.h"
33f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
34f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgusing namespace llvm;
35f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
36f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// Calling Convention Implementation
37f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
38f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#include "AMDGPUGenCallingConv.inc"
39f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
40f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
41f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// TargetLowering Implementation Help Functions End
42f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
43f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
44f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
45f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// TargetLowering Class Implementation Begins
46f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
47f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgvoid AMDGPUTargetLowering::InitAMDILLowering()
48f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
49f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  int types[] =
50f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  {
51f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i8,
52f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i16,
53f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i32,
54f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::f32,
55f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::f64,
56f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i64,
57f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i8,
58f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4i8,
59f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i16,
60f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4i16,
61f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4f32,
62f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4i32,
63f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2f32,
64f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i32,
65f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2f64,
66f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i64
67f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  };
68f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
69f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  int IntTypes[] =
70f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  {
71f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i8,
72f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i16,
73f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i32,
74f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::i64
75f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  };
76f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
77f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  int FloatTypes[] =
78f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  {
79f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::f32,
80f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::f64
81f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  };
82f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
83f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  int VectorTypes[] =
84f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  {
85f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i8,
86f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4i8,
87f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i16,
88f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4i16,
89f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4f32,
90f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v4i32,
91f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2f32,
92f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i32,
93f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2f64,
94f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    (int)MVT::v2i64
95f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  };
96f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  size_t numTypes = sizeof(types) / sizeof(*types);
97f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  size_t numFloatTypes = sizeof(FloatTypes) / sizeof(*FloatTypes);
98f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  size_t numIntTypes = sizeof(IntTypes) / sizeof(*IntTypes);
99f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  size_t numVectorTypes = sizeof(VectorTypes) / sizeof(*VectorTypes);
100f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
101f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  const AMDGPUSubtarget &STM = getTargetMachine().getSubtarget<AMDGPUSubtarget>();
102f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // These are the current register classes that are
103f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // supported
104f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
105f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  for (unsigned int x  = 0; x < numTypes; ++x) {
106f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    MVT::SimpleValueType VT = (MVT::SimpleValueType)types[x];
107f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
108f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    //FIXME: SIGN_EXTEND_INREG is not meaningful for floating point types
109f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // We cannot sextinreg, expand to shifts
110f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SIGN_EXTEND_INREG, VT, Custom);
111f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SUBE, VT, Expand);
112f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SUBC, VT, Expand);
113f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ADDE, VT, Expand);
114f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ADDC, VT, Expand);
115f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::BRCOND, VT, Custom);
116f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::BR_JT, VT, Expand);
117f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::BRIND, VT, Expand);
118f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // TODO: Implement custom UREM/SREM routines
119f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SREM, VT, Expand);
120f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SMUL_LOHI, VT, Expand);
121f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::UMUL_LOHI, VT, Expand);
122f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    if (VT != MVT::i64 && VT != MVT::v2i64) {
123f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      setOperationAction(ISD::SDIV, VT, Custom);
124f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    }
125f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
126f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  for (unsigned int x = 0; x < numFloatTypes; ++x) {
127f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    MVT::SimpleValueType VT = (MVT::SimpleValueType)FloatTypes[x];
128f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
129f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // IL does not have these operations for floating point types
130f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FP_ROUND_INREG, VT, Expand);
131f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETOLT, VT, Expand);
132f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETOGE, VT, Expand);
133f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETOGT, VT, Expand);
134f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETOLE, VT, Expand);
135f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETULT, VT, Expand);
136f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETUGE, VT, Expand);
137f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETUGT, VT, Expand);
138f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SETULE, VT, Expand);
139f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
140f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
141f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  for (unsigned int x = 0; x < numIntTypes; ++x) {
142f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    MVT::SimpleValueType VT = (MVT::SimpleValueType)IntTypes[x];
143f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
144f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // GPU also does not have divrem function for signed or unsigned
145f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SDIVREM, VT, Expand);
146f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
147f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // GPU does not have [S|U]MUL_LOHI functions as a single instruction
148f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SMUL_LOHI, VT, Expand);
149f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::UMUL_LOHI, VT, Expand);
150f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
151f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // GPU doesn't have a rotl, rotr, or byteswap instruction
152f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ROTR, VT, Expand);
153f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::BSWAP, VT, Expand);
154f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
155f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // GPU doesn't have any counting operators
156f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::CTPOP, VT, Expand);
157f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::CTTZ, VT, Expand);
158f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::CTLZ, VT, Expand);
159f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
160f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
161f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  for ( unsigned int ii = 0; ii < numVectorTypes; ++ii )
162f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  {
163f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    MVT::SimpleValueType VT = (MVT::SimpleValueType)VectorTypes[ii];
164f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
165f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::BUILD_VECTOR, VT, Custom);
166f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::VECTOR_SHUFFLE, VT, Expand);
167f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SDIVREM, VT, Expand);
168f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SMUL_LOHI, VT, Expand);
169f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // setOperationAction(ISD::VSETCC, VT, Expand);
170f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SELECT_CC, VT, Expand);
171f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
172f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
173f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (STM.device()->isSupported(AMDGPUDeviceInfo::LongOps)) {
174f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::MULHU, MVT::i64, Expand);
175f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::MULHU, MVT::v2i64, Expand);
176f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::MULHS, MVT::i64, Expand);
177f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::MULHS, MVT::v2i64, Expand);
178f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ADD, MVT::v2i64, Expand);
179f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SREM, MVT::v2i64, Expand);
180f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::Constant          , MVT::i64  , Legal);
181f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SDIV, MVT::v2i64, Expand);
182f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::TRUNCATE, MVT::v2i64, Expand);
183f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SIGN_EXTEND, MVT::v2i64, Expand);
184f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ZERO_EXTEND, MVT::v2i64, Expand);
185f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ANY_EXTEND, MVT::v2i64, Expand);
186f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
187f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (STM.device()->isSupported(AMDGPUDeviceInfo::DoubleOps)) {
188f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // we support loading/storing v2f64 but not operations on the type
189f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FADD, MVT::v2f64, Expand);
190f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FSUB, MVT::v2f64, Expand);
191f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FMUL, MVT::v2f64, Expand);
192f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FP_ROUND_INREG, MVT::v2f64, Expand);
193f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FP_EXTEND, MVT::v2f64, Expand);
194f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ConstantFP        , MVT::f64  , Legal);
195f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // We want to expand vector conversions into their scalar
196f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // counterparts.
197f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::TRUNCATE, MVT::v2f64, Expand);
198f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::SIGN_EXTEND, MVT::v2f64, Expand);
199f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ZERO_EXTEND, MVT::v2f64, Expand);
200f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::ANY_EXTEND, MVT::v2f64, Expand);
201f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FABS, MVT::f64, Expand);
202f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    setOperationAction(ISD::FABS, MVT::v2f64, Expand);
203f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
204f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // TODO: Fix the UDIV24 algorithm so it works for these
205f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // types correctly. This needs vector comparisons
206f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // for this to work correctly.
207f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::UDIV, MVT::v2i8, Expand);
208f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::UDIV, MVT::v4i8, Expand);
209f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::UDIV, MVT::v2i16, Expand);
210f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::UDIV, MVT::v4i16, Expand);
211f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::i1, Custom);
212f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::SUBC, MVT::Other, Expand);
213f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::ADDE, MVT::Other, Expand);
214f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::ADDC, MVT::Other, Expand);
215f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::BRCOND, MVT::Other, Custom);
216f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::BR_JT, MVT::Other, Expand);
217f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::BRIND, MVT::Other, Expand);
218f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::SIGN_EXTEND_INREG, MVT::Other, Expand);
219f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
220f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::BUILD_VECTOR, MVT::Other, Custom);
221f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
222f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // Use the default implementation.
223f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::ConstantFP        , MVT::f32    , Legal);
224f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setOperationAction(ISD::Constant          , MVT::i32    , Legal);
225f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
226f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setSchedulingPreference(Sched::RegPressure);
227f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setPow2DivIsCheap(false);
228f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setPrefLoopAlignment(16);
229f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setSelectIsExpensive(true);
230f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  setJumpIsExpensive(true);
231f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
232f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  maxStoresPerMemcpy  = 4096;
233f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  maxStoresPerMemmove = 4096;
234f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  maxStoresPerMemset  = 4096;
235f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
236f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#undef numTypes
237f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#undef numIntTypes
238f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#undef numVectorTypes
239f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#undef numFloatTypes
240f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
241f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
242f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgbool
243f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::getTgtMemIntrinsic(IntrinsicInfo &Info,
244f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    const CallInst &I, unsigned Intrinsic) const
245f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
246f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return false;
247f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
248f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// The backend supports 32 and 64 bit floating point immediates
249f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgbool
250f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::isFPImmLegal(const APFloat &Imm, EVT VT) const
251f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
252f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (VT.getScalarType().getSimpleVT().SimpleTy == MVT::f32
253f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      || VT.getScalarType().getSimpleVT().SimpleTy == MVT::f64) {
254f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    return true;
255f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else {
256f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    return false;
257f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
258f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
259f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
260f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgbool
261f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::ShouldShrinkFPConstant(EVT VT) const
262f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
263f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (VT.getScalarType().getSimpleVT().SimpleTy == MVT::f32
264f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      || VT.getScalarType().getSimpleVT().SimpleTy == MVT::f64) {
265f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    return false;
266f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else {
267f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    return true;
268f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
269f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
270f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
271f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
272f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// isMaskedValueZeroForTargetNode - Return true if 'Op & Mask' is known to
273f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// be zero. Op is expected to be a target specific node. Used by DAG
274f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org// combiner.
275f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
276f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgvoid
277f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::computeMaskedBitsForTargetNode(
278f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    const SDValue Op,
279f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    APInt &KnownZero,
280f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    APInt &KnownOne,
281f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    const SelectionDAG &DAG,
282f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    unsigned Depth) const
283f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
284f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  APInt KnownZero2;
285f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  APInt KnownOne2;
286f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  KnownZero = KnownOne = APInt(KnownOne.getBitWidth(), 0); // Don't know anything
287f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  switch (Op.getOpcode()) {
288f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    default: break;
289f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    case ISD::SELECT_CC:
290f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             DAG.ComputeMaskedBits(
291f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 Op.getOperand(1),
292f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 KnownZero,
293f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 KnownOne,
294f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 Depth + 1
295f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 );
296f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             DAG.ComputeMaskedBits(
297f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 Op.getOperand(0),
298f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 KnownZero2,
299f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 KnownOne2
300f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 );
301f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             assert((KnownZero & KnownOne) == 0
302f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 && "Bits known to be one AND zero?");
303f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             assert((KnownZero2 & KnownOne2) == 0
304f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org                 && "Bits known to be one AND zero?");
305f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             // Only known if known in both the LHS and RHS
306f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             KnownOne &= KnownOne2;
307f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             KnownZero &= KnownZero2;
308f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org             break;
309f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  };
310f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
311f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
312f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
313f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//                           Other Lowering Hooks
314f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org//===----------------------------------------------------------------------===//
315f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
316f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
317f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSDIV(SDValue Op, SelectionDAG &DAG) const
318f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
319f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
320f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue DST;
321f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (OVT.getScalarType() == MVT::i64) {
322f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSDIV64(Op, DAG);
323f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getScalarType() == MVT::i32) {
324f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSDIV32(Op, DAG);
325f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getScalarType() == MVT::i16
326f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      || OVT.getScalarType() == MVT::i8) {
327f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSDIV24(Op, DAG);
328f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else {
329f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = SDValue(Op.getNode(), 0);
330f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
331f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return DST;
332f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
333f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
334f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
335f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSREM(SDValue Op, SelectionDAG &DAG) const
336f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
337f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
338f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue DST;
339f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (OVT.getScalarType() == MVT::i64) {
340f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSREM64(Op, DAG);
341f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getScalarType() == MVT::i32) {
342f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSREM32(Op, DAG);
343f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getScalarType() == MVT::i16) {
344f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSREM16(Op, DAG);
345f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getScalarType() == MVT::i8) {
346f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = LowerSREM8(Op, DAG);
347f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else {
348f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DST = SDValue(Op.getNode(), 0);
349f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
350f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return DST;
351f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
352f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
353f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
354f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerBUILD_VECTOR( SDValue Op, SelectionDAG &DAG ) const
355f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
356f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT VT = Op.getValueType();
357f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Nodes1;
358f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue second;
359f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue third;
360f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue fourth;
361f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
362f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  Nodes1 = DAG.getNode(AMDGPUISD::VBUILD,
363f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      DL,
364f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      VT, Op.getOperand(0));
365f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#if 0
366f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  bool allEqual = true;
367f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  for (unsigned x = 1, y = Op.getNumOperands(); x < y; ++x) {
368f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    if (Op.getOperand(0) != Op.getOperand(x)) {
369f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      allEqual = false;
370f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      break;
371f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    }
372f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
373f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (allEqual) {
374f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    return Nodes1;
375f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
376f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org#endif
377f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  switch(Op.getNumOperands()) {
378f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    default:
379f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    case 1:
380f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      break;
381f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    case 4:
382f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      fourth = Op.getOperand(3);
383f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      if (fourth.getOpcode() != ISD::UNDEF) {
384f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org        Nodes1 = DAG.getNode(
385f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            ISD::INSERT_VECTOR_ELT,
386f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            DL,
387f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            Op.getValueType(),
388f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            Nodes1,
389f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            fourth,
390f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            DAG.getConstant(7, MVT::i32));
391f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      }
392f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    case 3:
393f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      third = Op.getOperand(2);
394f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      if (third.getOpcode() != ISD::UNDEF) {
395f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org        Nodes1 = DAG.getNode(
396f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            ISD::INSERT_VECTOR_ELT,
397f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            DL,
398f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            Op.getValueType(),
399f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            Nodes1,
400f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            third,
401f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            DAG.getConstant(6, MVT::i32));
402f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      }
403f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    case 2:
404f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      second = Op.getOperand(1);
405f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      if (second.getOpcode() != ISD::UNDEF) {
406f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org        Nodes1 = DAG.getNode(
407f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            ISD::INSERT_VECTOR_ELT,
408f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            DL,
409f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            Op.getValueType(),
410f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            Nodes1,
411f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            second,
412f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org            DAG.getConstant(5, MVT::i32));
413f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      }
414f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      break;
415f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  };
416f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return Nodes1;
417f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
418f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
419f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
420f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSIGN_EXTEND_INREG(SDValue Op, SelectionDAG &DAG) const
421f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
422f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Data = Op.getOperand(0);
423f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  VTSDNode *BaseType = cast<VTSDNode>(Op.getOperand(1));
424f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
425f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT DVT = Data.getValueType();
426f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT BVT = BaseType->getVT();
427f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  unsigned baseBits = BVT.getScalarType().getSizeInBits();
428f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  unsigned srcBits = DVT.isSimple() ? DVT.getScalarType().getSizeInBits() : 1;
429f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  unsigned shiftBits = srcBits - baseBits;
430f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (srcBits < 32) {
431f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // If the op is less than 32 bits, then it needs to extend to 32bits
432f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // so it can properly keep the upper bits valid.
433f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    EVT IVT = genIntType(32, DVT.isVector() ? DVT.getVectorNumElements() : 1);
434f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    Data = DAG.getNode(ISD::ZERO_EXTEND, DL, IVT, Data);
435f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    shiftBits = 32 - baseBits;
436f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    DVT = IVT;
437f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
438f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Shift = DAG.getConstant(shiftBits, DVT);
439f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // Shift left by 'Shift' bits.
440f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  Data = DAG.getNode(ISD::SHL, DL, DVT, Data, Shift);
441f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // Signed shift Right by 'Shift' bits.
442f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  Data = DAG.getNode(ISD::SRA, DL, DVT, Data, Shift);
443f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (srcBits < 32) {
444f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // Once the sign extension is done, the op needs to be converted to
445f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    // its original type.
446f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    Data = DAG.getSExtOrTrunc(Data, DL, Op.getOperand(0).getValueType());
447f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
448f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return Data;
449f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
450f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgEVT
451f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::genIntType(uint32_t size, uint32_t numEle) const
452f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
453f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  int iSize = (size * numEle);
454f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  int vEle = (iSize >> ((size == 64) ? 6 : 5));
455f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (!vEle) {
456f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    vEle = 1;
457f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
458f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (size == 64) {
459f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    if (vEle == 1) {
460f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      return EVT(MVT::i64);
461f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    } else {
462f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      return EVT(MVT::getVectorVT(MVT::i64, vEle));
463f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    }
464f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else {
465f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    if (vEle == 1) {
466f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      return EVT(MVT::i32);
467f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    } else {
468f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      return EVT(MVT::getVectorVT(MVT::i32, vEle));
469f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    }
470f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
471f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
472f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
473f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
474f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerBRCOND(SDValue Op, SelectionDAG &DAG) const
475f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
476f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Chain = Op.getOperand(0);
477f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Cond  = Op.getOperand(1);
478f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Jump  = Op.getOperand(2);
479f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue Result;
480f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  Result = DAG.getNode(
481f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      AMDGPUISD::BRANCH_COND,
482f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      Op.getDebugLoc(),
483f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      Op.getValueType(),
484f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      Chain, Jump, Cond);
485f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return Result;
486f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
487f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
488f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
489f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSDIV24(SDValue Op, SelectionDAG &DAG) const
490f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
491f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
492f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
493f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue LHS = Op.getOperand(0);
494f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue RHS = Op.getOperand(1);
495f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  MVT INTTY;
496f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  MVT FLTTY;
497f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (!OVT.isVector()) {
498f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::i32;
499f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    FLTTY = MVT::f32;
500f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getVectorNumElements() == 2) {
501f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::v2i32;
502f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    FLTTY = MVT::v2f32;
503f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT.getVectorNumElements() == 4) {
504f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::v4i32;
505f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    FLTTY = MVT::v4f32;
506f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
507f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  unsigned bitsize = OVT.getScalarType().getSizeInBits();
508f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // char|short jq = ia ^ ib;
509f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue jq = DAG.getNode(ISD::XOR, DL, OVT, LHS, RHS);
510f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
511f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // jq = jq >> (bitsize - 2)
512f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  jq = DAG.getNode(ISD::SRA, DL, OVT, jq, DAG.getConstant(bitsize - 2, OVT));
513f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
514f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // jq = jq | 0x1
515f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  jq = DAG.getNode(ISD::OR, DL, OVT, jq, DAG.getConstant(1, OVT));
516f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
517f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // jq = (int)jq
518f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  jq = DAG.getSExtOrTrunc(jq, DL, INTTY);
519f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
520f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // int ia = (int)LHS;
521f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue ia = DAG.getSExtOrTrunc(LHS, DL, INTTY);
522f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
523f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // int ib, (int)RHS;
524f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue ib = DAG.getSExtOrTrunc(RHS, DL, INTTY);
525f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
526f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // float fa = (float)ia;
527f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue fa = DAG.getNode(ISD::SINT_TO_FP, DL, FLTTY, ia);
528f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
529f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // float fb = (float)ib;
530f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue fb = DAG.getNode(ISD::SINT_TO_FP, DL, FLTTY, ib);
531f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
532f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // float fq = native_divide(fa, fb);
533f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue fq = DAG.getNode(AMDGPUISD::DIV_INF, DL, FLTTY, fa, fb);
534f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
535f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // fq = trunc(fq);
536f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  fq = DAG.getNode(ISD::FTRUNC, DL, FLTTY, fq);
537f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
538f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // float fqneg = -fq;
539f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue fqneg = DAG.getNode(ISD::FNEG, DL, FLTTY, fq);
540f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
541f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // float fr = mad(fqneg, fb, fa);
542f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue fr = DAG.getNode(AMDGPUISD::MAD, DL, FLTTY, fqneg, fb, fa);
543f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
544f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // int iq = (int)fq;
545f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue iq = DAG.getNode(ISD::FP_TO_SINT, DL, INTTY, fq);
546f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
547f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // fr = fabs(fr);
548f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  fr = DAG.getNode(ISD::FABS, DL, FLTTY, fr);
549f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
550f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // fb = fabs(fb);
551f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  fb = DAG.getNode(ISD::FABS, DL, FLTTY, fb);
552f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
553f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // int cv = fr >= fb;
554f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue cv;
555f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (INTTY == MVT::i32) {
556f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    cv = DAG.getSetCC(DL, INTTY, fr, fb, ISD::SETOGE);
557f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else {
558f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    cv = DAG.getSetCC(DL, INTTY, fr, fb, ISD::SETOGE);
559f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
560f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // jq = (cv ? jq : 0);
561f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  jq = DAG.getNode(ISD::SELECT, DL, OVT, cv, jq,
562f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      DAG.getConstant(0, OVT));
563f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // dst = iq + jq;
564f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  iq = DAG.getSExtOrTrunc(iq, DL, OVT);
565f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  iq = DAG.getNode(ISD::ADD, DL, OVT, iq, jq);
566f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return iq;
567f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
568f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
569f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
570f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSDIV32(SDValue Op, SelectionDAG &DAG) const
571f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
572f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
573f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
574f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue LHS = Op.getOperand(0);
575f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue RHS = Op.getOperand(1);
576f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // The LowerSDIV32 function generates equivalent to the following IL.
577f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r0, LHS
578f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r1, RHS
579f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r10, r0, 0
580f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r11, r1, 0
581f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
582f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r1, r1, r11
583f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r0, r0, r10
584f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r1, r1, r11
585f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // udiv r0, r0, r1
586f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r10, r10, r11
587f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
588f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor DST, r0, r10
589f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
590f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r0, LHS
591f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r0 = LHS;
592f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
593f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r1, RHS
594f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r1 = RHS;
595f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
596f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r10, r0, 0
597f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r10 = DAG.getSelectCC(DL,
598f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      r0, DAG.getConstant(0, OVT),
599f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      DAG.getConstant(-1, MVT::i32),
600f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      DAG.getConstant(0, MVT::i32),
601f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      ISD::SETLT);
602f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
603f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r11, r1, 0
604f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r11 = DAG.getSelectCC(DL,
605f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      r1, DAG.getConstant(0, OVT),
606f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      DAG.getConstant(-1, MVT::i32),
607f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      DAG.getConstant(0, MVT::i32),
608f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org      ISD::SETLT);
609f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
610f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
611f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::ADD, DL, OVT, r0, r10);
612f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
613f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r1, r1, r11
614f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r1 = DAG.getNode(ISD::ADD, DL, OVT, r1, r11);
615f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
616f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r0, r0, r10
617f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::XOR, DL, OVT, r0, r10);
618f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
619f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r1, r1, r11
620f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r1 = DAG.getNode(ISD::XOR, DL, OVT, r1, r11);
621f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
622f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // udiv r0, r0, r1
623f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::UDIV, DL, OVT, r0, r1);
624f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
625f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r10, r10, r11
626f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r10 = DAG.getNode(ISD::XOR, DL, OVT, r10, r11);
627f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
628f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
629f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::ADD, DL, OVT, r0, r10);
630f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
631f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor DST, r0, r10
632f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue DST = DAG.getNode(ISD::XOR, DL, OVT, r0, r10);
633f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return DST;
634f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
635f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
636f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
637f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSDIV64(SDValue Op, SelectionDAG &DAG) const
638f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
639f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return SDValue(Op.getNode(), 0);
640f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
641f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
642f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
643f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSREM8(SDValue Op, SelectionDAG &DAG) const
644f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
645f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
646f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
647f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  MVT INTTY = MVT::i32;
648f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (OVT == MVT::v2i8) {
649f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::v2i32;
650f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT == MVT::v4i8) {
651f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::v4i32;
652f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
653f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue LHS = DAG.getSExtOrTrunc(Op.getOperand(0), DL, INTTY);
654f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue RHS = DAG.getSExtOrTrunc(Op.getOperand(1), DL, INTTY);
655f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  LHS = DAG.getNode(ISD::SREM, DL, INTTY, LHS, RHS);
656f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  LHS = DAG.getSExtOrTrunc(LHS, DL, OVT);
657f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return LHS;
658f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
659f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
660f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
661f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSREM16(SDValue Op, SelectionDAG &DAG) const
662f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
663f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
664f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
665f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  MVT INTTY = MVT::i32;
666f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  if (OVT == MVT::v2i16) {
667f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::v2i32;
668f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  } else if (OVT == MVT::v4i16) {
669f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org    INTTY = MVT::v4i32;
670f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  }
671f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue LHS = DAG.getSExtOrTrunc(Op.getOperand(0), DL, INTTY);
672f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue RHS = DAG.getSExtOrTrunc(Op.getOperand(1), DL, INTTY);
673f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  LHS = DAG.getNode(ISD::SREM, DL, INTTY, LHS, RHS);
674f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  LHS = DAG.getSExtOrTrunc(LHS, DL, OVT);
675f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return LHS;
676f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
677f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
678f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
679f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSREM32(SDValue Op, SelectionDAG &DAG) const
680f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
681f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  DebugLoc DL = Op.getDebugLoc();
682f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  EVT OVT = Op.getValueType();
683f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue LHS = Op.getOperand(0);
684f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue RHS = Op.getOperand(1);
685f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // The LowerSREM32 function generates equivalent to the following IL.
686f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r0, LHS
687f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r1, RHS
688f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r10, r0, 0
689f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r11, r1, 0
690f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
691f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r1, r1, r11
692f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r0, r0, r10
693f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r1, r1, r11
694f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // udiv r20, r0, r1
695f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // umul r20, r20, r1
696f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // sub r0, r0, r20
697f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
698f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor DST, r0, r10
699f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
700f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r0, LHS
701f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r0 = LHS;
702f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
703f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // mov r1, RHS
704f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r1 = RHS;
705f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
706f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r10, r0, 0
707f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r10 = DAG.getSetCC(DL, OVT, r0, DAG.getConstant(0, OVT), ISD::SETLT);
708f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
709f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ilt r11, r1, 0
710f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r11 = DAG.getSetCC(DL, OVT, r1, DAG.getConstant(0, OVT), ISD::SETLT);
711f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
712f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
713f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::ADD, DL, OVT, r0, r10);
714f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
715f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r1, r1, r11
716f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r1 = DAG.getNode(ISD::ADD, DL, OVT, r1, r11);
717f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
718f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r0, r0, r10
719f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::XOR, DL, OVT, r0, r10);
720f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
721f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor r1, r1, r11
722f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r1 = DAG.getNode(ISD::XOR, DL, OVT, r1, r11);
723f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
724f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // udiv r20, r0, r1
725f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue r20 = DAG.getNode(ISD::UREM, DL, OVT, r0, r1);
726f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
727f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // umul r20, r20, r1
728f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r20 = DAG.getNode(AMDGPUISD::UMUL, DL, OVT, r20, r1);
729f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
730f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // sub r0, r0, r20
731f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::SUB, DL, OVT, r0, r20);
732f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
733f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // iadd r0, r0, r10
734f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  r0 = DAG.getNode(ISD::ADD, DL, OVT, r0, r10);
735f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
736f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  // ixor DST, r0, r10
737f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  SDValue DST = DAG.getNode(ISD::XOR, DL, OVT, r0, r10);
738f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return DST;
739f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
740f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org
741f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgSDValue
742f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.orgAMDGPUTargetLowering::LowerSREM64(SDValue Op, SelectionDAG &DAG) const
743f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org{
744f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org  return SDValue(Op.getNode(), 0);
745f2ba7591b1407a7ee9209f842c50696914dc2dedkbr@chromium.org}
746