169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands//===----- LegalizeIntegerTypes.cpp - Legalization of integer types -------===//
2cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//
3cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//                     The LLVM Compiler Infrastructure
4cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//
54ee451de366474b9c228b4e5fa573795a715216dChris Lattner// This file is distributed under the University of Illinois Open Source
64ee451de366474b9c228b4e5fa573795a715216dChris Lattner// License. See LICENSE.TXT for details.
7cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//
8cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//===----------------------------------------------------------------------===//
9cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//
1069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// This file implements integer type expansion and promotion for LegalizeTypes.
1169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// Promotion is the act of changing a computation in an illegal type into a
1269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// computation in a larger type.  For example, implementing i8 arithmetic in an
1369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// i32 register (often needed on powerpc).
1469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// Expansion is the act of changing a computation in an illegal type into a
1578cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands// computation in two identical registers of a smaller type.  For example,
1669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// implementing i64 arithmetic in two i32 registers (often needed on 32-bit
1769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands// targets).
18cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//
19cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//===----------------------------------------------------------------------===//
20cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
21cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner#include "LegalizeTypes.h"
220b8c9a80f20772c3793201ab5b251d3520b9cea3Chandler Carruth#include "llvm/IR/DerivedTypes.h"
237d696d80409aad20bb5da0fc4eccab941dd371d4Torok Edwin#include "llvm/Support/ErrorHandling.h"
24fd87a544c00c2ca04ee23aae67bbcad4dc852a54Dan Gohman#include "llvm/Support/raw_ostream.h"
25cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattnerusing namespace llvm;
26cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
27cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//===----------------------------------------------------------------------===//
2869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands//  Integer Result Promotion
29cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//===----------------------------------------------------------------------===//
30cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
3169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// PromoteIntegerResult - This method is called when a result of a node is
3269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// found to be in need of promotion to a larger type.  At this point, the node
3369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// may also have invalid operands or may have other results that need
3469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// expansion, we just know that (at least) one result needs promotion.
3569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sandsvoid DAGTypeLegalizer::PromoteIntegerResult(SDNode *N, unsigned ResNo) {
36d765353da89988e949fd4c021d8860f36ab7c392David Greene  DEBUG(dbgs() << "Promote integer result: "; N->dump(&DAG); dbgs() << "\n");
379fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  SDValue Res = SDValue();
3869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
39126d90770bdb17e6925b2fe26de99aa079b7b9b3Duncan Sands  // See if the target wants to custom expand this node.
40f43071beddb7ed5b2fd7d2f06c4130460616a13dDuncan Sands  if (CustomLowerNode(N, N->getValueType(ResNo), true))
411607f05cb7d77d01ce521a30232faa389dbed4e2Duncan Sands    return;
42126d90770bdb17e6925b2fe26de99aa079b7b9b3Duncan Sands
4369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  switch (N->getOpcode()) {
4469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  default:
4569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands#ifndef NDEBUG
46d765353da89988e949fd4c021d8860f36ab7c392David Greene    dbgs() << "PromoteIntegerResult #" << ResNo << ": ";
47d765353da89988e949fd4c021d8860f36ab7c392David Greene    N->dump(&DAG); dbgs() << "\n";
4869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands#endif
49c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    llvm_unreachable("Do not know how to promote this operator!");
504c19e12d28749c717d3b384962c9ec92796af1c9Duncan Sands  case ISD::MERGE_VALUES:Res = PromoteIntRes_MERGE_VALUES(N, ResNo); break;
519fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::AssertSext:  Res = PromoteIntRes_AssertSext(N); break;
529fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::AssertZext:  Res = PromoteIntRes_AssertZext(N); break;
53bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck  case ISD::BITCAST:     Res = PromoteIntRes_BITCAST(N); break;
549fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::BSWAP:       Res = PromoteIntRes_BSWAP(N); break;
559fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::BUILD_PAIR:  Res = PromoteIntRes_BUILD_PAIR(N); break;
569fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::Constant:    Res = PromoteIntRes_Constant(N); break;
5700ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang  case ISD::CONVERT_RNDSAT:
589fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands                         Res = PromoteIntRes_CONVERT_RNDSAT(N); break;
5963974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  case ISD::CTLZ_ZERO_UNDEF:
609fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::CTLZ:        Res = PromoteIntRes_CTLZ(N); break;
619fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::CTPOP:       Res = PromoteIntRes_CTPOP(N); break;
6263974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  case ISD::CTTZ_ZERO_UNDEF:
639fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::CTTZ:        Res = PromoteIntRes_CTTZ(N); break;
64bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  case ISD::EXTRACT_VECTOR_ELT:
659fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands                         Res = PromoteIntRes_EXTRACT_VECTOR_ELT(N); break;
669fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::LOAD:        Res = PromoteIntRes_LOAD(cast<LoadSDNode>(N));break;
679fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SELECT:      Res = PromoteIntRes_SELECT(N); break;
68436fe8498a0a3368d2690290e805213a0f114d0dNadav Rotem  case ISD::VSELECT:     Res = PromoteIntRes_VSELECT(N); break;
699fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SELECT_CC:   Res = PromoteIntRes_SELECT_CC(N); break;
709fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SETCC:       Res = PromoteIntRes_SETCC(N); break;
719fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SHL:         Res = PromoteIntRes_SHL(N); break;
728d56a6f4d8b010d4c582225a08ece971613f6fe3Duncan Sands  case ISD::SIGN_EXTEND_INREG:
739fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands                         Res = PromoteIntRes_SIGN_EXTEND_INREG(N); break;
749fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SRA:         Res = PromoteIntRes_SRA(N); break;
759fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SRL:         Res = PromoteIntRes_SRL(N); break;
769fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::TRUNCATE:    Res = PromoteIntRes_TRUNCATE(N); break;
779fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::UNDEF:       Res = PromoteIntRes_UNDEF(N); break;
789fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::VAARG:       Res = PromoteIntRes_VAARG(N); break;
79bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
80fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::EXTRACT_SUBVECTOR:
81fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem                         Res = PromoteIntRes_EXTRACT_SUBVECTOR(N); break;
82fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::VECTOR_SHUFFLE:
83fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem                         Res = PromoteIntRes_VECTOR_SHUFFLE(N); break;
84fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::INSERT_VECTOR_ELT:
85fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem                         Res = PromoteIntRes_INSERT_VECTOR_ELT(N); break;
86fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::BUILD_VECTOR:
87fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem                         Res = PromoteIntRes_BUILD_VECTOR(N); break;
88fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::SCALAR_TO_VECTOR:
89fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem                         Res = PromoteIntRes_SCALAR_TO_VECTOR(N); break;
90c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  case ISD::CONCAT_VECTORS:
91c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem                         Res = PromoteIntRes_CONCAT_VECTORS(N); break;
92fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
9369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SIGN_EXTEND:
9469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::ZERO_EXTEND:
959fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::ANY_EXTEND:  Res = PromoteIntRes_INT_EXTEND(N); break;
96bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
9769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::FP_TO_SINT:
989fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::FP_TO_UINT:  Res = PromoteIntRes_FP_TO_XINT(N); break;
9969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
100927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov  case ISD::FP32_TO_FP16:Res = PromoteIntRes_FP32_TO_FP16(N); break;
101927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov
10269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::AND:
10369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::OR:
10469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::XOR:
10569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::ADD:
10669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SUB:
1079fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::MUL:         Res = PromoteIntRes_SimpleIntBinOp(N); break;
10869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
10969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SDIV:
1109fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SREM:        Res = PromoteIntRes_SDIV(N); break;
11169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
11269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::UDIV:
1139fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::UREM:        Res = PromoteIntRes_UDIV(N); break;
1148ac0d4b4fb10406278cd600214cd3ee6d76620cdBill Wendling
115253174bf50c932abaa680f465e2888c0e5272267Bill Wendling  case ISD::SADDO:
1169fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::SSUBO:       Res = PromoteIntRes_SADDSUBO(N, ResNo); break;
11774c376529101acbe141a256d0bf23a44eb454c84Bill Wendling  case ISD::UADDO:
1189fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::USUBO:       Res = PromoteIntRes_UADDSUBO(N, ResNo); break;
11974c376529101acbe141a256d0bf23a44eb454c84Bill Wendling  case ISD::SMULO:
1209fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  case ISD::UMULO:       Res = PromoteIntRes_XMULO(N, ResNo); break;
121b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands
122331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  case ISD::ATOMIC_LOAD:
123331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman    Res = PromoteIntRes_Atomic0(cast<AtomicSDNode>(N)); break;
124331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman
1250b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_ADD:
1260b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_SUB:
1270b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_AND:
1280b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_OR:
1290b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_XOR:
1300b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_NAND:
1310b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_MIN:
1320b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_MAX:
1330b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_UMIN:
1340b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_LOAD_UMAX:
1350b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_SWAP:
1369fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands    Res = PromoteIntRes_Atomic1(cast<AtomicSDNode>(N)); break;
137b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands
1380b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman  case ISD::ATOMIC_CMP_SWAP:
1399fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands    Res = PromoteIntRes_Atomic2(cast<AtomicSDNode>(N)); break;
14069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  }
14169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
1429fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  // If the result is null then the sub-method took care of registering it.
1439fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  if (Res.getNode())
1449fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands    SetPromotedInteger(SDValue(N, ResNo), Res);
14569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
14669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
1474c19e12d28749c717d3b384962c9ec92796af1c9Duncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_MERGE_VALUES(SDNode *N,
1484c19e12d28749c717d3b384962c9ec92796af1c9Duncan Sands                                                     unsigned ResNo) {
1494c19e12d28749c717d3b384962c9ec92796af1c9Duncan Sands  SDValue Op = DisintegrateMERGE_VALUES(N, ResNo);
15062bb16cfd10dd271eab6c31d982bca4d79138602Eli Friedman  return GetPromotedInteger(Op);
15162bb16cfd10dd271eab6c31d982bca4d79138602Eli Friedman}
15262bb16cfd10dd271eab6c31d982bca4d79138602Eli Friedman
153475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_AssertSext(SDNode *N) {
15495db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  // Sign-extend the new bits, and continue the assertion.
155c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue Op = SExtPromotedInteger(N->getOperand(0));
156ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::AssertSext, SDLoc(N),
157786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                     Op.getValueType(), Op, N->getOperand(1));
15895db39a9de48f69f4d764335b492b83a698c7854Duncan Sands}
15995db39a9de48f69f4d764335b492b83a698c7854Duncan Sands
160475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_AssertZext(SDNode *N) {
16195db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  // Zero the new bits, and continue the assertion.
162c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue Op = ZExtPromotedInteger(N->getOperand(0));
163ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::AssertZext, SDLoc(N),
164786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                     Op.getValueType(), Op, N->getOperand(1));
16595db39a9de48f69f4d764335b492b83a698c7854Duncan Sands}
16695db39a9de48f69f4d764335b492b83a698c7854Duncan Sands
167331120b1a482b782e8dffce63033bb8514ba2a96Eli FriedmanSDValue DAGTypeLegalizer::PromoteIntRes_Atomic0(AtomicSDNode *N) {
168331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  EVT ResVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
169ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDValue Res = DAG.getAtomic(N->getOpcode(), SDLoc(N),
170331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman                              N->getMemoryVT(), ResVT,
171331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman                              N->getChain(), N->getBasePtr(),
172331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman                              N->getMemOperand(), N->getOrdering(),
173331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman                              N->getSynchScope());
174331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  // Legalized the chain result - switch anything that used the old chain to
175331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  // use the new one.
176331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
177331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  return Res;
178331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman}
179331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman
180b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_Atomic1(AtomicSDNode *N) {
181b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  SDValue Op2 = GetPromotedInteger(N->getOperand(2));
182ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDValue Res = DAG.getAtomic(N->getOpcode(), SDLoc(N),
183786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                              N->getMemoryVT(),
1840b1d4a798d1dd2f39521b6b381cd1c1911c9ab52Dan Gohman                              N->getChain(), N->getBasePtr(),
18555ba816883842e793cdeb32fcb805c4e011b527fEli Friedman                              Op2, N->getMemOperand(), N->getOrdering(),
18655ba816883842e793cdeb32fcb805c4e011b527fEli Friedman                              N->getSynchScope());
187b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  // Legalized the chain result - switch anything that used the old chain to
188b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  // use the new one.
189b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
190b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  return Res;
191b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands}
192b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands
193b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_Atomic2(AtomicSDNode *N) {
194b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  SDValue Op2 = GetPromotedInteger(N->getOperand(2));
195b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  SDValue Op3 = GetPromotedInteger(N->getOperand(3));
196ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDValue Res = DAG.getAtomic(N->getOpcode(), SDLoc(N),
197f8d3ec2c5725a2010f11de4ba78f6127712a5fe7Dale Johannesen                              N->getMemoryVT(), N->getChain(), N->getBasePtr(),
19855ba816883842e793cdeb32fcb805c4e011b527fEli Friedman                              Op2, Op3, N->getMemOperand(), N->getOrdering(),
19955ba816883842e793cdeb32fcb805c4e011b527fEli Friedman                              N->getSynchScope());
200b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  // Legalized the chain result - switch anything that used the old chain to
201b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  // use the new one.
202b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
203b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands  return Res;
204b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands}
205b5f68e241f9eb19e5694131df830acbfce20a6ebDuncan Sands
206bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley PeckSDValue DAGTypeLegalizer::PromoteIntRes_BITCAST(SDNode *N) {
207475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue InOp = N->getOperand(0);
208e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT InVT = InOp.getValueType();
20923b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NInVT = TLI.getTypeToTransformTo(*DAG.getContext(), InVT);
210e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OutVT = N->getValueType(0);
21123b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
212ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
21369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
21469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  switch (getTypeAction(InVT)) {
21596e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeLegal:
21669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    break;
21796e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypePromoteInteger:
21844bac7cd659090f15face5171e3c346983aeb521Nadav Rotem    if (NOutVT.bitsEq(NInVT) && !NOutVT.isVector() && !NInVT.isVector())
21969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands      // The input promotes to the same size.  Convert the promoted value.
220bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck      return DAG.getNode(ISD::BITCAST, dl, NOutVT, GetPromotedInteger(InOp));
22169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    break;
22296e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeSoftenFloat:
22369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // Promote the integer operand by hand.
224786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT, GetSoftenedFloat(InOp));
22596e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeExpandInteger:
22696e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeExpandFloat:
22769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    break;
22896e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeScalarizeVector:
22969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // Convert the element to an integer and promote it by hand.
230c2492c28ef04dbc77c5d47ec81ffc64c5407771fNadav Rotem    if (!NOutVT.isVector())
231c2492c28ef04dbc77c5d47ec81ffc64c5407771fNadav Rotem      return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT,
232c2492c28ef04dbc77c5d47ec81ffc64c5407771fNadav Rotem                         BitConvertToInteger(GetScalarizedVector(InOp)));
233c2492c28ef04dbc77c5d47ec81ffc64c5407771fNadav Rotem    break;
23496e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeSplitVector: {
235bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck    // For example, i32 = BITCAST v2i16 on alpha.  Convert the split
23669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // pieces of the input into integers and reassemble in the final type.
237475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Lo, Hi;
23869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    GetSplitVector(N->getOperand(0), Lo, Hi);
23969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    Lo = BitConvertToInteger(Lo);
24069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    Hi = BitConvertToInteger(Hi);
24169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
24269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    if (TLI.isBigEndian())
24369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands      std::swap(Lo, Hi);
24469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
245786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    InOp = DAG.getNode(ISD::ANY_EXTEND, dl,
246adf979900c84d00e1fe0872a68d2819c654b6f29Evan Cheng                       EVT::getIntegerVT(*DAG.getContext(),
247adf979900c84d00e1fe0872a68d2819c654b6f29Evan Cheng                                         NOutVT.getSizeInBits()),
24869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands                       JoinIntegers(Lo, Hi));
249bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck    return DAG.getNode(ISD::BITCAST, dl, NOutVT, InOp);
25069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  }
25196e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeWidenVector:
252819026f2f8b13ac7f6051727fce54b95868c3d85Nadav Rotem    // The input is widened to the same size. Convert to the widened value.
253819026f2f8b13ac7f6051727fce54b95868c3d85Nadav Rotem    // Make sure that the outgoing value is not a vector, because this would
254819026f2f8b13ac7f6051727fce54b95868c3d85Nadav Rotem    // make us bitcast between two vectors which are legalized in different ways.
255819026f2f8b13ac7f6051727fce54b95868c3d85Nadav Rotem    if (NOutVT.bitsEq(NInVT) && !NOutVT.isVector())
256fbb6f593c264551a5d585a6c97ff03420b142ea3Nadav Rotem      return DAG.getNode(ISD::BITCAST, dl, NOutVT, GetWidenedVector(InOp));
25787c8a8f304d1ee72829086ce2c41a8fa3813ba6aMon P Wang  }
25869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
259aad3460086a1b29c55f7490c6d8743ea4e53f07dEli Friedman  return DAG.getNode(ISD::ANY_EXTEND, dl, NOutVT,
260aad3460086a1b29c55f7490c6d8743ea4e53f07dEli Friedman                     CreateStackStoreLoad(InOp, OutVT));
26169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
26269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
263475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_BSWAP(SDNode *N) {
264475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
265e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OVT = N->getValueType(0);
266e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Op.getValueType();
267ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
268c07e6e53f757da1a7c79c66ed53f2844de85a77eDuncan Sands
269c07e6e53f757da1a7c79c66ed53f2844de85a77eDuncan Sands  unsigned DiffBits = NVT.getSizeInBits() - OVT.getSizeInBits();
270786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  return DAG.getNode(ISD::SRL, dl, NVT, DAG.getNode(ISD::BSWAP, dl, NVT, Op),
27153dfa78e4133f6cdb5d860279adc337ea099ac15Duncan Sands                     DAG.getConstant(DiffBits, TLI.getPointerTy()));
272c07e6e53f757da1a7c79c66ed53f2844de85a77eDuncan Sands}
273c07e6e53f757da1a7c79c66ed53f2844de85a77eDuncan Sands
274475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_BUILD_PAIR(SDNode *N) {
275bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The pair element type may be legal, or may not promote to the same type as
276bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // the result, for example i14 = BUILD_PAIR (i7, i7).  Handle all cases.
277ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::ANY_EXTEND, SDLoc(N),
27854e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                     TLI.getTypeToTransformTo(*DAG.getContext(),
27954e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                     N->getValueType(0)), JoinIntegers(N->getOperand(0),
28054e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                     N->getOperand(1)));
28169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
28269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
283475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_Constant(SDNode *N) {
284e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
285b300d2aa3ef08b5074449e2c05804717f488f4e4Dale Johannesen  // FIXME there is no actual debug info here
286ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
287bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Zero extend things like i1, sign extend everything else.  It shouldn't
288bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // matter in theory which one we pick, but this tends to give better code?
289bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  unsigned Opc = VT.isByteSized() ? ISD::SIGN_EXTEND : ISD::ZERO_EXTEND;
29054e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher  SDValue Result = DAG.getNode(Opc, dl,
29154e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                               TLI.getTypeToTransformTo(*DAG.getContext(), VT),
292a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands                               SDValue(N, 0));
293bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(isa<ConstantSDNode>(Result) && "Didn't constant fold ext?");
294bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  return Result;
29569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
29669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
29700ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P WangSDValue DAGTypeLegalizer::PromoteIntRes_CONVERT_RNDSAT(SDNode *N) {
29800ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang  ISD::CvtCode CvtCode = cast<CvtRndSatSDNode>(N)->getCvtCode();
29900ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang  assert ((CvtCode == ISD::CVT_SS || CvtCode == ISD::CVT_SU ||
30000ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang           CvtCode == ISD::CVT_US || CvtCode == ISD::CVT_UU ||
30100ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang           CvtCode == ISD::CVT_SF || CvtCode == ISD::CVT_UF) &&
30200ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang          "can only promote integers");
30323b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT OutVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
304ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getConvertRndSat(OutVT, SDLoc(N), N->getOperand(0),
30500ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang                              N->getOperand(1), N->getOperand(2),
30600ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang                              N->getOperand(3), N->getOperand(4), CvtCode);
30700ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang}
30800ec49b6bafc33ee17d97ec1c723e1edb41d4c97Mon P Wang
309475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_CTLZ(SDNode *N) {
310c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  // Zero extend to the promoted type and do the count there.
311c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue Op = ZExtPromotedInteger(N->getOperand(0));
312ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
313e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OVT = N->getValueType(0);
314e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Op.getValueType();
31563974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  Op = DAG.getNode(N->getOpcode(), dl, NVT, Op);
31669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // Subtract off the extra leading bits in the bigger type.
317b300d2aa3ef08b5074449e2c05804717f488f4e4Dale Johannesen  return DAG.getNode(ISD::SUB, dl, NVT, Op,
31869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands                     DAG.getConstant(NVT.getSizeInBits() -
31969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands                                     OVT.getSizeInBits(), NVT));
32069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
32169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
322475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_CTPOP(SDNode *N) {
32369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // Zero extend to the promoted type and do the count there.
324c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue Op = ZExtPromotedInteger(N->getOperand(0));
325ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::CTPOP, SDLoc(N), Op.getValueType(), Op);
32669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
32769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
328475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_CTTZ(SDNode *N) {
329475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
330e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OVT = N->getValueType(0);
331e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Op.getValueType();
332ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
33363974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  if (N->getOpcode() == ISD::CTTZ) {
33463974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth    // The count is the same in the promoted type except if the original
33563974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth    // value was zero.  This can be handled by setting the bit just off
33663974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth    // the top of the original type.
33763974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth    APInt TopBit(NVT.getSizeInBits(), 0);
33863974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth    TopBit.setBit(OVT.getSizeInBits());
33963974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth    Op = DAG.getNode(ISD::OR, dl, NVT, Op, DAG.getConstant(TopBit, NVT));
34063974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  }
34163974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  return DAG.getNode(N->getOpcode(), dl, NVT, Op);
34269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
34369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
344475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_EXTRACT_VECTOR_ELT(SDNode *N) {
345ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
34623b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
347c680ac90032bf455b2bba77de538fccea08eb267Eli Friedman  return DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, NVT, N->getOperand(0),
348c680ac90032bf455b2bba77de538fccea08eb267Eli Friedman                     N->getOperand(1));
34969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
35069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
351475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_FP_TO_XINT(SDNode *N) {
35223b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
353a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands  unsigned NewOpc = N->getOpcode();
354ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
355d3ca9fc9984d036146886a40ad3f73aaf7a424ebDuncan Sands
3564c9369df57a52cec5e1fc735e61a979766288074Dale Johannesen  // If we're promoting a UINT to a larger size and the larger FP_TO_UINT is
3574c9369df57a52cec5e1fc735e61a979766288074Dale Johannesen  // not Legal, check to see if we can use FP_TO_SINT instead.  (If both UINT
35854e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher  // and SINT conversions are Custom, there is no way to tell which is
35954e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher  // preferable. We choose SINT because that's the right thing on PPC.)
360a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands  if (N->getOpcode() == ISD::FP_TO_UINT &&
3614c9369df57a52cec5e1fc735e61a979766288074Dale Johannesen      !TLI.isOperationLegal(ISD::FP_TO_UINT, NVT) &&
362f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman      TLI.isOperationLegalOrCustom(ISD::FP_TO_SINT, NVT))
363a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands    NewOpc = ISD::FP_TO_SINT;
364a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands
365786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  SDValue Res = DAG.getNode(NewOpc, dl, NVT, N->getOperand(0));
366a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands
367a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands  // Assert that the converted value fits in the original type.  If it doesn't
368a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands  // (eg: because the value being converted is too big), then the result of the
369a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands  // original operation was undefined anyway, so the assert is still correct.
370a29c13086a3add78a3a79f744573fe09eaa9dc88Duncan Sands  return DAG.getNode(N->getOpcode() == ISD::FP_TO_UINT ?
3710928c9e18a1decd856501beeea1bd12453a366b3Nadav Rotem                     ISD::AssertZext : ISD::AssertSext, dl, NVT, Res,
3720928c9e18a1decd856501beeea1bd12453a366b3Nadav Rotem                     DAG.getValueType(N->getValueType(0).getScalarType()));
373d3ca9fc9984d036146886a40ad3f73aaf7a424ebDuncan Sands}
374d3ca9fc9984d036146886a40ad3f73aaf7a424ebDuncan Sands
375927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton KorobeynikovSDValue DAGTypeLegalizer::PromoteIntRes_FP32_TO_FP16(SDNode *N) {
376927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
377ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
378927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov
379927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov  SDValue Res = DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0));
380927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov
381927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov  return DAG.getNode(ISD::AssertZext, dl,
382927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov                     NVT, Res, DAG.getValueType(N->getValueType(0)));
383927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov}
384927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov
385475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_INT_EXTEND(SDNode *N) {
38623b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
387ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
388be1ad4de2900451626c8d4ace07b9ea16099ea1dDuncan Sands
38996e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  if (getTypeAction(N->getOperand(0).getValueType())
39096e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem      == TargetLowering::TypePromoteInteger) {
391475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Res = GetPromotedInteger(N->getOperand(0));
3926959b2bb6521baca57e5507ca039e51002d4a971Duncan Sands    assert(Res.getValueType().bitsLE(NVT) && "Extension doesn't make sense!");
393126d90770bdb17e6925b2fe26de99aa079b7b9b3Duncan Sands
394bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    // If the result and operand types are the same after promotion, simplify
395bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    // to an in-register extension.
396bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    if (NVT == Res.getValueType()) {
397bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands      // The high bits are not guaranteed to be anything.  Insert an extend.
398bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands      if (N->getOpcode() == ISD::SIGN_EXTEND)
399786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        return DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, NVT, Res,
400bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands                           DAG.getValueType(N->getOperand(0).getValueType()));
401bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands      if (N->getOpcode() == ISD::ZERO_EXTEND)
4020928c9e18a1decd856501beeea1bd12453a366b3Nadav Rotem        return DAG.getZeroExtendInReg(Res, dl,
4030928c9e18a1decd856501beeea1bd12453a366b3Nadav Rotem                      N->getOperand(0).getValueType().getScalarType());
404bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands      assert(N->getOpcode() == ISD::ANY_EXTEND && "Unknown integer extension!");
405bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands      return Res;
406126d90770bdb17e6925b2fe26de99aa079b7b9b3Duncan Sands    }
40769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  }
40869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
409bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Otherwise, just extend the original operand all the way to the larger type.
410786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  return DAG.getNode(N->getOpcode(), dl, NVT, N->getOperand(0));
411bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
41269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
413475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_LOAD(LoadSDNode *N) {
414bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(ISD::isUNINDEXEDLoad(N) && "Indexed load during type legalization!");
41523b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
416bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  ISD::LoadExtType ExtType =
417bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    ISD::isNON_EXTLoad(N) ? ISD::EXTLOAD : N->getExtensionType();
418ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
419a901129169194881a78b7fd8953e09f55b846d10Stuart Hastings  SDValue Res = DAG.getExtLoad(ExtType, dl, NVT, N->getChain(), N->getBasePtr(),
4203d6ccfba314ed38e4506dae2781a060e9a3e07acChris Lattner                               N->getPointerInfo(),
42147d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands                               N->getMemoryVT(), N->isVolatile(),
4221e559443a17d1b335f697551c6263ba60d5dd827David Greene                               N->isNonTemporal(), N->getAlignment());
42369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
424bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Legalized the chain result - switch anything that used the old chain to
425bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // use the new one.
426475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  ReplaceValueWith(SDValue(N, 1), Res.getValue(1));
427bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  return Res;
42869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
42969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
430874ae251c317788391f9c3f113957802d390a063Dale Johannesen/// Promote the overflow flag of an overflowing arithmetic node.
431ab0c578bfd1380326830180a9209df6c5be58887Duncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_Overflow(SDNode *N) {
432ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Simply change the return type of the boolean result.
43323b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(1));
434e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT ValueVTs[] = { N->getValueType(0), NVT };
435ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  SDValue Ops[] = { N->getOperand(0), N->getOperand(1) };
436ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDValue Res = DAG.getNode(N->getOpcode(), SDLoc(N),
437786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                            DAG.getVTList(ValueVTs, 2), Ops, 2);
438ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
439ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Modified the sum result - switch anything that used the old sum to use
440ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // the new one.
441ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  ReplaceValueWith(SDValue(N, 0), Res);
442ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
443ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  return SDValue(Res.getNode(), 1);
444ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands}
445ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
446ab0c578bfd1380326830180a9209df6c5be58887Duncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_SADDSUBO(SDNode *N, unsigned ResNo) {
447ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  if (ResNo == 1)
448ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands    return PromoteIntRes_Overflow(N);
449ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
45094c22716d60ff5edf6a98a3c67e0faa001be1142Sylvestre Ledru  // The operation overflowed iff the result in the larger type is not the
451ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // sign extension of its truncation to the original type.
452ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  SDValue LHS = SExtPromotedInteger(N->getOperand(0));
453ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  SDValue RHS = SExtPromotedInteger(N->getOperand(1));
454e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OVT = N->getOperand(0).getValueType();
455e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = LHS.getValueType();
456ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
457ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
458ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Do the arithmetic in the larger type.
459ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  unsigned Opcode = N->getOpcode() == ISD::SADDO ? ISD::ADD : ISD::SUB;
460786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  SDValue Res = DAG.getNode(Opcode, dl, NVT, LHS, RHS);
461ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
462ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Calculate the overflow flag: sign extend the arithmetic result from
463ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // the original type.
464786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  SDValue Ofl = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, NVT, Res,
465ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands                            DAG.getValueType(OVT));
466ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Overflowed if and only if this is not equal to Res.
467786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Ofl = DAG.getSetCC(dl, N->getValueType(1), Ofl, Res, ISD::SETNE);
468ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
469ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Use the calculated overflow everywhere.
470ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  ReplaceValueWith(SDValue(N, 1), Ofl);
471ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
472ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  return Res;
473ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands}
474ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
475475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SDIV(SDNode *N) {
476bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Sign extend the input.
477c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue LHS = SExtPromotedInteger(N->getOperand(0));
478c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue RHS = SExtPromotedInteger(N->getOperand(1));
479ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(N->getOpcode(), SDLoc(N),
480786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                     LHS.getValueType(), LHS, RHS);
48169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
48269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
483475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SELECT(SDNode *N) {
484475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHS = GetPromotedInteger(N->getOperand(1));
485475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue RHS = GetPromotedInteger(N->getOperand(2));
486b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault  return DAG.getSelect(SDLoc(N),
487b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                       LHS.getValueType(), N->getOperand(0), LHS, RHS);
48869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
48969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
490436fe8498a0a3368d2690290e805213a0f114d0dNadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_VSELECT(SDNode *N) {
4916059b836959f4c1f1da651779d03d0de37f74a8fNadav Rotem  SDValue Mask = N->getOperand(0);
4926059b836959f4c1f1da651779d03d0de37f74a8fNadav Rotem  EVT OpTy = N->getOperand(1).getValueType();
4936059b836959f4c1f1da651779d03d0de37f74a8fNadav Rotem
4946059b836959f4c1f1da651779d03d0de37f74a8fNadav Rotem  // Promote all the way up to the canonical SetCC type.
495225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  Mask = PromoteTargetBoolean(Mask, getSetCCResultType(OpTy));
496436fe8498a0a3368d2690290e805213a0f114d0dNadav Rotem  SDValue LHS = GetPromotedInteger(N->getOperand(1));
497436fe8498a0a3368d2690290e805213a0f114d0dNadav Rotem  SDValue RHS = GetPromotedInteger(N->getOperand(2));
498ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::VSELECT, SDLoc(N),
499436fe8498a0a3368d2690290e805213a0f114d0dNadav Rotem                     LHS.getValueType(), Mask, LHS, RHS);
500436fe8498a0a3368d2690290e805213a0f114d0dNadav Rotem}
501436fe8498a0a3368d2690290e805213a0f114d0dNadav Rotem
502475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SELECT_CC(SDNode *N) {
503475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHS = GetPromotedInteger(N->getOperand(2));
504475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue RHS = GetPromotedInteger(N->getOperand(3));
505ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::SELECT_CC, SDLoc(N),
506786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                     LHS.getValueType(), N->getOperand(0),
507bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands                     N->getOperand(1), LHS, RHS, N->getOperand(4));
50869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
50969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
510475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SETCC(SDNode *N) {
511225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  EVT SVT = getSetCCResultType(N->getOperand(0).getValueType());
51217e76bda552d5afa652c4bb45f6dbdad67dc5c20Nadav Rotem
51317e76bda552d5afa652c4bb45f6dbdad67dc5c20Nadav Rotem  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
51417e76bda552d5afa652c4bb45f6dbdad67dc5c20Nadav Rotem
51517e76bda552d5afa652c4bb45f6dbdad67dc5c20Nadav Rotem  // Only use the result of getSetCCResultType if it is legal,
51617e76bda552d5afa652c4bb45f6dbdad67dc5c20Nadav Rotem  // otherwise just use the promoted result type (NVT).
517a3c42f3d4e5d14c8f4fb9bb123e7759c425d041bNadav Rotem  if (!TLI.isTypeLegal(SVT))
5185622eaeffef44dd09a1dd061299d6c02d9ad4099Eli Bendersky    SVT = NVT;
51928b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands
520ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
52128b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  assert(SVT.isVector() == N->getOperand(0).getValueType().isVector() &&
52228b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands         "Vector compare must return a vector result!");
5237e4982287591945c4e42ba8470a978e629789c76Duncan Sands
52471da6755c8b0a7444be5531798556c00f4dad101Hal Finkel  SDValue LHS = N->getOperand(0);
52571da6755c8b0a7444be5531798556c00f4dad101Hal Finkel  SDValue RHS = N->getOperand(1);
52671da6755c8b0a7444be5531798556c00f4dad101Hal Finkel  if (LHS.getValueType() != RHS.getValueType()) {
52771da6755c8b0a7444be5531798556c00f4dad101Hal Finkel    if (getTypeAction(LHS.getValueType()) == TargetLowering::TypePromoteInteger &&
52871da6755c8b0a7444be5531798556c00f4dad101Hal Finkel        !LHS.getValueType().isVector())
52971da6755c8b0a7444be5531798556c00f4dad101Hal Finkel      LHS = GetPromotedInteger(LHS);
53071da6755c8b0a7444be5531798556c00f4dad101Hal Finkel    if (getTypeAction(RHS.getValueType()) == TargetLowering::TypePromoteInteger &&
53171da6755c8b0a7444be5531798556c00f4dad101Hal Finkel        !RHS.getValueType().isVector())
53271da6755c8b0a7444be5531798556c00f4dad101Hal Finkel      RHS = GetPromotedInteger(RHS);
53371da6755c8b0a7444be5531798556c00f4dad101Hal Finkel  }
53471da6755c8b0a7444be5531798556c00f4dad101Hal Finkel
5357e4982287591945c4e42ba8470a978e629789c76Duncan Sands  // Get the SETCC result using the canonical SETCC type.
53671da6755c8b0a7444be5531798556c00f4dad101Hal Finkel  SDValue SetCC = DAG.getNode(N->getOpcode(), dl, SVT, LHS, RHS,
53771da6755c8b0a7444be5531798556c00f4dad101Hal Finkel                              N->getOperand(2));
5387e4982287591945c4e42ba8470a978e629789c76Duncan Sands
5396959b2bb6521baca57e5507ca039e51002d4a971Duncan Sands  assert(NVT.bitsLE(SVT) && "Integer type overpromoted?");
540a3c42f3d4e5d14c8f4fb9bb123e7759c425d041bNadav Rotem  // Convert to the expected type.
541786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  return DAG.getNode(ISD::TRUNCATE, dl, NVT, SetCC);
54269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
54369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
544475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SHL(SDNode *N) {
545a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  SDValue Res = GetPromotedInteger(N->getOperand(0));
546a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  SDValue Amt = N->getOperand(1);
547a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  Amt = Amt.getValueType().isVector() ? ZExtPromotedInteger(Amt) : Amt;
548ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::SHL, SDLoc(N), Res.getValueType(), Res, Amt);
54969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
55069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
551475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SIGN_EXTEND_INREG(SDNode *N) {
552475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
553ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::SIGN_EXTEND_INREG, SDLoc(N),
554786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                     Op.getValueType(), Op, N->getOperand(1));
5558d56a6f4d8b010d4c582225a08ece971613f6fe3Duncan Sands}
5568d56a6f4d8b010d4c582225a08ece971613f6fe3Duncan Sands
557475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SimpleIntBinOp(SDNode *N) {
558bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The input may have strange things in the top bits of the registers, but
559bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // these operations don't care.  They may have weird bits going out, but
560bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // that too is okay if they are integer operations.
561475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHS = GetPromotedInteger(N->getOperand(0));
562475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue RHS = GetPromotedInteger(N->getOperand(1));
563ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(N->getOpcode(), SDLoc(N),
5645622eaeffef44dd09a1dd061299d6c02d9ad4099Eli Bendersky                     LHS.getValueType(), LHS, RHS);
56569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
56669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
567475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SRA(SDNode *N) {
568bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The input value must be properly sign extended.
569c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue Res = SExtPromotedInteger(N->getOperand(0));
570a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  SDValue Amt = N->getOperand(1);
571a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  Amt = Amt.getValueType().isVector() ? ZExtPromotedInteger(Amt) : Amt;
572ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::SRA, SDLoc(N), Res.getValueType(), Res, Amt);
573bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
57469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
575475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_SRL(SDNode *N) {
576bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The input value must be properly zero extended.
577475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Res = ZExtPromotedInteger(N->getOperand(0));
578a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  SDValue Amt = N->getOperand(1);
579a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao  Amt = Amt.getValueType().isVector() ? ZExtPromotedInteger(Amt) : Amt;
580ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::SRL, SDLoc(N), Res.getValueType(), Res, Amt);
58169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
58269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
583475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_TRUNCATE(SDNode *N) {
58423b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
585475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Res;
5864720611025276f01b158a1522620391332ffdc32Nadav Rotem  SDValue InOp = N->getOperand(0);
587ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
58869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
5894720611025276f01b158a1522620391332ffdc32Nadav Rotem  switch (getTypeAction(InOp.getValueType())) {
590c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  default: llvm_unreachable("Unknown type action!");
59196e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeLegal:
59296e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypeExpandInteger:
5934720611025276f01b158a1522620391332ffdc32Nadav Rotem    Res = InOp;
594bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    break;
59596e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem  case TargetLowering::TypePromoteInteger:
5964720611025276f01b158a1522620391332ffdc32Nadav Rotem    Res = GetPromotedInteger(InOp);
597bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    break;
5984720611025276f01b158a1522620391332ffdc32Nadav Rotem  case TargetLowering::TypeSplitVector:
5994720611025276f01b158a1522620391332ffdc32Nadav Rotem    EVT InVT = InOp.getValueType();
6004720611025276f01b158a1522620391332ffdc32Nadav Rotem    assert(InVT.isVector() && "Cannot split scalar types");
6014720611025276f01b158a1522620391332ffdc32Nadav Rotem    unsigned NumElts = InVT.getVectorNumElements();
6024720611025276f01b158a1522620391332ffdc32Nadav Rotem    assert(NumElts == NVT.getVectorNumElements() &&
6034720611025276f01b158a1522620391332ffdc32Nadav Rotem           "Dst and Src must have the same number of elements");
6044720611025276f01b158a1522620391332ffdc32Nadav Rotem    assert(isPowerOf2_32(NumElts) &&
6054720611025276f01b158a1522620391332ffdc32Nadav Rotem           "Promoted vector type must be a power of two");
6064720611025276f01b158a1522620391332ffdc32Nadav Rotem
6075589a69f0abd39e583786515cf6c9170554dc8deNadav Rotem    SDValue EOp1, EOp2;
6085589a69f0abd39e583786515cf6c9170554dc8deNadav Rotem    GetSplitVector(InOp, EOp1, EOp2);
6095589a69f0abd39e583786515cf6c9170554dc8deNadav Rotem
6104720611025276f01b158a1522620391332ffdc32Nadav Rotem    EVT HalfNVT = EVT::getVectorVT(*DAG.getContext(), NVT.getScalarType(),
6114720611025276f01b158a1522620391332ffdc32Nadav Rotem                                   NumElts/2);
6124720611025276f01b158a1522620391332ffdc32Nadav Rotem    EOp1 = DAG.getNode(ISD::TRUNCATE, dl, HalfNVT, EOp1);
6134720611025276f01b158a1522620391332ffdc32Nadav Rotem    EOp2 = DAG.getNode(ISD::TRUNCATE, dl, HalfNVT, EOp2);
6144720611025276f01b158a1522620391332ffdc32Nadav Rotem
6154720611025276f01b158a1522620391332ffdc32Nadav Rotem    return DAG.getNode(ISD::CONCAT_VECTORS, dl, NVT, EOp1, EOp2);
616bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  }
617bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
618bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Truncate to NVT instead of VT
6194720611025276f01b158a1522620391332ffdc32Nadav Rotem  return DAG.getNode(ISD::TRUNCATE, dl, NVT, Res);
62069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
62169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
622ab0c578bfd1380326830180a9209df6c5be58887Duncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_UADDSUBO(SDNode *N, unsigned ResNo) {
623ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  if (ResNo == 1)
624ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands    return PromoteIntRes_Overflow(N);
625ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
62694c22716d60ff5edf6a98a3c67e0faa001be1142Sylvestre Ledru  // The operation overflowed iff the result in the larger type is not the
627ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // zero extension of its truncation to the original type.
628c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue LHS = ZExtPromotedInteger(N->getOperand(0));
629c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue RHS = ZExtPromotedInteger(N->getOperand(1));
630e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OVT = N->getOperand(0).getValueType();
631e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = LHS.getValueType();
632ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
63369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
634ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Do the arithmetic in the larger type.
635ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  unsigned Opcode = N->getOpcode() == ISD::UADDO ? ISD::ADD : ISD::SUB;
636786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  SDValue Res = DAG.getNode(Opcode, dl, NVT, LHS, RHS);
6378ac0d4b4fb10406278cd600214cd3ee6d76620cdBill Wendling
638ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Calculate the overflow flag: zero extend the arithmetic result from
639ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // the original type.
6404be0bdf7c1162824927dd3de89e016ae4934d0d6Dale Johannesen  SDValue Ofl = DAG.getZeroExtendInReg(Res, dl, OVT);
641ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Overflowed if and only if this is not equal to Res.
642786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Ofl = DAG.getSetCC(dl, N->getValueType(1), Ofl, Res, ISD::SETNE);
6438ac0d4b4fb10406278cd600214cd3ee6d76620cdBill Wendling
644ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Use the calculated overflow everywhere.
645ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  ReplaceValueWith(SDValue(N, 1), Ofl);
6468ac0d4b4fb10406278cd600214cd3ee6d76620cdBill Wendling
647ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  return Res;
648ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands}
649ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands
6505c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris LattnerSDValue DAGTypeLegalizer::PromoteIntRes_XMULO(SDNode *N, unsigned ResNo) {
6515c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  // Promote the overflow bit trivially.
6525c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  if (ResNo == 1)
6535c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    return PromoteIntRes_Overflow(N);
654fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands
6555c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  SDValue LHS = N->getOperand(0), RHS = N->getOperand(1);
656ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc DL(N);
657fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands  EVT SmallVT = LHS.getValueType();
658fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands
659b3e009a165a423536acfa5861c12ef631239d9e4Eric Christopher  // To determine if the result overflowed in a larger type, we extend the
66048da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // input to the larger type, do the multiply (checking if it overflows),
66148da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // then also check the high bits of the result to see if overflow happened
66248da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // there.
6635c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  if (N->getOpcode() == ISD::SMULO) {
6645c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    LHS = SExtPromotedInteger(LHS);
6655c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    RHS = SExtPromotedInteger(RHS);
6665c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  } else {
6675c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    LHS = ZExtPromotedInteger(LHS);
6685c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    RHS = ZExtPromotedInteger(RHS);
6695c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  }
67048da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  SDVTList VTs = DAG.getVTList(LHS.getValueType(), N->getValueType(1));
67148da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  SDValue Mul = DAG.getNode(N->getOpcode(), DL, VTs, LHS, RHS);
672fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands
67348da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // Overflow occurred if it occurred in the larger type, or if the high part
67448da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // of the result does not zero/sign-extend the low part.  Check this second
67548da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // possibility first.
6765c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  SDValue Overflow;
6775c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  if (N->getOpcode() == ISD::UMULO) {
67848da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands    // Unsigned overflow occurred if the high part is non-zero.
6795c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    SDValue Hi = DAG.getNode(ISD::SRL, DL, Mul.getValueType(), Mul,
680fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands                             DAG.getIntPtrConstant(SmallVT.getSizeInBits()));
6815c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner    Overflow = DAG.getSetCC(DL, N->getValueType(1), Hi,
6825c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner                            DAG.getConstant(0, Hi.getValueType()), ISD::SETNE);
6835c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  } else {
68448da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands    // Signed overflow occurred if the high part does not sign extend the low.
685fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands    SDValue SExt = DAG.getNode(ISD::SIGN_EXTEND_INREG, DL, Mul.getValueType(),
686fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands                               Mul, DAG.getValueType(SmallVT));
687fbd53f79f5d475d103fba9303a4aa7e88567dd1aDuncan Sands    Overflow = DAG.getSetCC(DL, N->getValueType(1), SExt, Mul, ISD::SETNE);
6885c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  }
6895c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner
69048da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // The only other way for overflow to occur is if the multiplication in the
69148da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  // larger type itself overflowed.
69248da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands  Overflow = DAG.getNode(ISD::OR, DL, N->getValueType(1), Overflow,
69348da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands                         SDValue(Mul.getNode(), 1));
69448da0be8b5821dddbb5233ad9cb198369031684bDuncan Sands
6955c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  // Use the calculated overflow everywhere.
6965c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  ReplaceValueWith(SDValue(N, 1), Overflow);
6975c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner  return Mul;
6985c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner}
6995c3d4f0fc90c86a6c4ee9871835d70c9ff3833d5Chris Lattner
700ab0c578bfd1380326830180a9209df6c5be58887Duncan SandsSDValue DAGTypeLegalizer::PromoteIntRes_UDIV(SDNode *N) {
701ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  // Zero extend the input.
702ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  SDValue LHS = ZExtPromotedInteger(N->getOperand(0));
703ab0c578bfd1380326830180a9209df6c5be58887Duncan Sands  SDValue RHS = ZExtPromotedInteger(N->getOperand(1));
704ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(N->getOpcode(), SDLoc(N),
705786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                     LHS.getValueType(), LHS, RHS);
7068ac0d4b4fb10406278cd600214cd3ee6d76620cdBill Wendling}
7078ac0d4b4fb10406278cd600214cd3ee6d76620cdBill Wendling
708475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_UNDEF(SDNode *N) {
70953f6ed9560aa4586ba217fbf94acbfada52f561fEvan Cheng  return DAG.getUNDEF(TLI.getTypeToTransformTo(*DAG.getContext(),
71053f6ed9560aa4586ba217fbf94acbfada52f561fEvan Cheng                                               N->getValueType(0)));
71169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
71269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
713475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntRes_VAARG(SDNode *N) {
714475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Chain = N->getOperand(0); // Get the chain.
715475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ptr = N->getOperand(1); // Get the pointer.
716e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
717ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
71869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
719dfcf33a287d1756721f1f735af687595ce2f5a21Patrik Hagglund  MVT RegVT = TLI.getRegisterType(*DAG.getContext(), VT);
72023b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  unsigned NumRegs = TLI.getNumRegisters(*DAG.getContext(), VT);
721d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  // The argument is passed as NumRegs registers of type RegVT.
722d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands
723d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  SmallVector<SDValue, 8> Parts(NumRegs);
724d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  for (unsigned i = 0; i < NumRegs; ++i) {
725cbeeae23c31d32b833c9c7c3e8984e4cbcf22f45Rafael Espindola    Parts[i] = DAG.getVAArg(RegVT, dl, Chain, Ptr, N->getOperand(2),
726cbeeae23c31d32b833c9c7c3e8984e4cbcf22f45Rafael Espindola                            N->getConstantOperandVal(3));
727d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands    Chain = Parts[i].getValue(1);
728d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  }
72969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
730d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  // Handle endianness of the load.
731d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  if (TLI.isBigEndian())
732d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands    std::reverse(Parts.begin(), Parts.end());
73369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
734d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  // Assemble the parts in the promoted type.
73523b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
736786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  SDValue Res = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, Parts[0]);
737d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  for (unsigned i = 1; i < NumRegs; ++i) {
738786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    SDValue Part = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, Parts[i]);
739d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands    // Shift it to the right position and "or" it in.
740786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Part = DAG.getNode(ISD::SHL, dl, NVT, Part,
741d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands                       DAG.getConstant(i * RegVT.getSizeInBits(),
74292abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                                       TLI.getPointerTy()));
743786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Res = DAG.getNode(ISD::OR, dl, NVT, Res, Part);
744d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  }
74569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
746d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  // Modified the chain result - switch anything that used the old chain to
747bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // use the new one.
748d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  ReplaceValueWith(SDValue(N, 1), Chain);
749d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands
750d821726a91000c1b2de7ca8aafdc27b1a311741bDuncan Sands  return Res;
75169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
75269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
753bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands//===----------------------------------------------------------------------===//
754bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands//  Integer Operand Promotion
755bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands//===----------------------------------------------------------------------===//
7567fc8ab81f5f46dcba0f76b1c546a1d11ccbebe26Duncan Sands
757bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands/// PromoteIntegerOperand - This method is called when the specified operand of
758bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands/// the specified node is found to need promotion.  At this point, all of the
759bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands/// result types of the node are known to be legal, but other operands of the
760bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands/// node may need promotion or expansion as well as the specified one.
761bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sandsbool DAGTypeLegalizer::PromoteIntegerOperand(SDNode *N, unsigned OpNo) {
762d765353da89988e949fd4c021d8860f36ab7c392David Greene  DEBUG(dbgs() << "Promote integer operand: "; N->dump(&DAG); dbgs() << "\n");
763475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Res = SDValue();
7647fc8ab81f5f46dcba0f76b1c546a1d11ccbebe26Duncan Sands
765f43071beddb7ed5b2fd7d2f06c4130460616a13dDuncan Sands  if (CustomLowerNode(N, N->getOperand(OpNo).getValueType(), false))
766bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta    return false;
76769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
768bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  switch (N->getOpcode()) {
769bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta    default:
770bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  #ifndef NDEBUG
771d765353da89988e949fd4c021d8860f36ab7c392David Greene    dbgs() << "PromoteIntegerOperand Op #" << OpNo << ": ";
772d765353da89988e949fd4c021d8860f36ab7c392David Greene    N->dump(&DAG); dbgs() << "\n";
773bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  #endif
774c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    llvm_unreachable("Do not know how to promote this operator's operand!");
775bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
776bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::ANY_EXTEND:   Res = PromoteIntOp_ANY_EXTEND(N); break;
777331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  case ISD::ATOMIC_STORE:
778331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman    Res = PromoteIntOp_ATOMIC_STORE(cast<AtomicSDNode>(N));
779331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman    break;
780bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck  case ISD::BITCAST:      Res = PromoteIntOp_BITCAST(N); break;
781bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::BR_CC:        Res = PromoteIntOp_BR_CC(N, OpNo); break;
782bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::BRCOND:       Res = PromoteIntOp_BRCOND(N, OpNo); break;
783bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::BUILD_PAIR:   Res = PromoteIntOp_BUILD_PAIR(N); break;
784bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::BUILD_VECTOR: Res = PromoteIntOp_BUILD_VECTOR(N); break;
785fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::CONCAT_VECTORS: Res = PromoteIntOp_CONCAT_VECTORS(N); break;
786fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  case ISD::EXTRACT_VECTOR_ELT: Res = PromoteIntOp_EXTRACT_VECTOR_ELT(N); break;
787bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::CONVERT_RNDSAT:
788bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta                          Res = PromoteIntOp_CONVERT_RNDSAT(N); break;
789bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::INSERT_VECTOR_ELT:
790bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta                          Res = PromoteIntOp_INSERT_VECTOR_ELT(N, OpNo);break;
791aa9df0b0c3cef33514095bde2eedead986677955Mon P Wang  case ISD::SCALAR_TO_VECTOR:
792aa9df0b0c3cef33514095bde2eedead986677955Mon P Wang                          Res = PromoteIntOp_SCALAR_TO_VECTOR(N); break;
79328b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  case ISD::VSELECT:
794bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::SELECT:       Res = PromoteIntOp_SELECT(N, OpNo); break;
795bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::SELECT_CC:    Res = PromoteIntOp_SELECT_CC(N, OpNo); break;
796bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::SETCC:        Res = PromoteIntOp_SETCC(N, OpNo); break;
797bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::SIGN_EXTEND:  Res = PromoteIntOp_SIGN_EXTEND(N); break;
798bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::SINT_TO_FP:   Res = PromoteIntOp_SINT_TO_FP(N); break;
799bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::STORE:        Res = PromoteIntOp_STORE(cast<StoreSDNode>(N),
800bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta                                                   OpNo); break;
801bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::TRUNCATE:     Res = PromoteIntOp_TRUNCATE(N); break;
802927411b7ce0b7852fe4f392d8cd4faaa3881f852Anton Korobeynikov  case ISD::FP16_TO_FP32:
803bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::UINT_TO_FP:   Res = PromoteIntOp_UINT_TO_FP(N); break;
804bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::ZERO_EXTEND:  Res = PromoteIntOp_ZERO_EXTEND(N); break;
80555467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta
80655467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::SHL:
80755467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::SRA:
80855467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::SRL:
80955467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::ROTL:
81055467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::ROTR: Res = PromoteIntOp_Shift(N); break;
811bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  }
8129fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands
813bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // If the result is null, the sub-method took care of registering results etc.
8149fbc7e2e7a765298fb4326885b407e0962f7ab62Duncan Sands  if (!Res.getNode()) return false;
81547d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands
81647d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands  // If the result is N, the sub-method updated N in place.  Tell the legalizer
81747d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands  // core about this.
81847d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands  if (Res.getNode() == N)
819bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands    return true;
820bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
821bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(Res.getValueType() == N->getValueType(0) && N->getNumValues() == 1 &&
822bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands         "Invalid operand expansion");
823bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
824475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  ReplaceValueWith(SDValue(N, 0), Res);
825bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  return false;
82669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
82769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
82869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// PromoteSetCCOperands - Promote the operands of a comparison.  This code is
82969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// shared among BR_CC, SELECT_CC, and SETCC handlers.
830475871a144eb604ddaf37503397ba0941442e5fbDan Gohmanvoid DAGTypeLegalizer::PromoteSetCCOperands(SDValue &NewLHS,SDValue &NewRHS,
83169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands                                            ISD::CondCode CCCode) {
832cff50d9e20d7bbc3acf4845fe826bfb3095126c4Duncan Sands  // We have to insert explicit sign or zero extends.  Note that we could
833cff50d9e20d7bbc3acf4845fe826bfb3095126c4Duncan Sands  // insert sign extends for ALL conditions, but zero extend is cheaper on
834cff50d9e20d7bbc3acf4845fe826bfb3095126c4Duncan Sands  // many machines (an AND instead of two shifts), so prefer it.
83569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  switch (CCCode) {
836c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  default: llvm_unreachable("Unknown integer comparison!");
83769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETEQ:
83869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETNE:
83969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETUGE:
84069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETUGT:
84169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETULE:
84269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETULT:
84369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // ALL of these operations will work if we either sign or zero extend
84469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // the operands (including the unsigned comparisons!).  Zero extend is
84569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // usually a simpler/cheaper operation, so prefer it.
846c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands    NewLHS = ZExtPromotedInteger(NewLHS);
847c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands    NewRHS = ZExtPromotedInteger(NewRHS);
84811ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands    break;
84969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETGE:
85069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETGT:
85169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETLT:
85269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::SETLE:
853c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands    NewLHS = SExtPromotedInteger(NewLHS);
854c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands    NewRHS = SExtPromotedInteger(NewRHS);
85511ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands    break;
85669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  }
85769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
85869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
859475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_ANY_EXTEND(SDNode *N) {
860475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
861ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::ANY_EXTEND, SDLoc(N), N->getValueType(0), Op);
862bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
86369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
864331120b1a482b782e8dffce63033bb8514ba2a96Eli FriedmanSDValue DAGTypeLegalizer::PromoteIntOp_ATOMIC_STORE(AtomicSDNode *N) {
865331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman  SDValue Op2 = GetPromotedInteger(N->getOperand(2));
866ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getAtomic(N->getOpcode(), SDLoc(N), N->getMemoryVT(),
867331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman                       N->getChain(), N->getBasePtr(), Op2, N->getMemOperand(),
868331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman                       N->getOrdering(), N->getSynchScope());
869331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman}
870331120b1a482b782e8dffce63033bb8514ba2a96Eli Friedman
871bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley PeckSDValue DAGTypeLegalizer::PromoteIntOp_BITCAST(SDNode *N) {
87227759f41ca1c930e2860275c9ba2567a5890d7d2Eli Friedman  // This should only occur in unusual situations like bitcasting to an
87327759f41ca1c930e2860275c9ba2567a5890d7d2Eli Friedman  // x86_fp80, so just turn it into a store+load
87427759f41ca1c930e2860275c9ba2567a5890d7d2Eli Friedman  return CreateStackStoreLoad(N->getOperand(0), N->getValueType(0));
87527759f41ca1c930e2860275c9ba2567a5890d7d2Eli Friedman}
87627759f41ca1c930e2860275c9ba2567a5890d7d2Eli Friedman
877475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_BR_CC(SDNode *N, unsigned OpNo) {
878bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(OpNo == 2 && "Don't know how to promote this operand!");
87969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
880475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHS = N->getOperand(2);
881475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue RHS = N->getOperand(3);
882bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  PromoteSetCCOperands(LHS, RHS, cast<CondCodeSDNode>(N->getOperand(1))->get());
88369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
884bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The chain (Op#0), CC (#1) and basic block destination (Op#4) are always
885bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // legal types.
886027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
887027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                N->getOperand(1), LHS, RHS, N->getOperand(4)),
888027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                 0);
889bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
890bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
891475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_BRCOND(SDNode *N, unsigned OpNo) {
892bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(OpNo == 1 && "only know how to promote condition");
893bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
894b6e223a9e806921183da972253c49082a2e07944Duncan Sands  // Promote all the way up to the canonical SetCC type.
895225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  EVT SVT = getSetCCResultType(MVT::Other);
896b6e223a9e806921183da972253c49082a2e07944Duncan Sands  SDValue Cond = PromoteTargetBoolean(N->getOperand(1), SVT);
897bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
898bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The chain (Op#0) and basic block destination (Op#2) are always legal types.
899027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), Cond,
900027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                        N->getOperand(2)), 0);
901bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
902bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
903475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_BUILD_PAIR(SDNode *N) {
904bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Since the result type is legal, the operands must promote to it.
905e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT OVT = N->getOperand(0).getValueType();
906c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands  SDValue Lo = ZExtPromotedInteger(N->getOperand(0));
907475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Hi = GetPromotedInteger(N->getOperand(1));
908bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(Lo.getValueType() == N->getValueType(0) && "Operand over promoted?");
909ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
910bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
911786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Hi = DAG.getNode(ISD::SHL, dl, N->getValueType(0), Hi,
91292abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                   DAG.getConstant(OVT.getSizeInBits(), TLI.getPointerTy()));
913786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  return DAG.getNode(ISD::OR, dl, N->getValueType(0), Lo, Hi);
91469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
91569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
916475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_BUILD_VECTOR(SDNode *N) {
91769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // The vector type is legal but the element type is not.  This implies
91869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // that the vector is a power-of-two in length and that the element
91969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // type does not have a strange size (eg: it is not i1).
920e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VecVT = N->getValueType(0);
92169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  unsigned NumElts = VecVT.getVectorNumElements();
92269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  assert(!(NumElts & 1) && "Legal vector of one illegal element?");
92369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
924b1303d05a89972195de023fda432cc621375a27cBob Wilson  // Promote the inserted value.  The type does not need to match the
925b1303d05a89972195de023fda432cc621375a27cBob Wilson  // vector element type.  Check that any extra bits introduced will be
926b1303d05a89972195de023fda432cc621375a27cBob Wilson  // truncated away.
927b1303d05a89972195de023fda432cc621375a27cBob Wilson  assert(N->getOperand(0).getValueType().getSizeInBits() >=
928b1303d05a89972195de023fda432cc621375a27cBob Wilson         N->getValueType(0).getVectorElementType().getSizeInBits() &&
929b1303d05a89972195de023fda432cc621375a27cBob Wilson         "Type of inserted value narrower than vector element type!");
93069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
931b1303d05a89972195de023fda432cc621375a27cBob Wilson  SmallVector<SDValue, 16> NewOps;
932c885165e664f3b465403e1b6ce57ba63f57c5f0cBob Wilson  for (unsigned i = 0; i < NumElts; ++i)
933b1303d05a89972195de023fda432cc621375a27cBob Wilson    NewOps.push_back(GetPromotedInteger(N->getOperand(i)));
93469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
935027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, &NewOps[0], NumElts), 0);
93669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
93769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
93828088d3c049017a131aa7b07201c6e19c0227cefMon P WangSDValue DAGTypeLegalizer::PromoteIntOp_CONVERT_RNDSAT(SDNode *N) {
93928088d3c049017a131aa7b07201c6e19c0227cefMon P Wang  ISD::CvtCode CvtCode = cast<CvtRndSatSDNode>(N)->getCvtCode();
94028088d3c049017a131aa7b07201c6e19c0227cefMon P Wang  assert ((CvtCode == ISD::CVT_SS || CvtCode == ISD::CVT_SU ||
94128088d3c049017a131aa7b07201c6e19c0227cefMon P Wang           CvtCode == ISD::CVT_US || CvtCode == ISD::CVT_UU ||
94228088d3c049017a131aa7b07201c6e19c0227cefMon P Wang           CvtCode == ISD::CVT_FS || CvtCode == ISD::CVT_FU) &&
94328088d3c049017a131aa7b07201c6e19c0227cefMon P Wang           "can only promote integer arguments");
94428088d3c049017a131aa7b07201c6e19c0227cefMon P Wang  SDValue InOp = GetPromotedInteger(N->getOperand(0));
945ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getConvertRndSat(N->getValueType(0), SDLoc(N), InOp,
94628088d3c049017a131aa7b07201c6e19c0227cefMon P Wang                              N->getOperand(1), N->getOperand(2),
94728088d3c049017a131aa7b07201c6e19c0227cefMon P Wang                              N->getOperand(3), N->getOperand(4), CvtCode);
94828088d3c049017a131aa7b07201c6e19c0227cefMon P Wang}
94928088d3c049017a131aa7b07201c6e19c0227cefMon P Wang
950475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_INSERT_VECTOR_ELT(SDNode *N,
951475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                                         unsigned OpNo) {
95269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  if (OpNo == 1) {
95369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // Promote the inserted value.  This is valid because the type does not
95469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // have to match the vector element type.
95569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
95669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    // Check that any extra bits introduced will be truncated away.
95769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    assert(N->getOperand(1).getValueType().getSizeInBits() >=
95869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands           N->getValueType(0).getVectorElementType().getSizeInBits() &&
95969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands           "Type of inserted value narrower than vector element type!");
960027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman    return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
96169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands                                  GetPromotedInteger(N->getOperand(1)),
962027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                  N->getOperand(2)),
963027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                   0);
96469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  }
96569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
96669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  assert(OpNo == 2 && "Different operand and result vector types?");
96769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
96869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // Promote the index.
969425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard  SDValue Idx = DAG.getZExtOrTrunc(N->getOperand(2), SDLoc(N),
970425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard                                   TLI.getVectorIdxTy());
971027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
972027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                N->getOperand(1), Idx), 0);
97369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands}
97469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
975aa9df0b0c3cef33514095bde2eedead986677955Mon P WangSDValue DAGTypeLegalizer::PromoteIntOp_SCALAR_TO_VECTOR(SDNode *N) {
976b10b5ac8d9da43ca2db61401a20af6b676c98438Duncan Sands  // Integer SCALAR_TO_VECTOR operands are implicitly truncated, so just promote
977b10b5ac8d9da43ca2db61401a20af6b676c98438Duncan Sands  // the operand in place.
978027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N,
979027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                GetPromotedInteger(N->getOperand(0))), 0);
980aa9df0b0c3cef33514095bde2eedead986677955Mon P Wang}
981aa9df0b0c3cef33514095bde2eedead986677955Mon P Wang
982475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_SELECT(SDNode *N, unsigned OpNo) {
98328b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  assert(OpNo == 0 && "Only know how to promote the condition!");
98428b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  SDValue Cond = N->getOperand(0);
98528b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  EVT OpTy = N->getOperand(1).getValueType();
9867e4982287591945c4e42ba8470a978e629789c76Duncan Sands
987b6e223a9e806921183da972253c49082a2e07944Duncan Sands  // Promote all the way up to the canonical SetCC type.
988225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  EVT SVT = getSetCCResultType(N->getOpcode() == ISD::SELECT ?
98928b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands                                   OpTy.getScalarType() : OpTy);
99028b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  Cond = PromoteTargetBoolean(Cond, SVT);
991bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
99228b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands  return SDValue(DAG.UpdateNodeOperands(N, Cond, N->getOperand(1),
99328b77e968d2b01fc9da724762bd8ddcd80650e32Duncan Sands                                        N->getOperand(2)), 0);
994bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
995bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
996475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_SELECT_CC(SDNode *N, unsigned OpNo) {
997bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(OpNo == 0 && "Don't know how to promote this operand!");
998bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
999475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHS = N->getOperand(0);
1000475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue RHS = N->getOperand(1);
1001bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  PromoteSetCCOperands(LHS, RHS, cast<CondCodeSDNode>(N->getOperand(4))->get());
1002bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1003bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The CC (#4) and the possible return values (#2 and #3) have legal types.
1004027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, LHS, RHS, N->getOperand(2),
1005027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                N->getOperand(3), N->getOperand(4)), 0);
1006bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
1007bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1008475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_SETCC(SDNode *N, unsigned OpNo) {
1009bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(OpNo == 0 && "Don't know how to promote this operand!");
1010bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1011475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHS = N->getOperand(0);
1012475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue RHS = N->getOperand(1);
1013bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  PromoteSetCCOperands(LHS, RHS, cast<CondCodeSDNode>(N->getOperand(2))->get());
1014bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1015bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // The CC (#2) is always legal.
1016027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, LHS, RHS, N->getOperand(2)), 0);
1017bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
1018bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
101955467af31620c9d027e071ebcd9746b7593cff17Sanjiv GuptaSDValue DAGTypeLegalizer::PromoteIntOp_Shift(SDNode *N) {
1020027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
1021027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                ZExtPromotedInteger(N->getOperand(1))), 0);
102255467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta}
102355467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta
1024475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_SIGN_EXTEND(SDNode *N) {
1025475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
1026ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1027786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Op = DAG.getNode(ISD::ANY_EXTEND, dl, N->getValueType(0), Op);
1028786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  return DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Op.getValueType(),
1029bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands                     Op, DAG.getValueType(N->getOperand(0).getValueType()));
1030bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
1031bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1032c08468774b65dc288c44076d428f4beddabe58e2Duncan SandsSDValue DAGTypeLegalizer::PromoteIntOp_SINT_TO_FP(SDNode *N) {
1033027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N,
1034027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                SExtPromotedInteger(N->getOperand(0))), 0);
1035c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands}
1036c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands
1037475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_STORE(StoreSDNode *N, unsigned OpNo){
1038bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  assert(ISD::isUNINDEXEDStore(N) && "Indexed store during type legalization!");
1039475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ch = N->getChain(), Ptr = N->getBasePtr();
1040bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  unsigned Alignment = N->getAlignment();
1041bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  bool isVolatile = N->isVolatile();
10421e559443a17d1b335f697551c6263ba60d5dd827David Greene  bool isNonTemporal = N->isNonTemporal();
1043ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1044bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1045475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Val = GetPromotedInteger(N->getValue());  // Get promoted value.
1046bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1047bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands  // Truncate the value and store the result.
1048ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  return DAG.getTruncStore(Ch, dl, Val, Ptr, N->getPointerInfo(),
1049ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                           N->getMemoryVT(),
10501e559443a17d1b335f697551c6263ba60d5dd827David Greene                           isVolatile, isNonTemporal, Alignment);
1051bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
1052bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1053475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_TRUNCATE(SDNode *N) {
1054475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
1055ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::TRUNCATE, SDLoc(N), N->getValueType(0), Op);
1056bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
1057bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
1058c08468774b65dc288c44076d428f4beddabe58e2Duncan SandsSDValue DAGTypeLegalizer::PromoteIntOp_UINT_TO_FP(SDNode *N) {
1059027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N,
1060027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                ZExtPromotedInteger(N->getOperand(0))), 0);
1061c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands}
1062c08468774b65dc288c44076d428f4beddabe58e2Duncan Sands
1063475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::PromoteIntOp_ZERO_EXTEND(SDNode *N) {
1064ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1065475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = GetPromotedInteger(N->getOperand(0));
10664be0bdf7c1162824927dd3de89e016ae4934d0d6Dale Johannesen  Op = DAG.getNode(ISD::ANY_EXTEND, dl, N->getValueType(0), Op);
10678e614322498f9b38995a6bf41100ca617180eacbNadav Rotem  return DAG.getZeroExtendInReg(Op, dl,
10688e614322498f9b38995a6bf41100ca617180eacbNadav Rotem                                N->getOperand(0).getValueType().getScalarType());
1069bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands}
1070bf304c20651b80309af4c0fb3a14c0d73eaa984fDuncan Sands
107169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
107269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands//===----------------------------------------------------------------------===//
107369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands//  Integer Result Expansion
107469b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands//===----------------------------------------------------------------------===//
107569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
107669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands/// ExpandIntegerResult - This method is called when the specified result of the
1077cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner/// specified node is found to need expansion.  At this point, the node may also
1078cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner/// have invalid operands or may have other results that need promotion, we just
1079cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner/// know that (at least) one result needs expansion.
108069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sandsvoid DAGTypeLegalizer::ExpandIntegerResult(SDNode *N, unsigned ResNo) {
1081d765353da89988e949fd4c021d8860f36ab7c392David Greene  DEBUG(dbgs() << "Expand integer result: "; N->dump(&DAG); dbgs() << "\n");
1082475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Lo, Hi;
1083475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  Lo = Hi = SDValue();
1084cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1085cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // See if the target wants to custom expand this node.
1086f43071beddb7ed5b2fd7d2f06c4130460616a13dDuncan Sands  if (CustomLowerNode(N, N->getValueType(ResNo), true))
10871607f05cb7d77d01ce521a30232faa389dbed4e2Duncan Sands    return;
1088cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1089cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  switch (N->getOpcode()) {
1090cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  default:
1091cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner#ifndef NDEBUG
1092d765353da89988e949fd4c021d8860f36ab7c392David Greene    dbgs() << "ExpandIntegerResult #" << ResNo << ": ";
1093d765353da89988e949fd4c021d8860f36ab7c392David Greene    N->dump(&DAG); dbgs() << "\n";
1094cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner#endif
1095c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    llvm_unreachable("Do not know how to expand the result of this operator!");
109669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
10974c19e12d28749c717d3b384962c9ec92796af1c9Duncan Sands  case ISD::MERGE_VALUES: SplitRes_MERGE_VALUES(N, ResNo, Lo, Hi); break;
109878cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  case ISD::SELECT:       SplitRes_SELECT(N, Lo, Hi); break;
109978cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  case ISD::SELECT_CC:    SplitRes_SELECT_CC(N, Lo, Hi); break;
110078cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  case ISD::UNDEF:        SplitRes_UNDEF(N, Lo, Hi); break;
110178cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands
1102bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck  case ISD::BITCAST:            ExpandRes_BITCAST(N, Lo, Hi); break;
110378cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  case ISD::BUILD_PAIR:         ExpandRes_BUILD_PAIR(N, Lo, Hi); break;
11044a307ecce68f90e0eebf1ded52b947816cdc2304Duncan Sands  case ISD::EXTRACT_ELEMENT:    ExpandRes_EXTRACT_ELEMENT(N, Lo, Hi); break;
110578cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  case ISD::EXTRACT_VECTOR_ELT: ExpandRes_EXTRACT_VECTOR_ELT(N, Lo, Hi); break;
110621c2972f7d24680f6475877a3398b7f8cf515b33Duncan Sands  case ISD::VAARG:              ExpandRes_VAARG(N, Lo, Hi); break;
110778cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands
110869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::ANY_EXTEND:  ExpandIntRes_ANY_EXTEND(N, Lo, Hi); break;
110995db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  case ISD::AssertSext:  ExpandIntRes_AssertSext(N, Lo, Hi); break;
111069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::AssertZext:  ExpandIntRes_AssertZext(N, Lo, Hi); break;
111105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::BSWAP:       ExpandIntRes_BSWAP(N, Lo, Hi); break;
111205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::Constant:    ExpandIntRes_Constant(N, Lo, Hi); break;
111363974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  case ISD::CTLZ_ZERO_UNDEF:
111405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::CTLZ:        ExpandIntRes_CTLZ(N, Lo, Hi); break;
111505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::CTPOP:       ExpandIntRes_CTPOP(N, Lo, Hi); break;
111663974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  case ISD::CTTZ_ZERO_UNDEF:
111705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::CTTZ:        ExpandIntRes_CTTZ(N, Lo, Hi); break;
111869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::FP_TO_SINT:  ExpandIntRes_FP_TO_SINT(N, Lo, Hi); break;
111969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::FP_TO_UINT:  ExpandIntRes_FP_TO_UINT(N, Lo, Hi); break;
112069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  case ISD::LOAD:        ExpandIntRes_LOAD(cast<LoadSDNode>(N), Lo, Hi); break;
112105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::MUL:         ExpandIntRes_MUL(N, Lo, Hi); break;
112205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SDIV:        ExpandIntRes_SDIV(N, Lo, Hi); break;
112305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SIGN_EXTEND: ExpandIntRes_SIGN_EXTEND(N, Lo, Hi); break;
112405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SIGN_EXTEND_INREG: ExpandIntRes_SIGN_EXTEND_INREG(N, Lo, Hi); break;
112505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SREM:        ExpandIntRes_SREM(N, Lo, Hi); break;
112605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::TRUNCATE:    ExpandIntRes_TRUNCATE(N, Lo, Hi); break;
112705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::UDIV:        ExpandIntRes_UDIV(N, Lo, Hi); break;
112805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::UREM:        ExpandIntRes_UREM(N, Lo, Hi); break;
112905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::ZERO_EXTEND: ExpandIntRes_ZERO_EXTEND(N, Lo, Hi); break;
1130ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  case ISD::ATOMIC_LOAD: ExpandIntRes_ATOMIC_LOAD(N, Lo, Hi); break;
113169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
11328d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_ADD:
11338d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_SUB:
11348d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_AND:
11358d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_OR:
11368d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_XOR:
11378d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_NAND:
11388d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_MIN:
11398d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_MAX:
11408d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_UMIN:
11418d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  case ISD::ATOMIC_LOAD_UMAX:
1142dfccd9ee98cd6590bd82fa6edf24d510d953a2a0Lang Hames  case ISD::ATOMIC_SWAP:
1143dfccd9ee98cd6590bd82fa6edf24d510d953a2a0Lang Hames  case ISD::ATOMIC_CMP_SWAP: {
11448d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher    std::pair<SDValue, SDValue> Tmp = ExpandAtomic(N);
11458d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher    SplitInteger(Tmp.first, Lo, Hi);
11468d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher    ReplaceValueWith(SDValue(N, 1), Tmp.second);
11478d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher    break;
11488d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher  }
11498d93d19076fb6a67eeb63cb0ba79d00c3aa8478aEric Christopher
1150cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::AND:
1151cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::OR:
115205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::XOR: ExpandIntRes_Logical(N, Lo, Hi); break;
115305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1154cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::ADD:
115505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SUB: ExpandIntRes_ADDSUB(N, Lo, Hi); break;
115605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1157cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::ADDC:
115805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SUBC: ExpandIntRes_ADDSUBC(N, Lo, Hi); break;
115905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1160cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::ADDE:
116105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SUBE: ExpandIntRes_ADDSUBE(N, Lo, Hi); break;
116205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1163cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SHL:
1164cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SRA:
116505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  case ISD::SRL: ExpandIntRes_Shift(N, Lo, Hi); break;
1166268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
1167268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  case ISD::SADDO:
1168268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  case ISD::SSUBO: ExpandIntRes_SADDSUBO(N, Lo, Hi); break;
1169268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  case ISD::UADDO:
1170268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  case ISD::USUBO: ExpandIntRes_UADDSUBO(N, Lo, Hi); break;
1171362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  case ISD::UMULO:
1172362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  case ISD::SMULO: ExpandIntRes_XMULO(N, Lo, Hi); break;
1173cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
1174d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
1175cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // If Lo/Hi is null, the sub-method took care of registering results etc.
1176ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (Lo.getNode())
1177475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SetExpandedInteger(SDValue(N, ResNo), Lo, Hi);
1178cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
1179cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
118093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher/// Lower an atomic node to the appropriate builtin call.
118193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopherstd::pair <SDValue, SDValue> DAGTypeLegalizer::ExpandAtomic(SDNode *Node) {
118293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  unsigned Opc = Node->getOpcode();
118393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  MVT VT = cast<AtomicSDNode>(Node)->getMemoryVT().getSimpleVT();
118493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  RTLIB::Libcall LC;
118593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher
118693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  switch (Opc) {
118793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  default:
118893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    llvm_unreachable("Unhandled atomic intrinsic Expand!");
118993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_SWAP:
119093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
119193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
119293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_LOCK_TEST_AND_SET_1; break;
119393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_LOCK_TEST_AND_SET_2; break;
119493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_LOCK_TEST_AND_SET_4; break;
119593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_LOCK_TEST_AND_SET_8; break;
119693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
119793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
119893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_CMP_SWAP:
119993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
120093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
120193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_VAL_COMPARE_AND_SWAP_1; break;
120293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_VAL_COMPARE_AND_SWAP_2; break;
120393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_VAL_COMPARE_AND_SWAP_4; break;
120493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_VAL_COMPARE_AND_SWAP_8; break;
120593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
120693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
120793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_LOAD_ADD:
120893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
120993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
121093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_FETCH_AND_ADD_1; break;
121193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_FETCH_AND_ADD_2; break;
121293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_FETCH_AND_ADD_4; break;
121393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_FETCH_AND_ADD_8; break;
121493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
121593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
121693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_LOAD_SUB:
121793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
121893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
121993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_FETCH_AND_SUB_1; break;
122093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_FETCH_AND_SUB_2; break;
122193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_FETCH_AND_SUB_4; break;
122293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_FETCH_AND_SUB_8; break;
122393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
122493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
122593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_LOAD_AND:
122693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
122793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
122893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_FETCH_AND_AND_1; break;
122993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_FETCH_AND_AND_2; break;
123093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_FETCH_AND_AND_4; break;
123193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_FETCH_AND_AND_8; break;
123293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
123393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
123493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_LOAD_OR:
123593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
123693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
123793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_FETCH_AND_OR_1; break;
123893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_FETCH_AND_OR_2; break;
123993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_FETCH_AND_OR_4; break;
124093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_FETCH_AND_OR_8; break;
124193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
124293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
124393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_LOAD_XOR:
124493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
124593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
124693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_FETCH_AND_XOR_1; break;
124793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_FETCH_AND_XOR_2; break;
124893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_FETCH_AND_XOR_4; break;
124993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_FETCH_AND_XOR_8; break;
125093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
125193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
125293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  case ISD::ATOMIC_LOAD_NAND:
125393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    switch (VT.SimpleTy) {
125493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    default: llvm_unreachable("Unexpected value type for atomic!");
125593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i8:  LC = RTLIB::SYNC_FETCH_AND_NAND_1; break;
125693c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i16: LC = RTLIB::SYNC_FETCH_AND_NAND_2; break;
125793c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i32: LC = RTLIB::SYNC_FETCH_AND_NAND_4; break;
125893c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    case MVT::i64: LC = RTLIB::SYNC_FETCH_AND_NAND_8; break;
125993c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    }
126093c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher    break;
126193c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  }
126293c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher
126393c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher  return ExpandChainLibCall(LC, Node, false);
126493c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher}
126593c70426f581859f197df1b05fdb1b3664d361a0Eric Christopher
126605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// ExpandShiftByConstant - N is a shift by a value that needs to be expanded,
126705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// and the shift amount is a constant 'Amt'.  Expand the operation.
126805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandShiftByConstant(SDNode *N, unsigned Amt,
1269475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                             SDValue &Lo, SDValue &Hi) {
1270ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc DL(N);
127105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Expand the incoming operand to be shifted, so that we have its parts
1272475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue InL, InH;
127305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), InL, InH);
1274cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1275e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = InL.getValueType();
127605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  unsigned VTBits = N->getValueType(0).getSizeInBits();
127705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  unsigned NVTBits = NVT.getSizeInBits();
1278e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT ShTy = N->getOperand(1).getValueType();
1279cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
128005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (N->getOpcode() == ISD::SHL) {
128105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    if (Amt > VTBits) {
128205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Lo = Hi = DAG.getConstant(0, NVT);
128305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    } else if (Amt > NVTBits) {
128405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Lo = DAG.getConstant(0, NVT);
1285e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Hi = DAG.getNode(ISD::SHL, DL,
1286915eeb488786379250808d47668c43e010efe566Chris Lattner                       NVT, InL, DAG.getConstant(Amt-NVTBits, ShTy));
128705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    } else if (Amt == NVTBits) {
128805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Lo = DAG.getConstant(0, NVT);
128905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Hi = InL;
1290104de6cf7b80ec5e9beb502a069f376810a0a1e3Richard Osborne    } else if (Amt == 1 &&
1291f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman               TLI.isOperationLegalOrCustom(ISD::ADDC,
129254e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                              TLI.getTypeToExpandTo(*DAG.getContext(), NVT))) {
129305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      // Emit this X << 1 as X+X.
1294f1b4eafbfec976f939ec0ea3e8acf91cef5363e3Chris Lattner      SDVTList VTList = DAG.getVTList(NVT, MVT::Glue);
1295475871a144eb604ddaf37503397ba0941442e5fbDan Gohman      SDValue LoOps[2] = { InL, InL };
1296e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Lo = DAG.getNode(ISD::ADDC, DL, VTList, LoOps, 2);
1297475871a144eb604ddaf37503397ba0941442e5fbDan Gohman      SDValue HiOps[3] = { InH, InH, Lo.getValue(1) };
1298e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Hi = DAG.getNode(ISD::ADDE, DL, VTList, HiOps, 3);
129905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    } else {
1300e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Lo = DAG.getNode(ISD::SHL, DL, NVT, InL, DAG.getConstant(Amt, ShTy));
1301e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Hi = DAG.getNode(ISD::OR, DL, NVT,
1302e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner                       DAG.getNode(ISD::SHL, DL, NVT, InH,
130305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                   DAG.getConstant(Amt, ShTy)),
1304e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner                       DAG.getNode(ISD::SRL, DL, NVT, InL,
130505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                   DAG.getConstant(NVTBits-Amt, ShTy)));
130605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    }
130705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    return;
1308cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
1309cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
131005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (N->getOpcode() == ISD::SRL) {
131105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    if (Amt > VTBits) {
131205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Lo = DAG.getConstant(0, NVT);
131305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Hi = DAG.getConstant(0, NVT);
131405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    } else if (Amt > NVTBits) {
1315e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Lo = DAG.getNode(ISD::SRL, DL,
1316786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                       NVT, InH, DAG.getConstant(Amt-NVTBits,ShTy));
131705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Hi = DAG.getConstant(0, NVT);
131805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    } else if (Amt == NVTBits) {
131905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Lo = InH;
132005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Hi = DAG.getConstant(0, NVT);
132105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    } else {
1322e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Lo = DAG.getNode(ISD::OR, DL, NVT,
1323e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner                       DAG.getNode(ISD::SRL, DL, NVT, InL,
132405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                   DAG.getConstant(Amt, ShTy)),
1325e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner                       DAG.getNode(ISD::SHL, DL, NVT, InH,
132605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                   DAG.getConstant(NVTBits-Amt, ShTy)));
1327e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner      Hi = DAG.getNode(ISD::SRL, DL, NVT, InH, DAG.getConstant(Amt, ShTy));
132805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    }
132905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    return;
1330cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
1331d885dbdf9eb7a51ebb9a15a85921f27d8219997cDuncan Sands
133205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(N->getOpcode() == ISD::SRA && "Unknown shift!");
133305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (Amt > VTBits) {
1334e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner    Hi = Lo = DAG.getNode(ISD::SRA, DL, NVT, InH,
133505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                          DAG.getConstant(NVTBits-1, ShTy));
133605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else if (Amt > NVTBits) {
1337e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner    Lo = DAG.getNode(ISD::SRA, DL, NVT, InH,
133805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                     DAG.getConstant(Amt-NVTBits, ShTy));
1339e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner    Hi = DAG.getNode(ISD::SRA, DL, NVT, InH,
134005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                     DAG.getConstant(NVTBits-1, ShTy));
134105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else if (Amt == NVTBits) {
134205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    Lo = InH;
1343e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner    Hi = DAG.getNode(ISD::SRA, DL, NVT, InH,
134405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                     DAG.getConstant(NVTBits-1, ShTy));
1345d885dbdf9eb7a51ebb9a15a85921f27d8219997cDuncan Sands  } else {
1346e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner    Lo = DAG.getNode(ISD::OR, DL, NVT,
1347e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner                     DAG.getNode(ISD::SRL, DL, NVT, InL,
134805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                 DAG.getConstant(Amt, ShTy)),
1349e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner                     DAG.getNode(ISD::SHL, DL, NVT, InH,
135005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                 DAG.getConstant(NVTBits-Amt, ShTy)));
1351e075118489baf15a7cea2e7f155b4799b93d6d02Chris Lattner    Hi = DAG.getNode(ISD::SRA, DL, NVT, InH, DAG.getConstant(Amt, ShTy));
1352d885dbdf9eb7a51ebb9a15a85921f27d8219997cDuncan Sands  }
1353d885dbdf9eb7a51ebb9a15a85921f27d8219997cDuncan Sands}
1354d885dbdf9eb7a51ebb9a15a85921f27d8219997cDuncan Sands
135505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// ExpandShiftWithKnownAmountBit - Try to determine whether we can simplify
135605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// this shift based on knowledge of the high bit of the shift amount.  If we
135705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// can tell this, we know that it is >= 32 or < 32, without knowing the actual
135805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// shift amount.
135905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsbool DAGTypeLegalizer::
1360475871a144eb604ddaf37503397ba0941442e5fbDan GohmanExpandShiftWithKnownAmountBit(SDNode *N, SDValue &Lo, SDValue &Hi) {
1361475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Amt = N->getOperand(1);
136223b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1363e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT ShTy = Amt.getValueType();
13645b870aff81da0c07413f0241087bb3722954b83dDan Gohman  unsigned ShBits = ShTy.getScalarType().getSizeInBits();
13655b870aff81da0c07413f0241087bb3722954b83dDan Gohman  unsigned NVTBits = NVT.getScalarType().getSizeInBits();
136605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(isPowerOf2_32(NVTBits) &&
136705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands         "Expanded integer type size not a power of two!");
1368ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1369cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
137005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  APInt HighBitMask = APInt::getHighBitsSet(ShBits, ShBits - Log2_32(NVTBits));
137105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  APInt KnownZero, KnownOne;
137226c8dcc692fb2addd475446cfff24d6a4e958bcaRafael Espindola  DAG.ComputeMaskedBits(N->getOperand(1), KnownZero, KnownOne);
1373cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
137405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If we don't know anything about the high bits, exit.
137505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (((KnownZero|KnownOne) & HighBitMask) == 0)
137605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    return false;
1377cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
137805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Get the incoming operand to be shifted.
1379475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue InL, InH;
138005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), InL, InH);
1381be1ad4de2900451626c8d4ace07b9ea16099ea1dDuncan Sands
138205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If we know that any of the high bits of the shift amount are one, then we
138305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // can do this as a couple of simple shifts.
138405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (KnownOne.intersects(HighBitMask)) {
138505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Mask out the high bit, which we know is set.
1386786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Amt = DAG.getNode(ISD::AND, dl, ShTy, Amt,
138705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                      DAG.getConstant(~HighBitMask, ShTy));
138805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
138905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    switch (N->getOpcode()) {
1390c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    default: llvm_unreachable("Unknown shift");
139105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    case ISD::SHL:
139205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Lo = DAG.getConstant(0, NVT);              // Low part is zero.
1393786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::SHL, dl, NVT, InL, Amt); // High part from Lo part.
139405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      return true;
139505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    case ISD::SRL:
139605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Hi = DAG.getConstant(0, NVT);              // Hi part is zero.
1397786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Lo = DAG.getNode(ISD::SRL, dl, NVT, InH, Amt); // Lo part from Hi part.
139805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      return true;
139905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    case ISD::SRA:
1400786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::SRA, dl, NVT, InH,       // Sign extend high part.
140105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                       DAG.getConstant(NVTBits-1, ShTy));
1402786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Lo = DAG.getNode(ISD::SRA, dl, NVT, InH, Amt); // Lo part from Hi part.
140305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      return true;
140405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    }
140505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
140605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
140705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If we know that all of the high bits of the shift amount are zero, then we
140805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // can do this as a couple of simple shifts.
140905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if ((KnownZero & HighBitMask) == HighBitMask) {
14103bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    // Calculate 31-x. 31 is used instead of 32 to avoid creating an undefined
14113bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    // shift if x is zero.  We can use XOR here because x is known to be smaller
1412a3b2121ccf4f048640b4d79689b0e4a3906143f2Benjamin Kramer    // than 32.
14133bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    SDValue Amt2 = DAG.getNode(ISD::XOR, dl, ShTy, Amt,
14143bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer                               DAG.getConstant(NVTBits-1, ShTy));
14153bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer
141605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    unsigned Op1, Op2;
141705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    switch (N->getOpcode()) {
1418c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    default: llvm_unreachable("Unknown shift");
141905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    case ISD::SHL:  Op1 = ISD::SHL; Op2 = ISD::SRL; break;
142005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    case ISD::SRL:
142105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    case ISD::SRA:  Op1 = ISD::SRL; Op2 = ISD::SHL; break;
142205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    }
142305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
14243bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    // When shifting right the arithmetic for Lo and Hi is swapped.
14253bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    if (N->getOpcode() != ISD::SHL)
14263bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer      std::swap(InL, InH);
14273bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer
14283bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    // Use a little trick to get the bits that move from Lo to Hi. First
1429f1820b54e4d08ed78ca76b80b8bebb91cdc798a5Benjamin Kramer    // shift by one bit.
1430f1820b54e4d08ed78ca76b80b8bebb91cdc798a5Benjamin Kramer    SDValue Sh1 = DAG.getNode(Op2, dl, NVT, InL, DAG.getConstant(1, ShTy));
1431f1820b54e4d08ed78ca76b80b8bebb91cdc798a5Benjamin Kramer    // Then compute the remaining shift with amount-1.
1432f1820b54e4d08ed78ca76b80b8bebb91cdc798a5Benjamin Kramer    SDValue Sh2 = DAG.getNode(Op2, dl, NVT, Sh1, Amt2);
14333bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer
14343bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    Lo = DAG.getNode(N->getOpcode(), dl, NVT, InL, Amt);
14353bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    Hi = DAG.getNode(ISD::OR, dl, NVT, DAG.getNode(Op1, dl, NVT, InH, Amt),Sh2);
14363bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer
14373bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer    if (N->getOpcode() != ISD::SHL)
14383bf15ced2b91661ac314911c1f28332da0e1c37cBenjamin Kramer      std::swap(Hi, Lo);
143905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    return true;
144005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
144105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
144205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  return false;
144305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
144405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
14456fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng/// ExpandShiftWithUnknownAmountBit - Fully general expansion of integer shift
14466fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng/// of any size.
14476fb2168aaed06e4685d064b6f63dc4c668b42728Evan Chengbool DAGTypeLegalizer::
14486fb2168aaed06e4685d064b6f63dc4c668b42728Evan ChengExpandShiftWithUnknownAmountBit(SDNode *N, SDValue &Lo, SDValue &Hi) {
14496fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  SDValue Amt = N->getOperand(1);
145023b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1451e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT ShTy = Amt.getValueType();
14526fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  unsigned NVTBits = NVT.getSizeInBits();
14536fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  assert(isPowerOf2_32(NVTBits) &&
14546fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng         "Expanded integer type size not a power of two!");
1455ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
14566fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng
14576fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  // Get the incoming operand to be shifted.
14586fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  SDValue InL, InH;
14596fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  GetExpandedInteger(N->getOperand(0), InL, InH);
14606fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng
14616fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  SDValue NVBitsNode = DAG.getConstant(NVTBits, ShTy);
14629993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands  SDValue AmtExcess = DAG.getNode(ISD::SUB, dl, ShTy, Amt, NVBitsNode);
14639993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands  SDValue AmtLack = DAG.getNode(ISD::SUB, dl, ShTy, NVBitsNode, Amt);
1464225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  SDValue isShort = DAG.getSetCC(dl, getSetCCResultType(ShTy),
14659993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands                                 Amt, NVBitsNode, ISD::SETULT);
14666fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng
14679993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands  SDValue LoS, HiS, LoL, HiL;
14686fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  switch (N->getOpcode()) {
1469c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  default: llvm_unreachable("Unknown shift");
14706fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  case ISD::SHL:
14719993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    // Short: ShAmt < NVTBits
14729993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    LoS = DAG.getNode(ISD::SHL, dl, NVT, InL, Amt);
14739993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    HiS = DAG.getNode(ISD::OR, dl, NVT,
14746fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng                      DAG.getNode(ISD::SHL, dl, NVT, InH, Amt),
147536236b76a45be2a50315d1926c49bd3c63786b49Duncan Sands    // FIXME: If Amt is zero, the following shift generates an undefined result
147636236b76a45be2a50315d1926c49bd3c63786b49Duncan Sands    // on some architectures.
14779993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands                      DAG.getNode(ISD::SRL, dl, NVT, InL, AmtLack));
14789993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands
14799993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    // Long: ShAmt >= NVTBits
14809993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    LoL = DAG.getConstant(0, NVT);                        // Lo part is zero.
14819993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    HiL = DAG.getNode(ISD::SHL, dl, NVT, InL, AmtExcess); // Hi from Lo part.
14826fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng
1483b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Lo = DAG.getSelect(dl, NVT, isShort, LoS, LoL);
1484b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Hi = DAG.getSelect(dl, NVT, isShort, HiS, HiL);
14856fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng    return true;
14866fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  case ISD::SRL:
14879993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    // Short: ShAmt < NVTBits
14889993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    HiS = DAG.getNode(ISD::SRL, dl, NVT, InH, Amt);
14899993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    LoS = DAG.getNode(ISD::OR, dl, NVT,
14909993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands                      DAG.getNode(ISD::SRL, dl, NVT, InL, Amt),
149136236b76a45be2a50315d1926c49bd3c63786b49Duncan Sands    // FIXME: If Amt is zero, the following shift generates an undefined result
149236236b76a45be2a50315d1926c49bd3c63786b49Duncan Sands    // on some architectures.
14939993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands                      DAG.getNode(ISD::SHL, dl, NVT, InH, AmtLack));
14949993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands
14959993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    // Long: ShAmt >= NVTBits
14969993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    HiL = DAG.getConstant(0, NVT);                        // Hi part is zero.
14979993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    LoL = DAG.getNode(ISD::SRL, dl, NVT, InH, AmtExcess); // Lo from Hi part.
14989993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands
1499b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Lo = DAG.getSelect(dl, NVT, isShort, LoS, LoL);
1500b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Hi = DAG.getSelect(dl, NVT, isShort, HiS, HiL);
15016fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng    return true;
15026fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  case ISD::SRA:
15039993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    // Short: ShAmt < NVTBits
15049993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    HiS = DAG.getNode(ISD::SRA, dl, NVT, InH, Amt);
15059993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    LoS = DAG.getNode(ISD::OR, dl, NVT,
15066fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng                      DAG.getNode(ISD::SRL, dl, NVT, InL, Amt),
150736236b76a45be2a50315d1926c49bd3c63786b49Duncan Sands    // FIXME: If Amt is zero, the following shift generates an undefined result
150836236b76a45be2a50315d1926c49bd3c63786b49Duncan Sands    // on some architectures.
15099993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands                      DAG.getNode(ISD::SHL, dl, NVT, InH, AmtLack));
15109993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands
15119993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    // Long: ShAmt >= NVTBits
15129993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    HiL = DAG.getNode(ISD::SRA, dl, NVT, InH,             // Sign of Hi part.
15139993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands                      DAG.getConstant(NVTBits-1, ShTy));
15149993b88f06fd54c0be31d35f0970ada70a4c0439Duncan Sands    LoL = DAG.getNode(ISD::SRA, dl, NVT, InH, AmtExcess); // Lo from Hi part.
15156fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng
1516b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Lo = DAG.getSelect(dl, NVT, isShort, LoS, LoL);
1517b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Hi = DAG.getSelect(dl, NVT, isShort, HiS, HiL);
15186fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng    return true;
15196fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  }
15206fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng}
15216fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng
152205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_ADDSUB(SDNode *N,
1523475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                           SDValue &Lo, SDValue &Hi) {
1524ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
152505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Expand the subcomponents.
1526475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHSL, LHSH, RHSL, RHSH;
152705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
152805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
152929a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands
1530e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = LHSL.getValueType();
1531475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LoOps[2] = { LHSL, RHSL };
1532475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue HiOps[3] = { LHSH, RHSH };
153305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
153429a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands  // Do not generate ADDC/ADDE or SUBC/SUBE if the target does not support
153529a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands  // them.  TODO: Teach operation legalization how to expand unsupported
153629a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands  // ADDC/ADDE/SUBC/SUBE.  The problem is that these operations generate
1537f1b4eafbfec976f939ec0ea3e8acf91cef5363e3Chris Lattner  // a carry of type MVT::Glue, but there doesn't seem to be any way to
153829a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands  // generate a value of this type in the expanded code sequence.
153929a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands  bool hasCarry =
1540f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman    TLI.isOperationLegalOrCustom(N->getOpcode() == ISD::ADD ?
1541f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman                                   ISD::ADDC : ISD::SUBC,
1542bc7a902713c4e3f13a93c383e647d2a18712f447Dan Gohman                                 TLI.getTypeToExpandTo(*DAG.getContext(), NVT));
154329a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands
154429a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands  if (hasCarry) {
1545f1b4eafbfec976f939ec0ea3e8acf91cef5363e3Chris Lattner    SDVTList VTList = DAG.getVTList(NVT, MVT::Glue);
154629a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands    if (N->getOpcode() == ISD::ADD) {
1547786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Lo = DAG.getNode(ISD::ADDC, dl, VTList, LoOps, 2);
154829a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands      HiOps[2] = Lo.getValue(1);
1549786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::ADDE, dl, VTList, HiOps, 3);
155029a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands    } else {
1551786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Lo = DAG.getNode(ISD::SUBC, dl, VTList, LoOps, 2);
155229a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands      HiOps[2] = Lo.getValue(1);
1553786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::SUBE, dl, VTList, HiOps, 3);
155429a2822f287275a0d4df49f98104409d8f97c5dfDuncan Sands    }
1555c6d160bfa22fcb06c80c4c6cfc10ddbe7d8d28e4Owen Anderson    return;
15565078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner  }
1557c6d160bfa22fcb06c80c4c6cfc10ddbe7d8d28e4Owen Anderson
15585078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner  if (N->getOpcode() == ISD::ADD) {
15595078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    Lo = DAG.getNode(ISD::ADD, dl, NVT, LoOps, 2);
15605078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    Hi = DAG.getNode(ISD::ADD, dl, NVT, HiOps, 2);
1561225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault    SDValue Cmp1 = DAG.getSetCC(dl, getSetCCResultType(NVT), Lo, LoOps[0],
15625078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner                                ISD::SETULT);
1563b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    SDValue Carry1 = DAG.getSelect(dl, NVT, Cmp1,
1564b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                   DAG.getConstant(1, NVT),
1565b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                   DAG.getConstant(0, NVT));
1566225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault    SDValue Cmp2 = DAG.getSetCC(dl, getSetCCResultType(NVT), Lo, LoOps[1],
15675078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner                                ISD::SETULT);
1568b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    SDValue Carry2 = DAG.getSelect(dl, NVT, Cmp2,
1569b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                   DAG.getConstant(1, NVT), Carry1);
15705078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    Hi = DAG.getNode(ISD::ADD, dl, NVT, Hi, Carry2);
157105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
15725078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    Lo = DAG.getNode(ISD::SUB, dl, NVT, LoOps, 2);
15735078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    Hi = DAG.getNode(ISD::SUB, dl, NVT, HiOps, 2);
15745078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    SDValue Cmp =
1575225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault      DAG.getSetCC(dl, getSetCCResultType(LoOps[0].getValueType()),
15765078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner                   LoOps[0], LoOps[1], ISD::SETULT);
1577b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    SDValue Borrow = DAG.getSelect(dl, NVT, Cmp,
1578b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                   DAG.getConstant(1, NVT),
1579b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                   DAG.getConstant(0, NVT));
15805078293cc28dd03236384fa0a3b6c8347e0701fbChris Lattner    Hi = DAG.getNode(ISD::SUB, dl, NVT, Hi, Borrow);
158105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
158205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
158305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
158405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_ADDSUBC(SDNode *N,
1585475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                            SDValue &Lo, SDValue &Hi) {
158605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Expand the subcomponents.
1587475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHSL, LHSH, RHSL, RHSH;
1588ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
158905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
159005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
1591f1b4eafbfec976f939ec0ea3e8acf91cef5363e3Chris Lattner  SDVTList VTList = DAG.getVTList(LHSL.getValueType(), MVT::Glue);
1592475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LoOps[2] = { LHSL, RHSL };
1593475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue HiOps[3] = { LHSH, RHSH };
159405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
159505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (N->getOpcode() == ISD::ADDC) {
1596786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::ADDC, dl, VTList, LoOps, 2);
159705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    HiOps[2] = Lo.getValue(1);
1598786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::ADDE, dl, VTList, HiOps, 3);
159905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
1600786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::SUBC, dl, VTList, LoOps, 2);
160105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    HiOps[2] = Lo.getValue(1);
1602786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::SUBE, dl, VTList, HiOps, 3);
160305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
160405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1605874ae251c317788391f9c3f113957802d390a063Dale Johannesen  // Legalized the flag result - switch anything that used the old flag to
1606874ae251c317788391f9c3f113957802d390a063Dale Johannesen  // use the new one.
1607475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  ReplaceValueWith(SDValue(N, 1), Hi.getValue(1));
160805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
160905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
161005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_ADDSUBE(SDNode *N,
1611475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                            SDValue &Lo, SDValue &Hi) {
161205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Expand the subcomponents.
1613475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHSL, LHSH, RHSL, RHSH;
1614ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
161505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
161605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(1), RHSL, RHSH);
1617f1b4eafbfec976f939ec0ea3e8acf91cef5363e3Chris Lattner  SDVTList VTList = DAG.getVTList(LHSL.getValueType(), MVT::Glue);
1618475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LoOps[3] = { LHSL, RHSL, N->getOperand(2) };
1619475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue HiOps[3] = { LHSH, RHSH };
162005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1621786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Lo = DAG.getNode(N->getOpcode(), dl, VTList, LoOps, 3);
162205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  HiOps[2] = Lo.getValue(1);
1623786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Hi = DAG.getNode(N->getOpcode(), dl, VTList, HiOps, 3);
162405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1625874ae251c317788391f9c3f113957802d390a063Dale Johannesen  // Legalized the flag result - switch anything that used the old flag to
1626874ae251c317788391f9c3f113957802d390a063Dale Johannesen  // use the new one.
1627475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  ReplaceValueWith(SDValue(N, 1), Hi.getValue(1));
162805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
1629fcd75e5efb482f35cfc22fd4b64e047930130fd6Eli Friedman
16304c19e12d28749c717d3b384962c9ec92796af1c9Duncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_MERGE_VALUES(SDNode *N, unsigned ResNo,
1631fcd75e5efb482f35cfc22fd4b64e047930130fd6Eli Friedman                                                 SDValue &Lo, SDValue &Hi) {
16324c19e12d28749c717d3b384962c9ec92796af1c9Duncan Sands  SDValue Res = DisintegrateMERGE_VALUES(N, ResNo);
163362bb16cfd10dd271eab6c31d982bca4d79138602Eli Friedman  SplitInteger(Res, Lo, Hi);
163462bb16cfd10dd271eab6c31d982bca4d79138602Eli Friedman}
163505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
163605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_ANY_EXTEND(SDNode *N,
1637475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                               SDValue &Lo, SDValue &Hi) {
163823b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
1639ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1640475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
164105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (Op.getValueType().bitsLE(NVT)) {
164205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // The low part is any extension of the input (which degenerates to a copy).
1643786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::ANY_EXTEND, dl, NVT, Op);
1644e8d7230f480654cdb8ff1c3d0a38e1e9ab0bd55fDale Johannesen    Hi = DAG.getUNDEF(NVT);   // The high part is undefined.
164505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
164605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // For example, extension of an i48 to an i64.  The operand type necessarily
164705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // promotes to the result type, so will end up being expanded too.
164896e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem    assert(getTypeAction(Op.getValueType()) ==
164996e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem           TargetLowering::TypePromoteInteger &&
165005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Only know how to promote this result!");
1651475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Res = GetPromotedInteger(Op);
165205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    assert(Res.getValueType() == N->getValueType(0) &&
165305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Operand over promoted?");
165405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Split the promoted operand.  This will simplify when it is expanded.
165505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    SplitInteger(Res, Lo, Hi);
165605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
165705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
165805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
165995db39a9de48f69f4d764335b492b83a698c7854Duncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_AssertSext(SDNode *N,
1660475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                               SDValue &Lo, SDValue &Hi) {
1661ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
166295db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  GetExpandedInteger(N->getOperand(0), Lo, Hi);
1663e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Lo.getValueType();
1664e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT EVT = cast<VTSDNode>(N->getOperand(1))->getVT();
166595db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  unsigned NVTBits = NVT.getSizeInBits();
166695db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  unsigned EVTBits = EVT.getSizeInBits();
166795db39a9de48f69f4d764335b492b83a698c7854Duncan Sands
166895db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  if (NVTBits < EVTBits) {
1669786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::AssertSext, dl, NVT, Hi,
16704ff28527bb8e5ed4ae4b65f0fa6967eb79a05d4cEvan Cheng                     DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
16714ff28527bb8e5ed4ae4b65f0fa6967eb79a05d4cEvan Cheng                                                        EVTBits - NVTBits)));
167295db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  } else {
1673786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::AssertSext, dl, NVT, Lo, DAG.getValueType(EVT));
167495db39a9de48f69f4d764335b492b83a698c7854Duncan Sands    // The high part replicates the sign bit of Lo, make it explicit.
1675786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
167692abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                     DAG.getConstant(NVTBits-1, TLI.getPointerTy()));
167795db39a9de48f69f4d764335b492b83a698c7854Duncan Sands  }
167895db39a9de48f69f4d764335b492b83a698c7854Duncan Sands}
167995db39a9de48f69f4d764335b492b83a698c7854Duncan Sands
168005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_AssertZext(SDNode *N,
1681475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                               SDValue &Lo, SDValue &Hi) {
1682ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
168305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), Lo, Hi);
1684e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Lo.getValueType();
1685e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT EVT = cast<VTSDNode>(N->getOperand(1))->getVT();
168605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  unsigned NVTBits = NVT.getSizeInBits();
168705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  unsigned EVTBits = EVT.getSizeInBits();
168805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
168905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (NVTBits < EVTBits) {
1690786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::AssertZext, dl, NVT, Hi,
1691285fb1cc4a7ea924b4d94e9c2cb890125d56a7e0Evan Cheng                     DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
1692285fb1cc4a7ea924b4d94e9c2cb890125d56a7e0Evan Cheng                                                        EVTBits - NVTBits)));
169305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
1694786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::AssertZext, dl, NVT, Lo, DAG.getValueType(EVT));
169505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // The high part must be zero, make it explicit.
169605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    Hi = DAG.getConstant(0, NVT);
169705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
169805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
169905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
170005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_BSWAP(SDNode *N,
1701475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                          SDValue &Lo, SDValue &Hi) {
1702ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
170305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), Hi, Lo);  // Note swapped operands.
1704786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Lo = DAG.getNode(ISD::BSWAP, dl, Lo.getValueType(), Lo);
1705786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Hi = DAG.getNode(ISD::BSWAP, dl, Hi.getValueType(), Hi);
170605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
170705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
170805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_Constant(SDNode *N,
1709475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                             SDValue &Lo, SDValue &Hi) {
171023b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
171105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  unsigned NBitWidth = NVT.getSizeInBits();
171205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  const APInt &Cst = cast<ConstantSDNode>(N)->getAPIntValue();
171340f8f6264d5af2c38e797e0dc59827cd231e8ff7Jay Foad  Lo = DAG.getConstant(Cst.trunc(NBitWidth), NVT);
171405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  Hi = DAG.getConstant(Cst.lshr(NBitWidth).trunc(NBitWidth), NVT);
171505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
171605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
171705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_CTLZ(SDNode *N,
1718475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
1719ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
172005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // ctlz (HiLo) -> Hi != 0 ? ctlz(Hi) : (ctlz(Lo)+32)
172105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), Lo, Hi);
1722e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Lo.getValueType();
172305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1724225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  SDValue HiNotZero = DAG.getSetCC(dl, getSetCCResultType(NVT), Hi,
1725ef5b199905cee0b78eb30cd44836e5b6ca5cbd09Duncan Sands                                   DAG.getConstant(0, NVT), ISD::SETNE);
172605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
172763974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  SDValue LoLZ = DAG.getNode(N->getOpcode(), dl, NVT, Lo);
172863974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  SDValue HiLZ = DAG.getNode(ISD::CTLZ_ZERO_UNDEF, dl, NVT, Hi);
172905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1730b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault  Lo = DAG.getSelect(dl, NVT, HiNotZero, HiLZ,
1731b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                     DAG.getNode(ISD::ADD, dl, NVT, LoLZ,
1732b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                 DAG.getConstant(NVT.getSizeInBits(), NVT)));
173305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  Hi = DAG.getConstant(0, NVT);
173405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
173505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
173605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_CTPOP(SDNode *N,
1737475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                          SDValue &Lo, SDValue &Hi) {
1738ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
173905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // ctpop(HiLo) -> ctpop(Hi)+ctpop(Lo)
174005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), Lo, Hi);
1741e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Lo.getValueType();
1742b300d2aa3ef08b5074449e2c05804717f488f4e4Dale Johannesen  Lo = DAG.getNode(ISD::ADD, dl, NVT, DAG.getNode(ISD::CTPOP, dl, NVT, Lo),
1743786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                   DAG.getNode(ISD::CTPOP, dl, NVT, Hi));
174405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  Hi = DAG.getConstant(0, NVT);
174505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
174605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
174705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_CTTZ(SDNode *N,
1748475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
1749ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
175005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // cttz (HiLo) -> Lo != 0 ? cttz(Lo) : (cttz(Hi)+32)
175105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), Lo, Hi);
1752e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT NVT = Lo.getValueType();
175305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1754225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  SDValue LoNotZero = DAG.getSetCC(dl, getSetCCResultType(NVT), Lo,
1755ef5b199905cee0b78eb30cd44836e5b6ca5cbd09Duncan Sands                                   DAG.getConstant(0, NVT), ISD::SETNE);
175605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
175763974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  SDValue LoLZ = DAG.getNode(ISD::CTTZ_ZERO_UNDEF, dl, NVT, Lo);
175863974b2144c87c962effdc0508c27643c8ad98b6Chandler Carruth  SDValue HiLZ = DAG.getNode(N->getOpcode(), dl, NVT, Hi);
175905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1760b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault  Lo = DAG.getSelect(dl, NVT, LoNotZero, LoLZ,
1761b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                     DAG.getNode(ISD::ADD, dl, NVT, HiLZ,
1762b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                 DAG.getConstant(NVT.getSizeInBits(), NVT)));
176305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  Hi = DAG.getConstant(0, NVT);
176405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
176505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
1766475871a144eb604ddaf37503397ba0941442e5fbDan Gohmanvoid DAGTypeLegalizer::ExpandIntRes_FP_TO_SINT(SDNode *N, SDValue &Lo,
1767475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                               SDValue &Hi) {
1768ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1769e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
1770475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
1771b2ff885aaed8f9b033b16ca78d645650efc32433Duncan Sands  RTLIB::Libcall LC = RTLIB::getFPTOSINT(Op.getValueType(), VT);
1772be1ad4de2900451626c8d4ace07b9ea16099ea1dDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected fp-to-sint conversion!");
17732c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, &Op, 1, true/*irrelevant*/, dl),
17742c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover               Lo, Hi);
1775ddc016cc8592fe5c9379feb42a1fb4fb63164a91Duncan Sands}
1776ddc016cc8592fe5c9379feb42a1fb4fb63164a91Duncan Sands
1777475871a144eb604ddaf37503397ba0941442e5fbDan Gohmanvoid DAGTypeLegalizer::ExpandIntRes_FP_TO_UINT(SDNode *N, SDValue &Lo,
1778475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                               SDValue &Hi) {
1779ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1780e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
1781475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
1782b2ff885aaed8f9b033b16ca78d645650efc32433Duncan Sands  RTLIB::Libcall LC = RTLIB::getFPTOUINT(Op.getValueType(), VT);
1783be1ad4de2900451626c8d4ace07b9ea16099ea1dDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unexpected fp-to-uint conversion!");
17842c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, &Op, 1, false/*irrelevant*/, dl),
17852c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover               Lo, Hi);
1786ddc016cc8592fe5c9379feb42a1fb4fb63164a91Duncan Sands}
1787ddc016cc8592fe5c9379feb42a1fb4fb63164a91Duncan Sands
178869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_LOAD(LoadSDNode *N,
1789475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
1790ab09b7e8f34075c1759127a113f41bdf921f4034Duncan Sands  if (ISD::isNormalLoad(N)) {
1791ab09b7e8f34075c1759127a113f41bdf921f4034Duncan Sands    ExpandRes_NormalLoad(N, Lo, Hi);
179278cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands    return;
179378cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  }
179478cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands
179578cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  assert(ISD::isUNINDEXEDLoad(N) && "Indexed load during type legalization!");
179678cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands
1797e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
179823b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
1799475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ch  = N->getChain();
1800475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ptr = N->getBasePtr();
1801cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  ISD::LoadExtType ExtType = N->getExtensionType();
1802cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  unsigned Alignment = N->getAlignment();
1803cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  bool isVolatile = N->isVolatile();
18041e559443a17d1b335f697551c6263ba60d5dd827David Greene  bool isNonTemporal = N->isNonTemporal();
1805d752e0f7e64585839cb3a458ef52456eaebbea3cPete Cooper  bool isInvariant = N->isInvariant();
1806ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1807cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
180878cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  assert(NVT.isByteSized() && "Expanded type not byte sized!");
1809cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
181078cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  if (N->getMemoryVT().bitsLE(NVT)) {
18118a55ce4a392f07ac1f3c183100ac591b7ad7c693Dan Gohman    EVT MemVT = N->getMemoryVT();
1812cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1813a901129169194881a78b7fd8953e09f55b846d10Stuart Hastings    Lo = DAG.getExtLoad(ExtType, dl, NVT, Ch, Ptr, N->getPointerInfo(),
18141e559443a17d1b335f697551c6263ba60d5dd827David Greene                        MemVT, isVolatile, isNonTemporal, Alignment);
1815cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1816cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Remember the chain.
1817cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    Ch = Lo.getValue(1);
1818cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1819cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    if (ExtType == ISD::SEXTLOAD) {
1820cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // The high part is obtained by SRA'ing all but one of the bits of the
1821cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // lo part.
182283ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands      unsigned LoSize = Lo.getValueType().getSizeInBits();
1823786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
182492abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                       DAG.getConstant(LoSize-1, TLI.getPointerTy()));
1825cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    } else if (ExtType == ISD::ZEXTLOAD) {
1826cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // The high part is just a zero.
1827cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      Hi = DAG.getConstant(0, NVT);
1828cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    } else {
1829cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      assert(ExtType == ISD::EXTLOAD && "Unknown extload!");
1830cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // The high part is undefined.
1831e8d7230f480654cdb8ff1c3d0a38e1e9ab0bd55fDale Johannesen      Hi = DAG.getUNDEF(NVT);
1832cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    }
1833cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  } else if (TLI.isLittleEndian()) {
1834cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Little-endian - low bits are at low addresses.
1835ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    Lo = DAG.getLoad(NVT, dl, Ch, Ptr, N->getPointerInfo(),
1836d752e0f7e64585839cb3a458ef52456eaebbea3cPete Cooper                     isVolatile, isNonTemporal, isInvariant, Alignment);
1837cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1838cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    unsigned ExcessBits =
183983ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands      N->getMemoryVT().getSizeInBits() - NVT.getSizeInBits();
184023b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson    EVT NEVT = EVT::getIntegerVT(*DAG.getContext(), ExcessBits);
1841cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1842cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Increment the pointer to the other half.
184383ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands    unsigned IncrementSize = NVT.getSizeInBits()/8;
1844786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Ptr = DAG.getNode(ISD::ADD, dl, Ptr.getValueType(), Ptr,
18450bd4893a0726889b942405262e53d06cf3fe3be8Chris Lattner                      DAG.getIntPtrConstant(IncrementSize));
1846a901129169194881a78b7fd8953e09f55b846d10Stuart Hastings    Hi = DAG.getExtLoad(ExtType, dl, NVT, Ch, Ptr,
1847ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                        N->getPointerInfo().getWithOffset(IncrementSize), NEVT,
18481e559443a17d1b335f697551c6263ba60d5dd827David Greene                        isVolatile, isNonTemporal,
18491e559443a17d1b335f697551c6263ba60d5dd827David Greene                        MinAlign(Alignment, IncrementSize));
1850cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1851cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Build a factor node to remember that this load is independent of the
1852cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // other one.
1853825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    Ch = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo.getValue(1),
1854cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner                     Hi.getValue(1));
1855cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  } else {
1856cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Big-endian - high bits are at low addresses.  Favor aligned loads at
1857cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // the cost of some bit-fiddling.
18588a55ce4a392f07ac1f3c183100ac591b7ad7c693Dan Gohman    EVT MemVT = N->getMemoryVT();
18594e918b2c8ca81edd63f6708e08835b2c14648615Dan Gohman    unsigned EBytes = MemVT.getStoreSize();
186083ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands    unsigned IncrementSize = NVT.getSizeInBits()/8;
1861cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    unsigned ExcessBits = (EBytes - IncrementSize)*8;
1862cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1863cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Load both the high bits and maybe some of the low bits.
1864a901129169194881a78b7fd8953e09f55b846d10Stuart Hastings    Hi = DAG.getExtLoad(ExtType, dl, NVT, Ch, Ptr, N->getPointerInfo(),
18658a55ce4a392f07ac1f3c183100ac591b7ad7c693Dan Gohman                        EVT::getIntegerVT(*DAG.getContext(),
18668a55ce4a392f07ac1f3c183100ac591b7ad7c693Dan Gohman                                          MemVT.getSizeInBits() - ExcessBits),
18671e559443a17d1b335f697551c6263ba60d5dd827David Greene                        isVolatile, isNonTemporal, Alignment);
1868cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1869cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Increment the pointer to the other half.
1870786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Ptr = DAG.getNode(ISD::ADD, dl, Ptr.getValueType(), Ptr,
18710bd4893a0726889b942405262e53d06cf3fe3be8Chris Lattner                      DAG.getIntPtrConstant(IncrementSize));
1872cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Load the rest of the low bits.
1873a901129169194881a78b7fd8953e09f55b846d10Stuart Hastings    Lo = DAG.getExtLoad(ISD::ZEXTLOAD, dl, NVT, Ch, Ptr,
1874ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                        N->getPointerInfo().getWithOffset(IncrementSize),
187523b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson                        EVT::getIntegerVT(*DAG.getContext(), ExcessBits),
18761e559443a17d1b335f697551c6263ba60d5dd827David Greene                        isVolatile, isNonTemporal,
18771e559443a17d1b335f697551c6263ba60d5dd827David Greene                        MinAlign(Alignment, IncrementSize));
1878cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1879cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Build a factor node to remember that this load is independent of the
1880cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // other one.
1881825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    Ch = DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo.getValue(1),
1882cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner                     Hi.getValue(1));
1883cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
188483ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands    if (ExcessBits < NVT.getSizeInBits()) {
1885cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // Transfer low bits from the bottom of Hi to the top of Lo.
1886786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Lo = DAG.getNode(ISD::OR, dl, NVT, Lo,
1887786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                       DAG.getNode(ISD::SHL, dl, NVT, Hi,
1888cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner                                   DAG.getConstant(ExcessBits,
188992abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                                                   TLI.getPointerTy())));
1890cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // Move high bits to the right position in Hi.
18917fb085871857134f8cbeb17499d4ab771ba8da42Duncan Sands      Hi = DAG.getNode(ExtType == ISD::SEXTLOAD ? ISD::SRA : ISD::SRL, dl,
1892786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                       NVT, Hi,
189383ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands                       DAG.getConstant(NVT.getSizeInBits() - ExcessBits,
189492abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                                       TLI.getPointerTy()));
1895cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    }
1896cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
1897cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
1898cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // Legalized the chain result - switch anything that used the old chain to
1899cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // use the new one.
1900475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  ReplaceValueWith(SDValue(N, 1), Ch);
1901cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
1902cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
190369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_Logical(SDNode *N,
1904475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                            SDValue &Lo, SDValue &Hi) {
1905ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
1906475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LL, LH, RL, RH;
190769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  GetExpandedInteger(N->getOperand(0), LL, LH);
190869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  GetExpandedInteger(N->getOperand(1), RL, RH);
1909786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Lo = DAG.getNode(N->getOpcode(), dl, LL.getValueType(), LL, RL);
1910786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Hi = DAG.getNode(N->getOpcode(), dl, LL.getValueType(), LH, RH);
1911cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
1912cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
191305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_MUL(SDNode *N,
1914475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                        SDValue &Lo, SDValue &Hi) {
1915e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
191623b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
1917ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
191869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
1919f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman  bool HasMULHS = TLI.isOperationLegalOrCustom(ISD::MULHS, NVT);
1920f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman  bool HasMULHU = TLI.isOperationLegalOrCustom(ISD::MULHU, NVT);
1921f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman  bool HasSMUL_LOHI = TLI.isOperationLegalOrCustom(ISD::SMUL_LOHI, NVT);
1922f560ffae1f1f6591859c7b70636a3eca6c03f083Dan Gohman  bool HasUMUL_LOHI = TLI.isOperationLegalOrCustom(ISD::UMUL_LOHI, NVT);
1923cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  if (HasMULHU || HasMULHS || HasUMUL_LOHI || HasSMUL_LOHI) {
1924475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue LL, LH, RL, RH;
192569b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    GetExpandedInteger(N->getOperand(0), LL, LH);
192669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    GetExpandedInteger(N->getOperand(1), RL, RH);
192783ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands    unsigned OuterBitSize = VT.getSizeInBits();
1928e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    unsigned InnerBitSize = NVT.getSizeInBits();
1929cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    unsigned LHSSB = DAG.ComputeNumSignBits(N->getOperand(0));
1930cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    unsigned RHSSB = DAG.ComputeNumSignBits(N->getOperand(1));
193169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
1932e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    APInt HighMask = APInt::getHighBitsSet(OuterBitSize, InnerBitSize);
1933e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    if (DAG.MaskedValueIsZero(N->getOperand(0), HighMask) &&
1934e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands        DAG.MaskedValueIsZero(N->getOperand(1), HighMask)) {
1935cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // The inputs are both zero-extended.
1936cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      if (HasUMUL_LOHI) {
1937cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        // We can emit a umul_lohi.
1938786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        Lo = DAG.getNode(ISD::UMUL_LOHI, dl, DAG.getVTList(NVT, NVT), LL, RL);
1939ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif        Hi = SDValue(Lo.getNode(), 1);
1940cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        return;
1941cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      }
1942cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      if (HasMULHU) {
1943cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        // We can emit a mulhu+mul.
1944786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        Lo = DAG.getNode(ISD::MUL, dl, NVT, LL, RL);
1945786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        Hi = DAG.getNode(ISD::MULHU, dl, NVT, LL, RL);
1946cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        return;
1947cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      }
1948cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    }
1949e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    if (LHSSB > InnerBitSize && RHSSB > InnerBitSize) {
1950cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // The input values are both sign-extended.
1951cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      if (HasSMUL_LOHI) {
1952cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        // We can emit a smul_lohi.
1953786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        Lo = DAG.getNode(ISD::SMUL_LOHI, dl, DAG.getVTList(NVT, NVT), LL, RL);
1954ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif        Hi = SDValue(Lo.getNode(), 1);
1955cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        return;
1956cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      }
1957cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      if (HasMULHS) {
1958cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        // We can emit a mulhs+mul.
1959786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        Lo = DAG.getNode(ISD::MUL, dl, NVT, LL, RL);
1960786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen        Hi = DAG.getNode(ISD::MULHS, dl, NVT, LL, RL);
1961cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        return;
1962cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      }
1963cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    }
1964cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    if (HasUMUL_LOHI) {
1965cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      // Lo,Hi = umul LHS, RHS.
1966786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      SDValue UMulLOHI = DAG.getNode(ISD::UMUL_LOHI, dl,
1967cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner                                       DAG.getVTList(NVT, NVT), LL, RL);
1968cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      Lo = UMulLOHI;
1969cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      Hi = UMulLOHI.getValue(1);
1970786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      RH = DAG.getNode(ISD::MUL, dl, NVT, LL, RH);
1971786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      LH = DAG.getNode(ISD::MUL, dl, NVT, LH, RL);
1972786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::ADD, dl, NVT, Hi, RH);
1973786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::ADD, dl, NVT, Hi, LH);
1974cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      return;
1975cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    }
1976e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    if (HasMULHU) {
1977786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Lo = DAG.getNode(ISD::MUL, dl, NVT, LL, RL);
1978786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::MULHU, dl, NVT, LL, RL);
1979786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      RH = DAG.getNode(ISD::MUL, dl, NVT, LL, RH);
1980786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      LH = DAG.getNode(ISD::MUL, dl, NVT, LH, RL);
1981786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::ADD, dl, NVT, Hi, RH);
1982786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen      Hi = DAG.getNode(ISD::ADD, dl, NVT, Hi, LH);
1983e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands      return;
1984e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    }
1985cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
198641edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands
1987cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // If nothing else, we can make a libcall.
19885ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
1989825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  if (VT == MVT::i16)
199015c94d08ab2be2e3d00de4edbfc7adde6545a7dbSanjiv Gupta    LC = RTLIB::MUL_I16;
1991825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i32)
19925ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands    LC = RTLIB::MUL_I32;
1993825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i64)
1994e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands    LC = RTLIB::MUL_I64;
1995825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i128)
19965ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands    LC = RTLIB::MUL_I128;
19975ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported MUL!");
1998e9c80f4d576bf1ff682958d447c1a60fa9348da3Duncan Sands
1999475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
20002c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, 2, true/*irrelevant*/, dl),
20012c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover               Lo, Hi);
200241edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands}
2003cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2004268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedmanvoid DAGTypeLegalizer::ExpandIntRes_SADDSUBO(SDNode *Node,
2005268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                                             SDValue &Lo, SDValue &Hi) {
2006268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue LHS = Node->getOperand(0);
2007268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue RHS = Node->getOperand(1);
2008ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(Node);
2009268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2010268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // Expand the result by simply replacing it with the equivalent
2011268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // non-overflow-checking operation.
2012268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue Sum = DAG.getNode(Node->getOpcode() == ISD::SADDO ?
2013268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                            ISD::ADD : ISD::SUB, dl, LHS.getValueType(),
2014268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                            LHS, RHS);
2015268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SplitInteger(Sum, Lo, Hi);
2016268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2017268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // Compute the overflow.
2018268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //
2019268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   LHSSign -> LHS >= 0
2020268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   RHSSign -> RHS >= 0
2021268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   SumSign -> Sum >= 0
2022268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //
2023268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   Add:
2024268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   Overflow -> (LHSSign == RHSSign) && (LHSSign != SumSign)
2025268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   Sub:
2026268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //   Overflow -> (LHSSign != RHSSign) && (LHSSign != SumSign)
2027268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  //
2028268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  EVT OType = Node->getValueType(1);
2029268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue Zero = DAG.getConstant(0, LHS.getValueType());
2030268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2031268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue LHSSign = DAG.getSetCC(dl, OType, LHS, Zero, ISD::SETGE);
2032268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue RHSSign = DAG.getSetCC(dl, OType, RHS, Zero, ISD::SETGE);
2033268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue SignsMatch = DAG.getSetCC(dl, OType, LHSSign, RHSSign,
2034268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                                    Node->getOpcode() == ISD::SADDO ?
2035268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                                    ISD::SETEQ : ISD::SETNE);
2036268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2037268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue SumSign = DAG.getSetCC(dl, OType, Sum, Zero, ISD::SETGE);
2038268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue SumSignNE = DAG.getSetCC(dl, OType, LHSSign, SumSign, ISD::SETNE);
2039268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2040268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue Cmp = DAG.getNode(ISD::AND, dl, OType, SignsMatch, SumSignNE);
2041268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2042268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // Use the calculated overflow everywhere.
2043268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  ReplaceValueWith(SDValue(Node, 1), Cmp);
2044268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman}
2045268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
204669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_SDIV(SDNode *N,
2047475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
2048e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
2049ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
20505ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands
20515ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
2052825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  if (VT == MVT::i16)
2053a43a7aefd753fe7d6005cbebc9619268db4ae139Sanjiv Gupta    LC = RTLIB::SDIV_I16;
2054825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i32)
20555ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands    LC = RTLIB::SDIV_I32;
2056825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i64)
20575ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands    LC = RTLIB::SDIV_I64;
2058825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i128)
20595ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands    LC = RTLIB::SDIV_I128;
20605ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported SDIV!");
20615ac319ac7125b009adddcc49294d2e040c4a91e5Duncan Sands
2062475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
20632c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, 2, true, dl), Lo, Hi);
2064ddc016cc8592fe5c9379feb42a1fb4fb63164a91Duncan Sands}
2065ddc016cc8592fe5c9379feb42a1fb4fb63164a91Duncan Sands
206669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_Shift(SDNode *N,
2067475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                          SDValue &Lo, SDValue &Hi) {
2068e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
2069ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
207069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
207169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  // If we can emit an efficient shift operation, do so now.  Check to see if
2072cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // the RHS is a constant.
2073cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  if (ConstantSDNode *CN = dyn_cast<ConstantSDNode>(N->getOperand(1)))
2074f5aeb1a8e4cf272c7348376d185ef8d8267653e0Dan Gohman    return ExpandShiftByConstant(N, CN->getZExtValue(), Lo, Hi);
2075cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2076cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // If we can determine that the high bit of the shift is zero or one, even if
2077cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // the low bits are variable, emit this shift in an optimized form.
2078cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  if (ExpandShiftWithKnownAmountBit(N, Lo, Hi))
2079cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    return;
208069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2081cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // If this target supports shift_PARTS, use it.  First, map to the _PARTS opc.
2082cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  unsigned PartsOpc;
208341edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  if (N->getOpcode() == ISD::SHL) {
2084cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    PartsOpc = ISD::SHL_PARTS;
208541edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  } else if (N->getOpcode() == ISD::SRL) {
2086cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    PartsOpc = ISD::SRL_PARTS;
208741edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  } else {
2088cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    assert(N->getOpcode() == ISD::SRA && "Unknown shift!");
2089cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    PartsOpc = ISD::SRA_PARTS;
2090cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
209169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2092cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // Next check to see if the target supports this SHL_PARTS operation or if it
2093cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // will custom expand it.
209423b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
2095cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  TargetLowering::LegalizeAction Action = TLI.getOperationAction(PartsOpc, NVT);
2096cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  if ((Action == TargetLowering::Legal && TLI.isTypeLegal(NVT)) ||
2097cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      Action == TargetLowering::Custom) {
2098cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Expand the subcomponents.
2099475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue LHSL, LHSH;
210069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    GetExpandedInteger(N->getOperand(0), LHSL, LHSH);
2101e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson    EVT VT = LHSL.getValueType();
2102914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer
2103914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer    // If the shift amount operand is coming from a vector legalization it may
21040fef46f50e116e9aa0811ba8eb605d82ab64faedBenjamin Kramer    // have an illegal type.  Fix that first by casting the operand, otherwise
21050fef46f50e116e9aa0811ba8eb605d82ab64faedBenjamin Kramer    // the new SHL_PARTS operation would need further legalization.
2106914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer    SDValue ShiftOp = N->getOperand(1);
2107a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao    EVT ShiftTy = TLI.getShiftAmountTy(VT);
2108a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao    assert(ShiftTy.getScalarType().getSizeInBits() >=
2109a6b20ced765b67a85d9219d0c8547fc9c133e14fMichael Liao           Log2_32_Ceil(VT.getScalarType().getSizeInBits()) &&
2110022688c260f472b4befcd974a6c907c6830f308eBenjamin Kramer           "ShiftAmountTy is too small to cover the range of this type!");
2111914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer    if (ShiftOp.getValueType() != ShiftTy)
2112914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer      ShiftOp = DAG.getZExtOrTrunc(ShiftOp, dl, ShiftTy);
2113914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer
2114914f8c4825140a97219e94b815beb2bc77395d10Benjamin Kramer    SDValue Ops[] = { LHSL, LHSH, ShiftOp };
2115fc1665793e62eb4f26d24b8a19eecf59cd872e2aDan Gohman    Lo = DAG.getNode(PartsOpc, dl, DAG.getVTList(VT, VT), Ops, 3);
2116cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    Hi = Lo.getValue(1);
2117cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    return;
2118cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
211941edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands
2120cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // Otherwise, emit a libcall.
2121dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
212241edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  bool isSigned;
212341edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  if (N->getOpcode() == ISD::SHL) {
212441edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands    isSigned = false; /*sign irrelevant*/
2125825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    if (VT == MVT::i16)
212615c94d08ab2be2e3d00de4edbfc7adde6545a7dbSanjiv Gupta      LC = RTLIB::SHL_I16;
2127825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i32)
2128dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SHL_I32;
2129825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i64)
2130dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SHL_I64;
2131825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i128)
2132dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SHL_I128;
213341edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  } else if (N->getOpcode() == ISD::SRL) {
213441edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands    isSigned = false;
2135825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    if (VT == MVT::i16)
213615c94d08ab2be2e3d00de4edbfc7adde6545a7dbSanjiv Gupta      LC = RTLIB::SRL_I16;
2137825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i32)
2138dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SRL_I32;
2139825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i64)
2140dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SRL_I64;
2141825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i128)
2142dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SRL_I128;
214341edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  } else {
214441edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands    assert(N->getOpcode() == ISD::SRA && "Unknown shift!");
214541edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands    isSigned = true;
2146825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    if (VT == MVT::i16)
214715c94d08ab2be2e3d00de4edbfc7adde6545a7dbSanjiv Gupta      LC = RTLIB::SRA_I16;
2148825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i32)
2149dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SRA_I32;
2150825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i64)
2151dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SRA_I64;
2152825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (VT == MVT::i128)
2153dddc6291fb5274282a20d5923b50535d456d34a4Duncan Sands      LC = RTLIB::SRA_I128;
215441edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands  }
21558c899ee031481dbece5f111379a274c848cb5902Duncan Sands
21566fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  if (LC != RTLIB::UNKNOWN_LIBCALL && TLI.getLibcallName(LC)) {
21576fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng    SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
21582c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover    SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, 2, isSigned, dl), Lo, Hi);
21596fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng    return;
21606fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  }
216141edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands
21626fb2168aaed06e4685d064b6f63dc4c668b42728Evan Cheng  if (!ExpandShiftWithUnknownAmountBit(N, Lo, Hi))
2163c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    llvm_unreachable("Unsupported shift!");
216441edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands}
2165cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
216605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_SIGN_EXTEND(SDNode *N,
2167475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                                SDValue &Lo, SDValue &Hi) {
216823b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
2169ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2170475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
217105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (Op.getValueType().bitsLE(NVT)) {
2172b3bc6352defdf1a5c6b1b0770d0c4d603f6524a8Duncan Sands    // The low part is sign extension of the input (degenerates to a copy).
2173786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::SIGN_EXTEND, dl, NVT, N->getOperand(0));
217405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // The high part is obtained by SRA'ing all but one of the bits of low part.
217505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    unsigned LoSize = NVT.getSizeInBits();
2176786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::SRA, dl, NVT, Lo,
217792abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                     DAG.getConstant(LoSize-1, TLI.getPointerTy()));
217805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
217905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // For example, extension of an i48 to an i64.  The operand type necessarily
218005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // promotes to the result type, so will end up being expanded too.
218196e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem    assert(getTypeAction(Op.getValueType()) ==
218296e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem           TargetLowering::TypePromoteInteger &&
218305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Only know how to promote this result!");
2184475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Res = GetPromotedInteger(Op);
218505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    assert(Res.getValueType() == N->getValueType(0) &&
218605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Operand over promoted?");
218705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Split the promoted operand.  This will simplify when it is expanded.
218805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    SplitInteger(Res, Lo, Hi);
218905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    unsigned ExcessBits =
219005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Op.getValueType().getSizeInBits() - NVT.getSizeInBits();
2191786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Hi.getValueType(), Hi,
2192285fb1cc4a7ea924b4d94e9c2cb890125d56a7e0Evan Cheng                     DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
2193285fb1cc4a7ea924b4d94e9c2cb890125d56a7e0Evan Cheng                                                        ExcessBits)));
219405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
219505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
219605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
219705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::
2198475871a144eb604ddaf37503397ba0941442e5fbDan GohmanExpandIntRes_SIGN_EXTEND_INREG(SDNode *N, SDValue &Lo, SDValue &Hi) {
2199ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
220069b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  GetExpandedInteger(N->getOperand(0), Lo, Hi);
2201e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT EVT = cast<VTSDNode>(N->getOperand(1))->getVT();
2202d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
220305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (EVT.bitsLE(Lo.getValueType())) {
220405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // sext_inreg the low part if needed.
2205786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Lo.getValueType(), Lo,
220605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                     N->getOperand(1));
2207d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
220805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // The high part gets the sign extension from the lo-part.  This handles
220905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // things like sextinreg V:i64 from i8.
2210786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::SRA, dl, Hi.getValueType(), Lo,
221105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                     DAG.getConstant(Hi.getValueType().getSizeInBits()-1,
221292abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                                     TLI.getPointerTy()));
221305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
221405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // For example, extension of an i48 to an i64.  Leave the low part alone,
221505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // sext_inreg the high part.
221605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    unsigned ExcessBits =
221705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      EVT.getSizeInBits() - Lo.getValueType().getSizeInBits();
2218786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Hi = DAG.getNode(ISD::SIGN_EXTEND_INREG, dl, Hi.getValueType(), Hi,
221954e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                     DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(),
222054e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                                                        ExcessBits)));
222105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
222205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
2223d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
222405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_SREM(SDNode *N,
2225475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
2226e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
2227ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
222805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
222905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
2230825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  if (VT == MVT::i16)
2231a43a7aefd753fe7d6005cbebc9619268db4ae139Sanjiv Gupta    LC = RTLIB::SREM_I16;
2232825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i32)
223305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::SREM_I32;
2234825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i64)
223505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::SREM_I64;
2236825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i128)
223705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::SREM_I128;
223805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported SREM!");
223905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2240475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
22412c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, 2, true, dl), Lo, Hi);
2242d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands}
2243d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
224405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_TRUNCATE(SDNode *N,
2245475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                             SDValue &Lo, SDValue &Hi) {
224623b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
2247ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2248786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Lo = DAG.getNode(ISD::TRUNCATE, dl, NVT, N->getOperand(0));
2249786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Hi = DAG.getNode(ISD::SRL, dl,
2250786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                   N->getOperand(0).getValueType(), N->getOperand(0),
225192abc62399881ba9c525be80362c134ad836e2d9Duncan Sands                   DAG.getConstant(NVT.getSizeInBits(), TLI.getPointerTy()));
2252786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen  Hi = DAG.getNode(ISD::TRUNCATE, dl, NVT, Hi);
2253d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands}
2254d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
2255268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedmanvoid DAGTypeLegalizer::ExpandIntRes_UADDSUBO(SDNode *N,
2256268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                                             SDValue &Lo, SDValue &Hi) {
2257268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue LHS = N->getOperand(0);
2258268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue RHS = N->getOperand(1);
2259ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2260268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2261268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // Expand the result by simply replacing it with the equivalent
2262268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // non-overflow-checking operation.
2263268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue Sum = DAG.getNode(N->getOpcode() == ISD::UADDO ?
2264268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                            ISD::ADD : ISD::SUB, dl, LHS.getValueType(),
2265268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                            LHS, RHS);
2266268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SplitInteger(Sum, Lo, Hi);
2267268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
226894c22716d60ff5edf6a98a3c67e0faa001be1142Sylvestre Ledru  // Calculate the overflow: addition overflows iff a + b < a, and subtraction
226994c22716d60ff5edf6a98a3c67e0faa001be1142Sylvestre Ledru  // overflows iff a - b > a.
2270268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  SDValue Ofl = DAG.getSetCC(dl, N->getValueType(1), Sum, LHS,
2271268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                             N->getOpcode () == ISD::UADDO ?
2272268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman                             ISD::SETULT : ISD::SETUGT);
2273268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2274268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  // Use the calculated overflow everywhere.
2275268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman  ReplaceValueWith(SDValue(N, 1), Ofl);
2276268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman}
2277268637ed0f34e10e4125e94c44ff3e2975a19166Eli Friedman
2278362fee90b9a1d64ac091755466caf6a94ade22ebEric Christophervoid DAGTypeLegalizer::ExpandIntRes_XMULO(SDNode *N,
2279362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher                                          SDValue &Lo, SDValue &Hi) {
2280362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  EVT VT = N->getValueType(0);
2281ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2282362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
2283a3071455e540530ecb644a2e59098129f70ce705Eric Christopher  // A divide for UMULO should be faster than a function call.
2284a3071455e540530ecb644a2e59098129f70ce705Eric Christopher  if (N->getOpcode() == ISD::UMULO) {
2285a3071455e540530ecb644a2e59098129f70ce705Eric Christopher    SDValue LHS = N->getOperand(0), RHS = N->getOperand(1);
2286a3071455e540530ecb644a2e59098129f70ce705Eric Christopher
2287331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher    SDValue MUL = DAG.getNode(ISD::MUL, dl, LHS.getValueType(), LHS, RHS);
2288a3071455e540530ecb644a2e59098129f70ce705Eric Christopher    SplitInteger(MUL, Lo, Hi);
2289a3071455e540530ecb644a2e59098129f70ce705Eric Christopher
2290a3071455e540530ecb644a2e59098129f70ce705Eric Christopher    // A divide for UMULO will be faster than a function call. Select to
2291a3071455e540530ecb644a2e59098129f70ce705Eric Christopher    // make sure we aren't using 0.
2292225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault    SDValue isZero = DAG.getSetCC(dl, getSetCCResultType(VT),
2293ffaf69b8b118808ca35ab84d477fd2e4e54cce90Eric Christopher                                  RHS, DAG.getConstant(0, VT), ISD::SETEQ);
2294b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    SDValue NotZero = DAG.getSelect(dl, VT, isZero,
2295b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                    DAG.getConstant(1, VT), RHS);
2296331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher    SDValue DIV = DAG.getNode(ISD::UDIV, dl, VT, MUL, NotZero);
2297331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher    SDValue Overflow = DAG.getSetCC(dl, N->getValueType(1), DIV, LHS,
2298331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher                                    ISD::SETNE);
2299b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    Overflow = DAG.getSelect(dl, N->getValueType(1), isZero,
2300b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                             DAG.getConstant(0, N->getValueType(1)),
2301b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                             Overflow);
2302a3071455e540530ecb644a2e59098129f70ce705Eric Christopher    ReplaceValueWith(SDValue(N, 1), Overflow);
2303a3071455e540530ecb644a2e59098129f70ce705Eric Christopher    return;
2304a3071455e540530ecb644a2e59098129f70ce705Eric Christopher  }
2305a3071455e540530ecb644a2e59098129f70ce705Eric Christopher
2306331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher  Type *RetTy = VT.getTypeForEVT(*DAG.getContext());
2307331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher  EVT PtrVT = TLI.getPointerTy();
2308331f64cd0dc1249d0708af63b4d13509850c234eEric Christopher  Type *PtrTy = PtrVT.getTypeForEVT(*DAG.getContext());
2309155615d7dc4e4fbfd3b7273720a76356468edf46Stephen Lin
23105e687ac6158bc28f1831699d7dbfa39d3120b892Eric Christopher  // Replace this with a libcall that will check overflow.
2311362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
2312362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  if (VT == MVT::i32)
2313362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    LC = RTLIB::MULO_I32;
2314362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  else if (VT == MVT::i64)
2315362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    LC = RTLIB::MULO_I64;
2316362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  else if (VT == MVT::i128)
2317362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    LC = RTLIB::MULO_I128;
2318362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported XMULO!");
2319362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
2320362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  SDValue Temp = DAG.CreateStackTemporary(PtrVT);
2321362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  // Temporary for the overflow value, default it to zero.
2322362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  SDValue Chain = DAG.getStore(DAG.getEntryNode(), dl,
232396cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                               DAG.getConstant(0, PtrVT), Temp,
232496cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                               MachinePointerInfo(), false, false, 0);
2325362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
2326362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  TargetLowering::ArgListTy Args;
2327362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  TargetLowering::ArgListEntry Entry;
2328362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  for (unsigned i = 0, e = N->getNumOperands(); i != e; ++i) {
2329362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    EVT ArgVT = N->getOperand(i).getValueType();
2330db125cfaf57cc83e7dd7453de2d509bc8efd0e5eChris Lattner    Type *ArgTy = ArgVT.getTypeForEVT(*DAG.getContext());
2331362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    Entry.Node = N->getOperand(i);
2332362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    Entry.Ty = ArgTy;
2333362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    Entry.isSExt = true;
2334362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    Entry.isZExt = false;
2335362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher    Args.push_back(Entry);
2336362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  }
2337362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
2338362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  // Also pass the address of the overflow check.
2339362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  Entry.Node = Temp;
2340b8bce928f4ffdf50eff69334f3e25b27848536b6Micah Villmow  Entry.Ty = PtrTy->getPointerTo();
2341362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  Entry.isSExt = true;
2342362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  Entry.isZExt = false;
2343362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  Args.push_back(Entry);
2344362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
2345362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  SDValue Func = DAG.getExternalSymbol(TLI.getLibcallName(LC), PtrVT);
2346d2ea0e10cbd158c93fb870cdd03001b9cd1156b8Justin Holewinski  TargetLowering::
2347d2ea0e10cbd158c93fb870cdd03001b9cd1156b8Justin Holewinski  CallLoweringInfo CLI(Chain, RetTy, true, false, false, false,
234896cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                       0, TLI.getLibcallCallingConv(LC),
234996cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                       /*isTailCall=*/false,
235096cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                       /*doesNotReturn=*/false, /*isReturnValueUsed=*/true,
235196cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                       Func, Args, DAG, dl);
2352d2ea0e10cbd158c93fb870cdd03001b9cd1156b8Justin Holewinski  std::pair<SDValue, SDValue> CallInfo = TLI.LowerCallTo(CLI);
2353362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
2354362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  SplitInteger(CallInfo.first, Lo, Hi);
2355362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  SDValue Temp2 = DAG.getLoad(PtrVT, dl, CallInfo.second, Temp,
235696cb1128528a512f1ef9c28ae5e1b78a98dcc505Bill Wendling                              MachinePointerInfo(), false, false, false, 0);
2357362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  SDValue Ofl = DAG.getSetCC(dl, N->getValueType(1), Temp2,
2358362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher                             DAG.getConstant(0, PtrVT),
2359362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher                             ISD::SETNE);
2360362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  // Use the overflow from the libcall everywhere.
2361362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher  ReplaceValueWith(SDValue(N, 1), Ofl);
2362362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher}
2363362fee90b9a1d64ac091755466caf6a94ade22ebEric Christopher
236405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_UDIV(SDNode *N,
2365475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
2366e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
2367ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2368d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
236905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
2370825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  if (VT == MVT::i16)
2371a43a7aefd753fe7d6005cbebc9619268db4ae139Sanjiv Gupta    LC = RTLIB::UDIV_I16;
2372825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i32)
237305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::UDIV_I32;
2374825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i64)
237505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::UDIV_I64;
2376825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i128)
237705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::UDIV_I128;
237805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported UDIV!");
2379d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands
2380475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
23812c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, 2, false, dl), Lo, Hi);
2382d462ba853981d45bf9c777564e79dc9e1c850ca6Duncan Sands}
2383cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
238405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_UREM(SDNode *N,
2385475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                         SDValue &Lo, SDValue &Hi) {
2386e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getValueType(0);
2387ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
238869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
238905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  RTLIB::Libcall LC = RTLIB::UNKNOWN_LIBCALL;
2390825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  if (VT == MVT::i16)
2391a43a7aefd753fe7d6005cbebc9619268db4ae139Sanjiv Gupta    LC = RTLIB::UREM_I16;
2392825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i32)
239305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::UREM_I32;
2394825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i64)
239505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::UREM_I64;
2396825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson  else if (VT == MVT::i128)
239705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    LC = RTLIB::UREM_I128;
239805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL && "Unsupported UREM!");
2399cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2400475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ops[2] = { N->getOperand(0), N->getOperand(1) };
24012c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  SplitInteger(TLI.makeLibCall(DAG, LC, VT, Ops, 2, false, dl), Lo, Hi);
2402cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
2403cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
240405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsvoid DAGTypeLegalizer::ExpandIntRes_ZERO_EXTEND(SDNode *N,
2405475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                                SDValue &Lo, SDValue &Hi) {
240623b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), N->getValueType(0));
2407ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2408475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
240905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  if (Op.getValueType().bitsLE(NVT)) {
2410b3bc6352defdf1a5c6b1b0770d0c4d603f6524a8Duncan Sands    // The low part is zero extension of the input (degenerates to a copy).
2411786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Lo = DAG.getNode(ISD::ZERO_EXTEND, dl, NVT, N->getOperand(0));
241205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    Hi = DAG.getConstant(0, NVT);   // The high part is just a zero.
241305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  } else {
241405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // For example, extension of an i48 to an i64.  The operand type necessarily
241505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // promotes to the result type, so will end up being expanded too.
241696e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem    assert(getTypeAction(Op.getValueType()) ==
241796e0c5477c41b316263e894bbb5821c7cdeb25efNadav Rotem           TargetLowering::TypePromoteInteger &&
241805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Only know how to promote this result!");
2419475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Res = GetPromotedInteger(Op);
242005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    assert(Res.getValueType() == N->getValueType(0) &&
242105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Operand over promoted?");
242205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Split the promoted operand.  This will simplify when it is expanded.
242305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    SplitInteger(Res, Lo, Hi);
242405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    unsigned ExcessBits =
242505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      Op.getValueType().getSizeInBits() - NVT.getSizeInBits();
2426adf979900c84d00e1fe0872a68d2819c654b6f29Evan Cheng    Hi = DAG.getZeroExtendInReg(Hi, dl,
242754e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                                EVT::getIntegerVT(*DAG.getContext(),
242854e1791e4ba30867bda603acadda77fa85de6aa1Eric Christopher                                                  ExcessBits));
24299e255b7df5a0a629920706e086e78ef89bf2f183Dan Gohman  }
2430cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
2431cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2432ba567d670d32e102a70b106fbfe284835085cb3fEli Friedmanvoid DAGTypeLegalizer::ExpandIntRes_ATOMIC_LOAD(SDNode *N,
2433ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                                                SDValue &Lo, SDValue &Hi) {
2434ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2435ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  EVT VT = cast<AtomicSDNode>(N)->getMemoryVT();
2436ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  SDValue Zero = DAG.getConstant(0, VT);
2437ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  SDValue Swap = DAG.getAtomic(ISD::ATOMIC_CMP_SWAP, dl, VT,
2438ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               N->getOperand(0),
2439ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               N->getOperand(1), Zero, Zero,
2440ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getMemOperand(),
2441ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getOrdering(),
2442ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getSynchScope());
2443ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  ReplaceValueWith(SDValue(N, 0), Swap.getValue(0));
2444ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  ReplaceValueWith(SDValue(N, 1), Swap.getValue(1));
2445ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman}
2446cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2447cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//===----------------------------------------------------------------------===//
244869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands//  Integer Operand Expansion
2449cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner//===----------------------------------------------------------------------===//
2450cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
245105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// ExpandIntegerOperand - This method is called when the specified operand of
245205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// the specified node is found to need expansion.  At this point, all of the
245305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// result types of the node are known to be legal, but other operands of the
245405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands/// node may need promotion or expansion as well as the specified one.
245505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sandsbool DAGTypeLegalizer::ExpandIntegerOperand(SDNode *N, unsigned OpNo) {
2456d765353da89988e949fd4c021d8860f36ab7c392David Greene  DEBUG(dbgs() << "Expand integer operand: "; N->dump(&DAG); dbgs() << "\n");
2457475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Res = SDValue();
2458051bb7b07504be9f848f7cce802e62ed24980bc5Duncan Sands
2459f43071beddb7ed5b2fd7d2f06c4130460616a13dDuncan Sands  if (CustomLowerNode(N, N->getOperand(OpNo).getValueType(), false))
2460bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta    return false;
246111ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands
2462bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  switch (N->getOpcode()) {
2463bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  default:
246405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  #ifndef NDEBUG
2465d765353da89988e949fd4c021d8860f36ab7c392David Greene    dbgs() << "ExpandIntegerOperand Op #" << OpNo << ": ";
2466d765353da89988e949fd4c021d8860f36ab7c392David Greene    N->dump(&DAG); dbgs() << "\n";
246705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  #endif
2468c23197a26f34f559ea9797de51e187087c039c42Torok Edwin    llvm_unreachable("Do not know how to expand this operator's operand!");
2469bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta
2470bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck  case ISD::BITCAST:           Res = ExpandOp_BITCAST(N); break;
247192abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::BR_CC:             Res = ExpandIntOp_BR_CC(N); break;
247292abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::BUILD_VECTOR:      Res = ExpandOp_BUILD_VECTOR(N); break;
2473bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::EXTRACT_ELEMENT:   Res = ExpandOp_EXTRACT_ELEMENT(N); break;
2474bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::INSERT_VECTOR_ELT: Res = ExpandOp_INSERT_VECTOR_ELT(N); break;
2475bb326bbe88d0b243d5d9d224308eb0c028d4d4afSanjiv Gupta  case ISD::SCALAR_TO_VECTOR:  Res = ExpandOp_SCALAR_TO_VECTOR(N); break;
247692abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::SELECT_CC:         Res = ExpandIntOp_SELECT_CC(N); break;
247792abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::SETCC:             Res = ExpandIntOp_SETCC(N); break;
247892abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::SINT_TO_FP:        Res = ExpandIntOp_SINT_TO_FP(N); break;
247992abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::STORE:   Res = ExpandIntOp_STORE(cast<StoreSDNode>(N), OpNo); break;
248092abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::TRUNCATE:          Res = ExpandIntOp_TRUNCATE(N); break;
248192abc62399881ba9c525be80362c134ad836e2d9Duncan Sands  case ISD::UINT_TO_FP:        Res = ExpandIntOp_UINT_TO_FP(N); break;
248255467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta
248355467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::SHL:
248455467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::SRA:
248555467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::SRL:
248655467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  case ISD::ROTL:
24871c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  case ISD::ROTR:              Res = ExpandIntOp_Shift(N); break;
24881c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  case ISD::RETURNADDR:
24891c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  case ISD::FRAMEADDR:         Res = ExpandIntOp_RETURNADDR(N); break;
2490ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman
2491ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  case ISD::ATOMIC_STORE:      Res = ExpandIntOp_ATOMIC_STORE(N); break;
249205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
249369b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
249405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If the result is null, the sub-method took care of registering results etc.
2495ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (!Res.getNode()) return false;
249647d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands
249747d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands  // If the result is N, the sub-method updated N in place.  Tell the legalizer
249847d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands  // core about this.
249947d9dcc584cdb7fd645ca1d5c2a0ce363570aeb7Duncan Sands  if (Res.getNode() == N)
250005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    return true;
2501cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
250205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(Res.getValueType() == N->getValueType(0) && N->getNumValues() == 1 &&
250305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands         "Invalid operand expansion");
250405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2505475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  ReplaceValueWith(SDValue(N, 0), Res);
250605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  return false;
2507cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
2508cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
250911ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands/// IntegerExpandSetCCOperands - Expand the operands of a comparison.  This code
251011ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands/// is shared among BR_CC, SELECT_CC, and SETCC handlers.
2511475871a144eb604ddaf37503397ba0941442e5fbDan Gohmanvoid DAGTypeLegalizer::IntegerExpandSetCCOperands(SDValue &NewLHS,
2512475871a144eb604ddaf37503397ba0941442e5fbDan Gohman                                                  SDValue &NewRHS,
2513c8fc99d66a03dc603f49d653937ad1d94e833006Dale Johannesen                                                  ISD::CondCode &CCCode,
2514ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick                                                  SDLoc dl) {
2515475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue LHSLo, LHSHi, RHSLo, RHSHi;
251669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  GetExpandedInteger(NewLHS, LHSLo, LHSHi);
251769b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands  GetExpandedInteger(NewRHS, RHSLo, RHSHi);
251841edfb8ae119d6cf6579046619dd2820ec876065Duncan Sands
2519cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  if (CCCode == ISD::SETEQ || CCCode == ISD::SETNE) {
252011ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands    if (RHSLo == RHSHi) {
252111ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands      if (ConstantSDNode *RHSCST = dyn_cast<ConstantSDNode>(RHSLo)) {
2522cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        if (RHSCST->isAllOnesValue()) {
2523cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner          // Equality comparison to -1.
25247fb085871857134f8cbeb17499d4ab771ba8da42Duncan Sands          NewLHS = DAG.getNode(ISD::AND, dl,
2525786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen                               LHSLo.getValueType(), LHSLo, LHSHi);
2526cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner          NewRHS = RHSLo;
2527cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner          return;
2528cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        }
252911ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands      }
253011ac797f5ed142f11aafde3dd76c28a73d84282eDuncan Sands    }
253169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2532786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    NewLHS = DAG.getNode(ISD::XOR, dl, LHSLo.getValueType(), LHSLo, RHSLo);
2533786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    NewRHS = DAG.getNode(ISD::XOR, dl, LHSLo.getValueType(), LHSHi, RHSHi);
2534786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    NewLHS = DAG.getNode(ISD::OR, dl, NewLHS.getValueType(), NewLHS, NewRHS);
2535cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    NewRHS = DAG.getConstant(0, NewLHS.getValueType());
2536cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    return;
2537cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
253869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2539cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // If this is a comparison of the sign bit, just look at the top part.
2540cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // X > -1,  x < 0
2541cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  if (ConstantSDNode *CST = dyn_cast<ConstantSDNode>(NewRHS))
2542002e5d0a170dadd5c307e0b00d8c7970835837e6Dan Gohman    if ((CCCode == ISD::SETLT && CST->isNullValue()) ||     // X < 0
2543cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        (CCCode == ISD::SETGT && CST->isAllOnesValue())) {  // X > -1
2544cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      NewLHS = LHSHi;
2545cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      NewRHS = RHSHi;
2546cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner      return;
2547cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    }
254869b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2549cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // FIXME: This generated code sucks.
2550cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  ISD::CondCode LowCC;
2551cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  switch (CCCode) {
2552c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  default: llvm_unreachable("Unknown integer setcc!");
2553cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETLT:
2554cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETULT: LowCC = ISD::SETULT; break;
2555cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETGT:
2556cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETUGT: LowCC = ISD::SETUGT; break;
2557cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETLE:
2558cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETULE: LowCC = ISD::SETULE; break;
2559cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETGE:
2560cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  case ISD::SETUGE: LowCC = ISD::SETUGE; break;
2561cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
256269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2563cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // Tmp1 = lo(op1) < lo(op2)   // Always unsigned comparison
2564cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // Tmp2 = hi(op1) < hi(op2)   // Signedness depends on operands
2565cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // dest = hi(op1) == hi(op2) ? Tmp1 : Tmp2;
256669b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2567cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // NOTE: on targets without efficient SELECT of bools, we can always use
2568cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  // this identity: (B1 ? B2 : B3) --> (B1 & B2)|(!B1&B3)
2569444b4bf5c84c80833ff283244de0885124091a13Nadav Rotem  TargetLowering::DAGCombinerInfo DagCombineInfo(DAG, AfterLegalizeTypes, true, NULL);
2570475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Tmp1, Tmp2;
2571225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  Tmp1 = TLI.SimplifySetCC(getSetCCResultType(LHSLo.getValueType()),
2572ff97d4fe81ef0dcee9fe490bed8ab08e40251905Dale Johannesen                           LHSLo, RHSLo, LowCC, false, DagCombineInfo, dl);
2573ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (!Tmp1.getNode())
2574225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault    Tmp1 = DAG.getSetCC(dl, getSetCCResultType(LHSLo.getValueType()),
25755480c0469e5c0323ffb12f1ead2abd169d6cc0e7Duncan Sands                        LHSLo, RHSLo, LowCC);
2576225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  Tmp2 = TLI.SimplifySetCC(getSetCCResultType(LHSHi.getValueType()),
2577ff97d4fe81ef0dcee9fe490bed8ab08e40251905Dale Johannesen                           LHSHi, RHSHi, CCCode, false, DagCombineInfo, dl);
2578ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (!Tmp2.getNode())
2579786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Tmp2 = DAG.getNode(ISD::SETCC, dl,
2580225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault                       getSetCCResultType(LHSHi.getValueType()),
25815480c0469e5c0323ffb12f1ead2abd169d6cc0e7Duncan Sands                       LHSHi, RHSHi, DAG.getCondCode(CCCode));
258269b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2583ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  ConstantSDNode *Tmp1C = dyn_cast<ConstantSDNode>(Tmp1.getNode());
2584ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  ConstantSDNode *Tmp2C = dyn_cast<ConstantSDNode>(Tmp2.getNode());
2585002e5d0a170dadd5c307e0b00d8c7970835837e6Dan Gohman  if ((Tmp1C && Tmp1C->isNullValue()) ||
2586002e5d0a170dadd5c307e0b00d8c7970835837e6Dan Gohman      (Tmp2C && Tmp2C->isNullValue() &&
2587cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner       (CCCode == ISD::SETLE || CCCode == ISD::SETGE ||
2588cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        CCCode == ISD::SETUGE || CCCode == ISD::SETULE)) ||
2589002e5d0a170dadd5c307e0b00d8c7970835837e6Dan Gohman      (Tmp2C && Tmp2C->getAPIntValue() == 1 &&
2590cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner       (CCCode == ISD::SETLT || CCCode == ISD::SETGT ||
2591cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner        CCCode == ISD::SETUGT || CCCode == ISD::SETULT))) {
2592cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // low part is known false, returns high part.
2593cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // For LE / GE, if high part is known false, ignore the low part.
2594cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // For LT / GT, if high part is known true, ignore the low part.
2595cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    NewLHS = Tmp2;
2596475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    NewRHS = SDValue();
2597cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    return;
2598cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
259969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands
2600225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault  NewLHS = TLI.SimplifySetCC(getSetCCResultType(LHSHi.getValueType()),
2601fdc40a0a696c658d550d894ea03772e5f8af2c94Scott Michel                             LHSHi, RHSHi, ISD::SETEQ, false,
2602ff97d4fe81ef0dcee9fe490bed8ab08e40251905Dale Johannesen                             DagCombineInfo, dl);
2603ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (!NewLHS.getNode())
2604225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault    NewLHS = DAG.getSetCC(dl, getSetCCResultType(LHSHi.getValueType()),
26055480c0469e5c0323ffb12f1ead2abd169d6cc0e7Duncan Sands                          LHSHi, RHSHi, ISD::SETEQ);
2606b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault  NewLHS = DAG.getSelect(dl, Tmp1.getValueType(),
2607b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                         NewLHS, Tmp1, Tmp2);
2608475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  NewRHS = SDValue();
2609cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
2610cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2611475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_BR_CC(SDNode *N) {
2612475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue NewLHS = N->getOperand(2), NewRHS = N->getOperand(3);
261305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  ISD::CondCode CCCode = cast<CondCodeSDNode>(N->getOperand(1))->get();
2614ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  IntegerExpandSetCCOperands(NewLHS, NewRHS, CCCode, SDLoc(N));
261505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
261605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If ExpandSetCCOperands returned a scalar, we need to compare the result
261705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // against zero to select between true and false values.
2618ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (NewRHS.getNode() == 0) {
261905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    NewRHS = DAG.getConstant(0, NewLHS.getValueType());
262005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    CCCode = ISD::SETNE;
262105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
262205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
262305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Update N to have the operands specified.
2624027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0),
262505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                DAG.getCondCode(CCCode), NewLHS, NewRHS,
2626027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                N->getOperand(4)), 0);
262705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
262805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2629475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_SELECT_CC(SDNode *N) {
2630475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue NewLHS = N->getOperand(0), NewRHS = N->getOperand(1);
263105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  ISD::CondCode CCCode = cast<CondCodeSDNode>(N->getOperand(4))->get();
2632ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  IntegerExpandSetCCOperands(NewLHS, NewRHS, CCCode, SDLoc(N));
263305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
263405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If ExpandSetCCOperands returned a scalar, we need to compare the result
263505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // against zero to select between true and false values.
2636ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (NewRHS.getNode() == 0) {
263705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    NewRHS = DAG.getConstant(0, NewLHS.getValueType());
263805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    CCCode = ISD::SETNE;
263905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
264005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
264105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Update N to have the operands specified.
2642027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, NewLHS, NewRHS,
264305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands                                N->getOperand(2), N->getOperand(3),
2644027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                DAG.getCondCode(CCCode)), 0);
264505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
264605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2647475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_SETCC(SDNode *N) {
2648475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue NewLHS = N->getOperand(0), NewRHS = N->getOperand(1);
264905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  ISD::CondCode CCCode = cast<CondCodeSDNode>(N->getOperand(2))->get();
2650ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  IntegerExpandSetCCOperands(NewLHS, NewRHS, CCCode, SDLoc(N));
265105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
265205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // If ExpandSetCCOperands returned a scalar, use it.
2653ba36cb5242eb02b12b277f82b9efe497f7da4d7fGabor Greif  if (NewRHS.getNode() == 0) {
265405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    assert(NewLHS.getValueType() == N->getValueType(0) &&
265505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands           "Unexpected setcc expansion!");
265605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    return NewLHS;
265705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
265805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
265905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Otherwise, update N to have the operands specified.
2660027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, NewLHS, NewRHS,
2661027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman                                DAG.getCondCode(CCCode)), 0);
266205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
266305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
266455467af31620c9d027e071ebcd9746b7593cff17Sanjiv GuptaSDValue DAGTypeLegalizer::ExpandIntOp_Shift(SDNode *N) {
266555467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  // The value being shifted is legal, but the shift amount is too big.
266655467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  // It follows that either the result of the shift is undefined, or the
266755467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  // upper half of the shift amount is zero.  Just use the lower half.
266855467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  SDValue Lo, Hi;
266955467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta  GetExpandedInteger(N->getOperand(1), Lo, Hi);
2670027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, N->getOperand(0), Lo), 0);
267155467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta}
267255467af31620c9d027e071ebcd9746b7593cff17Sanjiv Gupta
26731c3436a67afcfaee5f972836ff1ffff2985adce1Anton KorobeynikovSDValue DAGTypeLegalizer::ExpandIntOp_RETURNADDR(SDNode *N) {
26741c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  // The argument of RETURNADDR / FRAMEADDR builtin is 32 bit contant.  This
26751c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  // surely makes pretty nice problems on 8/16 bit targets. Just truncate this
26761c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  // constant to valid type.
26771c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  SDValue Lo, Hi;
26781c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov  GetExpandedInteger(N->getOperand(0), Lo, Hi);
2679027657db7cf60bcbf40403496d7e4a170f9ce1ecDan Gohman  return SDValue(DAG.UpdateNodeOperands(N, Lo), 0);
26801c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov}
26811c3436a67afcfaee5f972836ff1ffff2985adce1Anton Korobeynikov
2682475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_SINT_TO_FP(SDNode *N) {
2683475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
2684e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT DstVT = N->getValueType(0);
2685b2ff885aaed8f9b033b16ca78d645650efc32433Duncan Sands  RTLIB::Libcall LC = RTLIB::getSINTTOFP(Op.getValueType(), DstVT);
268605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL &&
268705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands         "Don't know how to expand this SINT_TO_FP!");
2688ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return TLI.makeLibCall(DAG, LC, DstVT, &Op, 1, true, SDLoc(N));
268905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
269005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2691475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_STORE(StoreSDNode *N, unsigned OpNo) {
2692ab09b7e8f34075c1759127a113f41bdf921f4034Duncan Sands  if (ISD::isNormalStore(N))
2693ab09b7e8f34075c1759127a113f41bdf921f4034Duncan Sands    return ExpandOp_NormalStore(N, OpNo);
269478cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands
269578cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  assert(ISD::isUNINDEXEDStore(N) && "Indexed store during type legalization!");
2696cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  assert(OpNo == 1 && "Can only expand the stored value so far");
2697cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2698e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT VT = N->getOperand(1).getValueType();
269923b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson  EVT NVT = TLI.getTypeToTransformTo(*DAG.getContext(), VT);
2700475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ch  = N->getChain();
2701475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Ptr = N->getBasePtr();
2702cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  unsigned Alignment = N->getAlignment();
2703cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  bool isVolatile = N->isVolatile();
27041e559443a17d1b335f697551c6263ba60d5dd827David Greene  bool isNonTemporal = N->isNonTemporal();
2705ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2706475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Lo, Hi;
2707cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2708a1ace76c70ae5332d6f33fce5c0c1e2fdb8cca11Duncan Sands  assert(NVT.isByteSized() && "Expanded type not byte sized!");
2709cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
271078cd649ad326f79a1f8424ca2b63cea3239a9a52Duncan Sands  if (N->getMemoryVT().bitsLE(NVT)) {
271169b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    GetExpandedInteger(N->getValue(), Lo, Hi);
2712ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    return DAG.getTruncStore(Ch, dl, Lo, Ptr, N->getPointerInfo(),
27131e559443a17d1b335f697551c6263ba60d5dd827David Greene                             N->getMemoryVT(), isVolatile, isNonTemporal,
27141e559443a17d1b335f697551c6263ba60d5dd827David Greene                             Alignment);
2715ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  }
2716bf17cfa3f904e488e898ac2e3af706fd1a892f08Wesley Peck
2717ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  if (TLI.isLittleEndian()) {
2718cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Little-endian - low bits are at low addresses.
271969b01e92a29ce6d7e435171aeea3fbc987b81586Duncan Sands    GetExpandedInteger(N->getValue(), Lo, Hi);
2720cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2721ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    Lo = DAG.getStore(Ch, dl, Lo, Ptr, N->getPointerInfo(),
27221e559443a17d1b335f697551c6263ba60d5dd827David Greene                      isVolatile, isNonTemporal, Alignment);
2723cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2724cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    unsigned ExcessBits =
272583ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands      N->getMemoryVT().getSizeInBits() - NVT.getSizeInBits();
272623b9b19b1a5a00faa9fce0788155c7dbfd00bfb1Owen Anderson    EVT NEVT = EVT::getIntegerVT(*DAG.getContext(), ExcessBits);
2727cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2728cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner    // Increment the pointer to the other half.
272983ec4b6711980242ef3c55a4fa36b2d7a39c1bfbDuncan Sands    unsigned IncrementSize = NVT.getSizeInBits()/8;
2730786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    Ptr = DAG.getNode(ISD::ADD, dl, Ptr.getValueType(), Ptr,
27310bd4893a0726889b942405262e53d06cf3fe3be8Chris Lattner                      DAG.getIntPtrConstant(IncrementSize));
2732ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    Hi = DAG.getTruncStore(Ch, dl, Hi, Ptr,
2733ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                           N->getPointerInfo().getWithOffset(IncrementSize),
2734ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                           NEVT, isVolatile, isNonTemporal,
27351e559443a17d1b335f697551c6263ba60d5dd827David Greene                           MinAlign(Alignment, IncrementSize));
2736825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    return DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo, Hi);
2737ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  }
2738cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner
2739ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  // Big-endian - high bits are at low addresses.  Favor aligned stores at
2740ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  // the cost of some bit-fiddling.
2741ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  GetExpandedInteger(N->getValue(), Lo, Hi);
2742ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner
2743ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  EVT ExtVT = N->getMemoryVT();
2744ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  unsigned EBytes = ExtVT.getStoreSize();
2745ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  unsigned IncrementSize = NVT.getSizeInBits()/8;
2746ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  unsigned ExcessBits = (EBytes - IncrementSize)*8;
2747ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  EVT HiVT = EVT::getIntegerVT(*DAG.getContext(),
2748ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                               ExtVT.getSizeInBits() - ExcessBits);
2749ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner
2750ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  if (ExcessBits < NVT.getSizeInBits()) {
2751ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    // Transfer high bits from the top of Lo to the bottom of Hi.
2752ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    Hi = DAG.getNode(ISD::SHL, dl, NVT, Hi,
2753ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                     DAG.getConstant(NVT.getSizeInBits() - ExcessBits,
2754ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                                     TLI.getPointerTy()));
2755ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner    Hi = DAG.getNode(ISD::OR, dl, NVT, Hi,
2756ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                     DAG.getNode(ISD::SRL, dl, NVT, Lo,
2757ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                                 DAG.getConstant(ExcessBits,
2758ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                                                 TLI.getPointerTy())));
2759cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner  }
2760ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner
2761ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  // Store both the high bits and maybe some of the low bits.
2762ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  Hi = DAG.getTruncStore(Ch, dl, Hi, Ptr, N->getPointerInfo(),
2763ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                         HiVT, isVolatile, isNonTemporal, Alignment);
2764ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner
2765ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  // Increment the pointer to the other half.
2766ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  Ptr = DAG.getNode(ISD::ADD, dl, Ptr.getValueType(), Ptr,
2767ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                    DAG.getIntPtrConstant(IncrementSize));
2768ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  // Store the lowest ExcessBits bits in the second half.
2769ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  Lo = DAG.getTruncStore(Ch, dl, Lo, Ptr,
2770ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                         N->getPointerInfo().getWithOffset(IncrementSize),
2771ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                         EVT::getIntegerVT(*DAG.getContext(), ExcessBits),
2772ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                         isVolatile, isNonTemporal,
2773ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner                         MinAlign(Alignment, IncrementSize));
2774ecf42c4720aba6ee315d0166045c54187ac2de4dChris Lattner  return DAG.getNode(ISD::TokenFactor, dl, MVT::Other, Lo, Hi);
2775cc663a8112017f06e0cd4b6fe1546ccfcd5d05c3Chris Lattner}
277605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2777475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_TRUNCATE(SDNode *N) {
2778475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue InL, InH;
277905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  GetExpandedInteger(N->getOperand(0), InL, InH);
278005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Just truncate the low part of the source.
2781ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  return DAG.getNode(ISD::TRUNCATE, SDLoc(N), N->getValueType(0), InL);
278205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
278305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
2784475871a144eb604ddaf37503397ba0941442e5fbDan GohmanSDValue DAGTypeLegalizer::ExpandIntOp_UINT_TO_FP(SDNode *N) {
2785475871a144eb604ddaf37503397ba0941442e5fbDan Gohman  SDValue Op = N->getOperand(0);
2786e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT SrcVT = Op.getValueType();
2787e50ed30282bb5b4a9ed952580523f2dda16215acOwen Anderson  EVT DstVT = N->getValueType(0);
2788ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
278905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
27908d908ebd1926d00ff47d8284e52657705efb7f9bDale Johannesen  // The following optimization is valid only if every value in SrcVT (when
27918d908ebd1926d00ff47d8284e52657705efb7f9bDale Johannesen  // treated as signed) is representable in DstVT.  Check that the mantissa
27928d908ebd1926d00ff47d8284e52657705efb7f9bDale Johannesen  // size of DstVT is >= than the number of bits in SrcVT -1.
27930a29cb045444c13160e90fe7942a9d7c720185edTim Northover  const fltSemantics &sem = DAG.EVTToAPFloatSemantics(DstVT);
27940a29cb045444c13160e90fe7942a9d7c720185edTim Northover  if (APFloat::semanticsPrecision(sem) >= SrcVT.getSizeInBits()-1 &&
27958d908ebd1926d00ff47d8284e52657705efb7f9bDale Johannesen      TLI.getOperationAction(ISD::SINT_TO_FP, SrcVT) == TargetLowering::Custom){
279605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Do a signed conversion then adjust the result.
2797786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    SDValue SignedConv = DAG.getNode(ISD::SINT_TO_FP, dl, DstVT, Op);
279805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    SignedConv = TLI.LowerOperation(SignedConv, DAG);
279905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
280005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // The result of the signed conversion needs adjusting if the 'sign bit' of
280105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // the incoming integer was set.  To handle this, we dynamically test to see
280205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // if it is set, and, if so, add a fudge factor.
280305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
280405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    const uint64_t F32TwoE32  = 0x4F800000ULL;
280505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    const uint64_t F32TwoE64  = 0x5F800000ULL;
280605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    const uint64_t F32TwoE128 = 0x7F800000ULL;
280705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
280805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    APInt FF(32, 0);
2809825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    if (SrcVT == MVT::i32)
281005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      FF = APInt(32, F32TwoE32);
2811825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (SrcVT == MVT::i64)
281205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      FF = APInt(32, F32TwoE64);
2813825b72b0571821bf2d378749f69d6c4cfb52d2f9Owen Anderson    else if (SrcVT == MVT::i128)
281405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands      FF = APInt(32, F32TwoE128);
281505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    else
28165e25ee8a1fcf8288d00d731b0f7ab7976f33b123Craig Topper      llvm_unreachable("Unsupported UINT_TO_FP!");
281705c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
281805c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Check whether the sign bit is set.
2819475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Lo, Hi;
282005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    GetExpandedInteger(Op, Lo, Hi);
28217fb085871857134f8cbeb17499d4ab771ba8da42Duncan Sands    SDValue SignSet = DAG.getSetCC(dl,
2822225ed7069caae9ece32d8bd3d15c6e41e21cc04bMatt Arsenault                                   getSetCCResultType(Hi.getValueType()),
28235480c0469e5c0323ffb12f1ead2abd169d6cc0e7Duncan Sands                                   Hi, DAG.getConstant(0, Hi.getValueType()),
2824ef5b199905cee0b78eb30cd44836e5b6ca5cbd09Duncan Sands                                   ISD::SETLT);
282505c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
282605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Build a 64 bit pair (0, FF) in the constant pool, with FF in the lo bits.
2827001dbfebcbbded8c8e74b19e838b50da2b6c6fb5Owen Anderson    SDValue FudgePtr = DAG.getConstantPool(
2828eed707b1e6097aac2bb6b3d47271f6300ace7f2eOwen Anderson                               ConstantInt::get(*DAG.getContext(), FF.zext(64)),
282949c18cce976c158e86f54c681dff21bb81640fb8Duncan Sands                                           TLI.getPointerTy());
283005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
283105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Get a pointer to FF if the sign bit was set, or to 0 otherwise.
2832475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Zero = DAG.getIntPtrConstant(0);
2833475871a144eb604ddaf37503397ba0941442e5fbDan Gohman    SDValue Four = DAG.getIntPtrConstant(4);
283405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    if (TLI.isBigEndian()) std::swap(Zero, Four);
2835b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault    SDValue Offset = DAG.getSelect(dl, Zero.getValueType(), SignSet,
2836b05e4778f0871cbb02f61e4d55ad7375738a1d01Matt Arsenault                                   Zero, Four);
28371606e8e4cd937e6de6681f686c266cf61722d972Evan Cheng    unsigned Alignment = cast<ConstantPoolSDNode>(FudgePtr)->getAlignment();
2838786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    FudgePtr = DAG.getNode(ISD::ADD, dl, TLI.getPointerTy(), FudgePtr, Offset);
283987a0f10dc7eff8cf5e83a754f75adf9cb3991435Dan Gohman    Alignment = std::min(Alignment, 4u);
284005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
284105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // Load the value out, extending it from f32 to the destination float type.
284205c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands    // FIXME: Avoid the extend by constructing the right constant pool?
2843a901129169194881a78b7fd8953e09f55b846d10Stuart Hastings    SDValue Fudge = DAG.getExtLoad(ISD::EXTLOAD, dl, DstVT, DAG.getEntryNode(),
28443d6ccfba314ed38e4506dae2781a060e9a3e07acChris Lattner                                   FudgePtr,
28453d6ccfba314ed38e4506dae2781a060e9a3e07acChris Lattner                                   MachinePointerInfo::getConstantPool(),
28463d6ccfba314ed38e4506dae2781a060e9a3e07acChris Lattner                                   MVT::f32,
28471e559443a17d1b335f697551c6263ba60d5dd827David Greene                                   false, false, Alignment);
2848786fd4dded6a42561c0d82bbd9d13b9a4d8d9675Dale Johannesen    return DAG.getNode(ISD::FADD, dl, DstVT, SignedConv, Fudge);
284905c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  }
285005c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands
285105c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  // Otherwise, use a libcall.
2852b2ff885aaed8f9b033b16ca78d645650efc32433Duncan Sands  RTLIB::Libcall LC = RTLIB::getUINTTOFP(SrcVT, DstVT);
285305c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands  assert(LC != RTLIB::UNKNOWN_LIBCALL &&
285405c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands         "Don't know how to expand this UINT_TO_FP!");
28552c8cf4b404e549482f593f62f9e27e0bab4a8b3fTim Northover  return TLI.makeLibCall(DAG, LC, DstVT, &Op, 1, true, dl);
285605c397d52a145c8844790d6491c4c51d4bbfed7cDuncan Sands}
2857fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2858ba567d670d32e102a70b106fbfe284835085cb3fEli FriedmanSDValue DAGTypeLegalizer::ExpandIntOp_ATOMIC_STORE(SDNode *N) {
2859ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2860ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  SDValue Swap = DAG.getAtomic(ISD::ATOMIC_SWAP, dl,
2861ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getMemoryVT(),
2862ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               N->getOperand(0),
2863ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               N->getOperand(1), N->getOperand(2),
2864ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getMemOperand(),
2865ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getOrdering(),
2866ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman                               cast<AtomicSDNode>(N)->getSynchScope());
2867ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman  return Swap.getValue(1);
2868ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman}
2869ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman
2870ba567d670d32e102a70b106fbfe284835085cb3fEli Friedman
2871fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_EXTRACT_SUBVECTOR(SDNode *N) {
2872fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue InOp0 = N->getOperand(0);
2873fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT InVT = InOp0.getValueType();
2874fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2875fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT OutVT = N->getValueType(0);
2876fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
2877fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  assert(NOutVT.isVector() && "This type must be promoted to a vector type");
28785b82c2f8911e7e7bcaa563cf15b5d03cf0292379Nadav Rotem  unsigned OutNumElems = OutVT.getVectorNumElements();
2879fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVTElem = NOutVT.getVectorElementType();
2880fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2881ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2882fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue BaseIdx = N->getOperand(1);
2883fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2884fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SmallVector<SDValue, 8> Ops;
28855b82c2f8911e7e7bcaa563cf15b5d03cf0292379Nadav Rotem  Ops.reserve(OutNumElems);
2886fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  for (unsigned i = 0; i != OutNumElems; ++i) {
2887fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2888fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    // Extract the element from the original vector.
2889fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    SDValue Index = DAG.getNode(ISD::ADD, dl, BaseIdx.getValueType(),
2890425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard      BaseIdx, DAG.getConstant(i, BaseIdx.getValueType()));
2891fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl,
2892fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem      InVT.getVectorElementType(), N->getOperand(0), Index);
2893fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2894fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    SDValue Op = DAG.getNode(ISD::ANY_EXTEND, dl, NOutVTElem, Ext);
2895fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    // Insert the converted element to the new vector.
2896fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    Ops.push_back(Op);
2897fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  }
2898fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2899fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  return DAG.getNode(ISD::BUILD_VECTOR, dl, NOutVT, &Ops[0], Ops.size());
2900fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem}
2901fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2902fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2903fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_VECTOR_SHUFFLE(SDNode *N) {
2904fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  ShuffleVectorSDNode *SV = cast<ShuffleVectorSDNode>(N);
2905fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT VT = N->getValueType(0);
2906ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2907fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2908fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  unsigned NumElts = VT.getVectorNumElements();
2909fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SmallVector<int, 8> NewMask;
2910fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  for (unsigned i = 0; i != NumElts; ++i) {
2911fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    NewMask.push_back(SV->getMaskElt(i));
2912fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  }
2913fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2914fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue V0 = GetPromotedInteger(N->getOperand(0));
2915fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue V1 = GetPromotedInteger(N->getOperand(1));
29165b82c2f8911e7e7bcaa563cf15b5d03cf0292379Nadav Rotem  EVT OutVT = V0.getValueType();
2917fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
29185b82c2f8911e7e7bcaa563cf15b5d03cf0292379Nadav Rotem  return DAG.getVectorShuffle(OutVT, dl, V0, V1, &NewMask[0]);
2919fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem}
2920fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2921fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2922fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_BUILD_VECTOR(SDNode *N) {
2923fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT OutVT = N->getValueType(0);
2924fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
2925fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  assert(NOutVT.isVector() && "This type must be promoted to a vector type");
2926fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  unsigned NumElems = N->getNumOperands();
2927fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVTElem = NOutVT.getVectorElementType();
2928fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2929ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2930fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2931fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SmallVector<SDValue, 8> Ops;
29325b82c2f8911e7e7bcaa563cf15b5d03cf0292379Nadav Rotem  Ops.reserve(NumElems);
2933fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  for (unsigned i = 0; i != NumElems; ++i) {
293463e7a38c8980d70197ecdb9ba54b79b87c7b064dHal Finkel    SDValue Op;
29356c75160b875799a9303879e11022edf4ba44c3f9Hal Finkel    // BUILD_VECTOR integer operand types are allowed to be larger than the
29366c75160b875799a9303879e11022edf4ba44c3f9Hal Finkel    // result's element type. This may still be true after the promotion. For
29376c75160b875799a9303879e11022edf4ba44c3f9Hal Finkel    // example, we might be promoting (<v?i1> = BV <i32>, <i32>, ...) to
29386c75160b875799a9303879e11022edf4ba44c3f9Hal Finkel    // (v?i16 = BV <i32>, <i32>, ...), and we can't any_extend <i32> to <i16>.
293963e7a38c8980d70197ecdb9ba54b79b87c7b064dHal Finkel    if (N->getOperand(i).getValueType().bitsLT(NOutVTElem))
294063e7a38c8980d70197ecdb9ba54b79b87c7b064dHal Finkel      Op = DAG.getNode(ISD::ANY_EXTEND, dl, NOutVTElem, N->getOperand(i));
294163e7a38c8980d70197ecdb9ba54b79b87c7b064dHal Finkel    else
294263e7a38c8980d70197ecdb9ba54b79b87c7b064dHal Finkel      Op = N->getOperand(i);
2943fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    Ops.push_back(Op);
2944fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  }
2945fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2946fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  return DAG.getNode(ISD::BUILD_VECTOR, dl, NOutVT, &Ops[0], Ops.size());
2947fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem}
2948fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2949fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_SCALAR_TO_VECTOR(SDNode *N) {
2950fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2951ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2952fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
29531396c403897e3d3e04fbf59f6c5fe77cbbab74a6Benjamin Kramer  assert(!N->getOperand(0).getValueType().isVector() &&
29541396c403897e3d3e04fbf59f6c5fe77cbbab74a6Benjamin Kramer         "Input must be a scalar");
2955fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2956fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT OutVT = N->getValueType(0);
2957fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
2958fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  assert(NOutVT.isVector() && "This type must be promoted to a vector type");
2959fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVTElem = NOutVT.getVectorElementType();
2960fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2961fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue Op = DAG.getNode(ISD::ANY_EXTEND, dl, NOutVTElem, N->getOperand(0));
2962fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2963fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  return DAG.getNode(ISD::SCALAR_TO_VECTOR, dl, NOutVT, Op);
2964fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem}
2965fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
2966c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_CONCAT_VECTORS(SDNode *N) {
2967ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
2968c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem
2969c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  EVT OutVT = N->getValueType(0);
2970c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
2971c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  assert(NOutVT.isVector() && "This type must be promoted to a vector type");
2972c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem
2973d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman  EVT InElemTy = OutVT.getVectorElementType();
2974c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  EVT OutElemTy = NOutVT.getVectorElementType();
2975c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem
2976d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman  unsigned NumElem = N->getOperand(0).getValueType().getVectorNumElements();
2977c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  unsigned NumOutElem = NOutVT.getVectorNumElements();
2978d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman  unsigned NumOperands = N->getNumOperands();
2979d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman  assert(NumElem * NumOperands == NumOutElem &&
2980d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman         "Unexpected number of elements");
2981c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem
2982c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  // Take the elements from the first vector.
2983c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  SmallVector<SDValue, 8> Ops(NumOutElem);
2984d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman  for (unsigned i = 0; i < NumOperands; ++i) {
2985d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman    SDValue Op = N->getOperand(i);
2986d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman    for (unsigned j = 0; j < NumElem; ++j) {
2987d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman      SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl,
2988425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard                                InElemTy, Op, DAG.getConstant(j,
2989425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard                                              TLI.getVectorIdxTy()));
2990d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman      Ops[i * NumElem + j] = DAG.getNode(ISD::ANY_EXTEND, dl, OutElemTy, Ext);
2991d577df8e5ada3f4f97fa90bdc46c6f9b1db1dee1Eli Friedman    }
2992c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  }
2993c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem
2994c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem  return DAG.getNode(ISD::BUILD_VECTOR, dl, NOutVT, &Ops[0], Ops.size());
2995c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem}
2996c56d65f63cd632ef57d9f80b4539f15a2f937364Nadav Rotem
2997fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntRes_INSERT_VECTOR_ELT(SDNode *N) {
2998fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT OutVT = N->getValueType(0);
2999fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVT = TLI.getTypeToTransformTo(*DAG.getContext(), OutVT);
3000fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  assert(NOutVT.isVector() && "This type must be promoted to a vector type");
3001fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3002fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT NOutVTElem = NOutVT.getVectorElementType();
3003fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3004ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
3005811ad8690b798cdcbd9d80a2b6a404145222b9a9Nadav Rotem  SDValue V0 = GetPromotedInteger(N->getOperand(0));
3006fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3007fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue ConvElem = DAG.getNode(ISD::ANY_EXTEND, dl,
3008fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    NOutVTElem, N->getOperand(1));
3009811ad8690b798cdcbd9d80a2b6a404145222b9a9Nadav Rotem  return DAG.getNode(ISD::INSERT_VECTOR_ELT, dl, NOutVT,
30102ff4bc615584fa9f32e64959767d64f2cb09fb99Nadav Rotem    V0, ConvElem, N->getOperand(2));
3011fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem}
3012fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3013fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntOp_EXTRACT_VECTOR_ELT(SDNode *N) {
3014ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
3015fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue V0 = GetPromotedInteger(N->getOperand(0));
3016425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard  SDValue V1 = DAG.getZExtOrTrunc(N->getOperand(1), dl, TLI.getVectorIdxTy());
3017fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SDValue Ext = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl,
3018fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    V0->getValueType(0).getScalarType(), V0, V1);
3019fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
30200eba4fe292a0bb343da5fb2667850a39459cef0bNadav Rotem  // EXTRACT_VECTOR_ELT can return types which are wider than the incoming
3021a3c42f3d4e5d14c8f4fb9bb123e7759c425d041bNadav Rotem  // element types. If this is the case then we need to expand the outgoing
3022a3c42f3d4e5d14c8f4fb9bb123e7759c425d041bNadav Rotem  // value and not truncate it.
3023a3c42f3d4e5d14c8f4fb9bb123e7759c425d041bNadav Rotem  return DAG.getAnyExtOrTrunc(Ext, dl, N->getValueType(0));
3024fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem}
3025fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3026fc3623bc50aa9e2a56736775edbd3ae919565351Nadav RotemSDValue DAGTypeLegalizer::PromoteIntOp_CONCAT_VECTORS(SDNode *N) {
3027ac6d9bec671252dd1e596fa71180ff6b39d06b5dAndrew Trick  SDLoc dl(N);
3028811ad8690b798cdcbd9d80a2b6a404145222b9a9Nadav Rotem  unsigned NumElems = N->getNumOperands();
3029fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3030fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  EVT RetSclrTy = N->getValueType(0).getVectorElementType();
3031fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3032fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  SmallVector<SDValue, 8> NewOps;
3033811ad8690b798cdcbd9d80a2b6a404145222b9a9Nadav Rotem  NewOps.reserve(NumElems);
3034fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3035fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  // For each incoming vector
3036811ad8690b798cdcbd9d80a2b6a404145222b9a9Nadav Rotem  for (unsigned VecIdx = 0; VecIdx != NumElems; ++VecIdx) {
3037fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    SDValue Incoming = GetPromotedInteger(N->getOperand(VecIdx));
3038fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    EVT SclrTy = Incoming->getValueType(0).getVectorElementType();
3039fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    unsigned NumElem = Incoming->getValueType(0).getVectorNumElements();
3040fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3041fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    for (unsigned i=0; i<NumElem; ++i) {
3042fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem      // Extract element from incoming vector
3043fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem      SDValue Ex = DAG.getNode(ISD::EXTRACT_VECTOR_ELT, dl, SclrTy,
3044425b76c2314ff7ee7ad507011bdda1988ae481efTom Stellard      Incoming, DAG.getConstant(i, TLI.getVectorIdxTy()));
3045fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem      SDValue Tr = DAG.getNode(ISD::TRUNCATE, dl, RetSclrTy, Ex);
3046fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem      NewOps.push_back(Tr);
3047fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    }
3048fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  }
3049fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem
3050fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  return DAG.getNode(ISD::BUILD_VECTOR, dl,  N->getValueType(0),
3051fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem    &NewOps[0], NewOps.size());
3052fc3623bc50aa9e2a56736775edbd3ae919565351Nadav Rotem  }
3053