AutoUpgrade.cpp revision de49f360ec4780acb382a3ae923d1716fdb0dc03
16994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//===-- AutoUpgrade.cpp - Implement auto-upgrade helper functions ---------===//
26994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//
36994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//                     The LLVM Compiler Infrastructure
46994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//
54ee451de366474b9c228b4e5fa573795a715216dChris Lattner// This file is distributed under the University of Illinois Open Source
64ee451de366474b9c228b4e5fa573795a715216dChris Lattner// License. See LICENSE.TXT for details.
76994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//
86994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//===----------------------------------------------------------------------===//
96994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//
106994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// This file implements the auto-upgrade helper functions
116994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//
126994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth//===----------------------------------------------------------------------===//
136994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
146994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth#include "llvm/AutoUpgrade.h"
15d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson#include "llvm/Constants.h"
166994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth#include "llvm/Function.h"
17f81b57694b3c34a79b1464ffd21e6768c8d22662Owen Anderson#include "llvm/LLVMContext.h"
186994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth#include "llvm/Module.h"
19e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel#include "llvm/IntrinsicInst.h"
2058d74910c6b82e622ecbb57d6644d48fec5a5c0fChris Lattner#include "llvm/ADT/SmallVector.h"
21bb6eabf4f5b518a333ab4cedce910962ff935e3aGabor Greif#include "llvm/Support/CallSite.h"
22c25e7581b9b8088910da31702d4ca21c4734c6d7Torok Edwin#include "llvm/Support/ErrorHandling.h"
236d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher#include "llvm/Support/IRBuilder.h"
24ae9f3a3b7c915f725aef5a7250e88eaeddda03c6Anton Korobeynikov#include <cstring>
256994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruthusing namespace llvm;
266994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
276994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
28f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Chengstatic bool UpgradeIntrinsicFunction1(Function *F, Function *&NewFn) {
296994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  assert(F && "Illegal to upgrade a non-existent Function.");
306994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
316994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  // Get the Function's name.
326994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  const std::string& Name = F->getName();
336994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
346994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  // Convenience
356994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  const FunctionType *FTy = F->getFunctionType();
366994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
376994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  // Quickly eliminate it, if it's not a candidate.
386994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  if (Name.length() <= 8 || Name[0] != 'l' || Name[1] != 'l' ||
396994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      Name[2] != 'v' || Name[3] != 'm' || Name[4] != '.')
40f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng    return false;
416994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
426994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  Module *M = F->getParent();
436994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  switch (Name[5]) {
446994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  default: break;
4528873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang  case 'a':
46e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang    // This upgrades the llvm.atomic.lcs, llvm.atomic.las, llvm.atomic.lss,
47e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang    // and atomics with default address spaces to their new names to their new
48e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang    // function name (e.g. llvm.atomic.add.i32 => llvm.atomic.add.i32.p0i32)
49e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang    if (Name.compare(5,7,"atomic.",7) == 0) {
5028873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang      if (Name.compare(12,3,"lcs",3) == 0) {
5128873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        std::string::size_type delim = Name.find('.',12);
52e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        F->setName("llvm.atomic.cmp.swap" + Name.substr(delim) +
53e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang                   ".p0" + Name.substr(delim+1));
5428873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        NewFn = F;
5528873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        return true;
5628873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang      }
5728873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang      else if (Name.compare(12,3,"las",3) == 0) {
5828873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        std::string::size_type delim = Name.find('.',12);
59e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        F->setName("llvm.atomic.load.add"+Name.substr(delim)
60e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang                   + ".p0" + Name.substr(delim+1));
6128873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        NewFn = F;
6228873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        return true;
6328873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang      }
6428873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang      else if (Name.compare(12,3,"lss",3) == 0) {
6528873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        std::string::size_type delim = Name.find('.',12);
66e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        F->setName("llvm.atomic.load.sub"+Name.substr(delim)
67e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang                   + ".p0" + Name.substr(delim+1));
68e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        NewFn = F;
69e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        return true;
70e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang      }
71e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang      else if (Name.rfind(".p") == std::string::npos) {
72e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        // We don't have an address space qualifier so this has be upgraded
73e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        // to the new name.  Copy the type name at the end of the intrinsic
74e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        // and add to it
75e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        std::string::size_type delim = Name.find_last_of('.');
76e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        assert(delim != std::string::npos && "can not find type");
77e3b3a7241c01f26613694e53b26b01abf764ddfcMon P Wang        F->setName(Name + ".p0" + Name.substr(delim+1));
7828873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        NewFn = F;
7928873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang        return true;
8028873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang      }
81b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson    } else if (Name.compare(5, 9, "arm.neon.", 9) == 0) {
8204d6c289ab28114af5471c4dc38cbf7b7127d3c3Bob Wilson      if (((Name.compare(14, 5, "vmovl", 5) == 0 ||
8304d6c289ab28114af5471c4dc38cbf7b7127d3c3Bob Wilson            Name.compare(14, 5, "vaddl", 5) == 0 ||
84eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vsubl", 5) == 0 ||
85eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vaddw", 5) == 0 ||
86eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vsubw", 5) == 0 ||
87eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vmull", 5) == 0 ||
88d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson            Name.compare(14, 5, "vmlal", 5) == 0 ||
89eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vmlsl", 5) == 0 ||
90eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vabdl", 5) == 0 ||
91eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(14, 5, "vabal", 5) == 0) &&
92d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson           (Name.compare(19, 2, "s.", 2) == 0 ||
93d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson            Name.compare(19, 2, "u.", 2) == 0)) ||
94d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson
95eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson          (Name.compare(14, 4, "vaba", 4) == 0 &&
96eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson           (Name.compare(18, 2, "s.", 2) == 0 ||
97eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson            Name.compare(18, 2, "u.", 2) == 0)) ||
98eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson
99973a074345add36c046c0f0bfea0156a532ab479Bob Wilson          (Name.compare(14, 6, "vmovn.", 6) == 0)) {
10004d6c289ab28114af5471c4dc38cbf7b7127d3c3Bob Wilson
101b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        // Calls to these are transformed into IR without intrinsics.
102b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        NewFn = 0;
103b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        return true;
104b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      }
1057a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      // Old versions of NEON ld/st intrinsics are missing alignment arguments.
1067a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      bool isVLd = (Name.compare(14, 3, "vld", 3) == 0);
1077a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      bool isVSt = (Name.compare(14, 3, "vst", 3) == 0);
1087a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      if (isVLd || isVSt) {
1097a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        unsigned NumVecs = Name.at(17) - '0';
1107a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        if (NumVecs == 0 || NumVecs > 4)
1117a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson          return false;
1127a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        bool isLaneOp = (Name.compare(18, 5, "lane.", 5) == 0);
1137a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        if (!isLaneOp && Name.at(18) != '.')
1147a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson          return false;
1157a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        unsigned ExpectedArgs = 2; // for the address and alignment
1167a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        if (isVSt || isLaneOp)
1177a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson          ExpectedArgs += NumVecs;
1187a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        if (isLaneOp)
1197a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson          ExpectedArgs += 1; // for the lane number
1207a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        unsigned NumP = FTy->getNumParams();
1217a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        if (NumP != ExpectedArgs - 1)
1227a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson          return false;
1237a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson
1247a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        // Change the name of the old (bad) intrinsic, because
1257a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        // its type is incorrect, but we cannot overload that name.
1267a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        F->setName("");
1277a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson
1287a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        // One argument is missing: add the alignment argument.
1297a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        std::vector<const Type*> NewParams;
1307a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        for (unsigned p = 0; p < NumP; ++p)
1317a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson          NewParams.push_back(FTy->getParamType(p));
1327a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        NewParams.push_back(Type::getInt32Ty(F->getContext()));
1337a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        FunctionType *NewFTy = FunctionType::get(FTy->getReturnType(),
1347a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson                                                 NewParams, false);
1357a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        NewFn = cast<Function>(M->getOrInsertFunction(Name, NewFTy));
1367a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson        return true;
1377a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      }
13828873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang    }
13928873106309db515d58889a4c4fa3e0a92d1b60eMon P Wang    break;
1406994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  case 'b':
1416994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  This upgrades the name of the llvm.bswap intrinsic function to only use
1426994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  a single type name for overloading. We only care about the old format
1436994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  'llvm.bswap.i*.i*', so check for 'bswap.' and then for there being
1446994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  a '.' after 'bswap.'
1456994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    if (Name.compare(5,6,"bswap.",6) == 0) {
1466994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      std::string::size_type delim = Name.find('.',11);
1476994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
1486994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      if (delim != std::string::npos) {
1496994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        //  Construct the new name as 'llvm.bswap' + '.i*'
1506994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        F->setName(Name.substr(0,10)+Name.substr(delim));
151f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        NewFn = F;
152f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        return true;
1536994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      }
1546994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    }
1556994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    break;
1566994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
1576994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  case 'c':
1586994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  We only want to fix the 'llvm.ct*' intrinsics which do not have the
1596994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  correct return type, so we check for the name, and then check if the
1606994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  return type does not match the parameter type.
1616994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    if ( (Name.compare(5,5,"ctpop",5) == 0 ||
1626994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth          Name.compare(5,4,"ctlz",4) == 0 ||
1636994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth          Name.compare(5,4,"cttz",4) == 0) &&
1646994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        FTy->getReturnType() != FTy->getParamType(0)) {
1656994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  We first need to change the name of the old (bad) intrinsic, because
1666994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  its type is incorrect, but we cannot overload that name. We
1676994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  arbitrarily unique it here allowing us to construct a correctly named
1686994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  and typed function below.
1696994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      F->setName("");
1706994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
1716994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  Now construct the new intrinsic with the correct name and type. We
1726994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  leave the old function around in order to query its type, whatever it
1736994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  may be, and correctly convert up to the new type.
174f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      NewFn = cast<Function>(M->getOrInsertFunction(Name,
175f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    FTy->getParamType(0),
176f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    FTy->getParamType(0),
177f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    (Type *)0));
178f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      return true;
1796994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    }
1806994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    break;
1816994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
182b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands  case 'e':
183b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    //  The old llvm.eh.selector.i32 is equivalent to the new llvm.eh.selector.
184b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    if (Name.compare("llvm.eh.selector.i32") == 0) {
185b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      F->setName("llvm.eh.selector");
186b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      NewFn = F;
187b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      return true;
188b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    }
189b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    //  The old llvm.eh.typeid.for.i32 is equivalent to llvm.eh.typeid.for.
190b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    if (Name.compare("llvm.eh.typeid.for.i32") == 0) {
191b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      F->setName("llvm.eh.typeid.for");
192b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      NewFn = F;
193b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      return true;
194b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    }
195b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    //  Convert the old llvm.eh.selector.i64 to a call to llvm.eh.selector.
196b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    if (Name.compare("llvm.eh.selector.i64") == 0) {
197b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      NewFn = Intrinsic::getDeclaration(M, Intrinsic::eh_selector);
198b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      return true;
199b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    }
200b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    //  Convert the old llvm.eh.typeid.for.i64 to a call to llvm.eh.typeid.for.
201b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    if (Name.compare("llvm.eh.typeid.for.i64") == 0) {
202b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      NewFn = Intrinsic::getDeclaration(M, Intrinsic::eh_typeid_for);
203b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      return true;
204b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    }
205b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    break;
206b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands
20720adc9dc4650313f017b27d9818eb2176238113dMon P Wang  case 'm': {
20820adc9dc4650313f017b27d9818eb2176238113dMon P Wang    // This upgrades the llvm.memcpy, llvm.memmove, and llvm.memset to the
20920adc9dc4650313f017b27d9818eb2176238113dMon P Wang    // new format that allows overloading the pointer for different address
21020adc9dc4650313f017b27d9818eb2176238113dMon P Wang    // space (e.g., llvm.memcpy.i16 => llvm.memcpy.p0i8.p0i8.i16)
21120adc9dc4650313f017b27d9818eb2176238113dMon P Wang    const char* NewFnName = NULL;
21220adc9dc4650313f017b27d9818eb2176238113dMon P Wang    if (Name.compare(5,8,"memcpy.i",8) == 0) {
21320adc9dc4650313f017b27d9818eb2176238113dMon P Wang      if (Name[13] == '8')
21420adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memcpy.p0i8.p0i8.i8";
21520adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(13,2,"16") == 0)
21620adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memcpy.p0i8.p0i8.i16";
21720adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(13,2,"32") == 0)
21820adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memcpy.p0i8.p0i8.i32";
21920adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(13,2,"64") == 0)
22020adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memcpy.p0i8.p0i8.i64";
22120adc9dc4650313f017b27d9818eb2176238113dMon P Wang    } else if (Name.compare(5,9,"memmove.i",9) == 0) {
22220adc9dc4650313f017b27d9818eb2176238113dMon P Wang      if (Name[14] == '8')
22320adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memmove.p0i8.p0i8.i8";
22420adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(14,2,"16") == 0)
22520adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memmove.p0i8.p0i8.i16";
22620adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(14,2,"32") == 0)
22720adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memmove.p0i8.p0i8.i32";
22820adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(14,2,"64") == 0)
22920adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memmove.p0i8.p0i8.i64";
23020adc9dc4650313f017b27d9818eb2176238113dMon P Wang    }
23120adc9dc4650313f017b27d9818eb2176238113dMon P Wang    else if (Name.compare(5,8,"memset.i",8) == 0) {
23220adc9dc4650313f017b27d9818eb2176238113dMon P Wang      if (Name[13] == '8')
23320adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memset.p0i8.i8";
23420adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(13,2,"16") == 0)
23520adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memset.p0i8.i16";
23620adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(13,2,"32") == 0)
23720adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memset.p0i8.i32";
23820adc9dc4650313f017b27d9818eb2176238113dMon P Wang      else if (Name.compare(13,2,"64") == 0)
23920adc9dc4650313f017b27d9818eb2176238113dMon P Wang        NewFnName = "llvm.memset.p0i8.i64";
24020adc9dc4650313f017b27d9818eb2176238113dMon P Wang    }
24120adc9dc4650313f017b27d9818eb2176238113dMon P Wang    if (NewFnName) {
24220adc9dc4650313f017b27d9818eb2176238113dMon P Wang      NewFn = cast<Function>(M->getOrInsertFunction(NewFnName,
24320adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            FTy->getReturnType(),
24420adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            FTy->getParamType(0),
24520adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            FTy->getParamType(1),
24620adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            FTy->getParamType(2),
24720adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            FTy->getParamType(3),
24820adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            Type::getInt1Ty(F->getContext()),
24920adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                            (Type *)0));
25020adc9dc4650313f017b27d9818eb2176238113dMon P Wang      return true;
25120adc9dc4650313f017b27d9818eb2176238113dMon P Wang    }
25220adc9dc4650313f017b27d9818eb2176238113dMon P Wang    break;
25320adc9dc4650313f017b27d9818eb2176238113dMon P Wang  }
2546994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  case 'p':
2556994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  This upgrades the llvm.part.select overloaded intrinsic names to only
2566994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  use one type specifier in the name. We only care about the old format
2576994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  'llvm.part.select.i*.i*', and solve as above with bswap.
2586994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    if (Name.compare(5,12,"part.select.",12) == 0) {
2596994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      std::string::size_type delim = Name.find('.',17);
2606994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
2616994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      if (delim != std::string::npos) {
2626994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        //  Construct a new name as 'llvm.part.select' + '.i*'
2636994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        F->setName(Name.substr(0,16)+Name.substr(delim));
264f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        NewFn = F;
265f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        return true;
2666994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      }
2676994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      break;
2686994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    }
2696994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
2706994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  This upgrades the llvm.part.set intrinsics similarly as above, however
2716994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  we care about 'llvm.part.set.i*.i*.i*', but only the first two types
2726994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  must match. There is an additional type specifier after these two
2736994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  matching types that we must retain when upgrading.  Thus, we require
2746994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  finding 2 periods, not just one, after the intrinsic name.
2756994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    if (Name.compare(5,9,"part.set.",9) == 0) {
2766994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      std::string::size_type delim = Name.find('.',14);
2776994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
2786994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      if (delim != std::string::npos &&
2796994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth          Name.find('.',delim+1) != std::string::npos) {
2806994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        //  Construct a new name as 'llvm.part.select' + '.i*.i*'
2816994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        F->setName(Name.substr(0,13)+Name.substr(delim));
282f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        NewFn = F;
283f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        return true;
2846994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      }
2856994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      break;
2866994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    }
2876994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
2886994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    break;
289d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case 'x':
290d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    // This fixes all MMX shift intrinsic instructions to take a
291d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    // v1i64 instead of a v2i32 as the second parameter.
292d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    if (Name.compare(5,10,"x86.mmx.ps",10) == 0 &&
293d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson        (Name.compare(13,4,"psll", 4) == 0 ||
294d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson         Name.compare(13,4,"psra", 4) == 0 ||
29522b942aa4df824adbd3f6eaede53abe451f616e9Evan Cheng         Name.compare(13,4,"psrl", 4) == 0) && Name[17] != 'i') {
296d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
297f81b57694b3c34a79b1464ffd21e6768c8d22662Owen Anderson      const llvm::Type *VT =
2981d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson                    VectorType::get(IntegerType::get(FTy->getContext(), 64), 1);
299d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
300d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      // We don't have to do anything if the parameter already has
301d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      // the correct type.
302d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      if (FTy->getParamType(1) == VT)
303d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson        break;
304d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
305d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  We first need to change the name of the old (bad) intrinsic, because
306d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  its type is incorrect, but we cannot overload that name. We
307d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  arbitrarily unique it here allowing us to construct a correctly named
308d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  and typed function below.
309d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      F->setName("");
310d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
311d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      assert(FTy->getNumParams() == 2 && "MMX shift intrinsics take 2 args!");
312d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
313d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  Now construct the new intrinsic with the correct name and type. We
314d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  leave the old function around in order to query its type, whatever it
315d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  may be, and correctly convert up to the new type.
316f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      NewFn = cast<Function>(M->getOrInsertFunction(Name,
317f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    FTy->getReturnType(),
318f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    FTy->getParamType(0),
319f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    VT,
320f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng                                                    (Type *)0));
321f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      return true;
3224797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng    } else if (Name.compare(5,17,"x86.sse2.loadh.pd",17) == 0 ||
3234797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng               Name.compare(5,17,"x86.sse2.loadl.pd",17) == 0 ||
324e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng               Name.compare(5,16,"x86.sse2.movl.dq",16) == 0 ||
325e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng               Name.compare(5,15,"x86.sse2.movs.d",15) == 0 ||
326e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng               Name.compare(5,16,"x86.sse2.shuf.pd",16) == 0 ||
327e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng               Name.compare(5,18,"x86.sse2.unpckh.pd",18) == 0 ||
328a31593901de573813d1d8e7884a152011641a713Evan Cheng               Name.compare(5,18,"x86.sse2.unpckl.pd",18) == 0 ||
329a31593901de573813d1d8e7884a152011641a713Evan Cheng               Name.compare(5,20,"x86.sse2.punpckh.qdq",20) == 0 ||
330a31593901de573813d1d8e7884a152011641a713Evan Cheng               Name.compare(5,20,"x86.sse2.punpckl.qdq",20) == 0) {
3314797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng      // Calls to these intrinsics are transformed into ShuffleVector's.
332f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      NewFn = 0;
333f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      return true;
3348258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher    } else if (Name.compare(5, 16, "x86.sse41.pmulld", 16) == 0) {
3358258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      // Calls to these intrinsics are transformed into vector multiplies.
3368258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      NewFn = 0;
3378258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      return true;
3386d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher    } else if (Name.compare(5, 18, "x86.ssse3.palign.r", 18) == 0 ||
3396d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher               Name.compare(5, 22, "x86.ssse3.palign.r.128", 22) == 0) {
3406d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // Calls to these intrinsics are transformed into vector shuffles, shifts,
3416d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // or 0.
3426d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      NewFn = 0;
3436d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      return true;
344d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    }
345f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng
346d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    break;
3476994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  }
3486994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
3496994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  //  This may not belong here. This function is effectively being overloaded
3506994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  //  to both detect an intrinsic which needs upgrading, and to provide the
3516994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  //  upgraded form of the intrinsic. We should perhaps have two separate
3526994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  //  functions for this.
353f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  return false;
3546994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth}
3556994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
356f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Chengbool llvm::UpgradeIntrinsicFunction(Function *F, Function *&NewFn) {
357f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  NewFn = 0;
358f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  bool Upgraded = UpgradeIntrinsicFunction1(F, NewFn);
359a3355ffb3d30d19d226bbb75707991c60f236e37Duncan Sands
360a3355ffb3d30d19d226bbb75707991c60f236e37Duncan Sands  // Upgrade intrinsic attributes.  This does not change the function.
361f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  if (NewFn)
362f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng    F = NewFn;
36349de98214b82fefeb8f16efbf8cdd8813a85469bDale Johannesen  if (unsigned id = F->getIntrinsicID())
3640598866c052147c31b808391f58434ce3dbfb838Devang Patel    F->setAttributes(Intrinsic::getAttributes((Intrinsic::ID)id));
365a3355ffb3d30d19d226bbb75707991c60f236e37Duncan Sands  return Upgraded;
366a3355ffb3d30d19d226bbb75707991c60f236e37Duncan Sands}
367a3355ffb3d30d19d226bbb75707991c60f236e37Duncan Sands
368de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendlingbool llvm::UpgradeGlobalVariable(GlobalVariable *GV) {
369de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  const std::string &Name = GV->getName();
370de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling
371de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  // We are only upgrading one symbol here. If we upgrade more, we will want to
372de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  // perform some sort of short-circuiting like in the
373de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  // "UpgradeIntrinsicFunction1" function.
374de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  if (Name == ".llvm.eh.catch.all.value") {
375de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling    GV->setName("llvm.eh.catch.all.value");
376de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling    return true;
377de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  }
378de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling
379de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling  return false;
380de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling}
381de49f360ec4780acb382a3ae923d1716fdb0dc03Bill Wendling
382d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson/// ExtendNEONArgs - For NEON "long" and "wide" operations, where the results
383d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson/// have vector elements twice as big as one or both source operands, do the
384d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson/// sign- or zero-extension that used to be handled by intrinsics.  The
385d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson/// extended values are returned via V0 and V1.
386d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilsonstatic void ExtendNEONArgs(CallInst *CI, Value *Arg0, Value *Arg1,
387d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson                           Value *&V0, Value *&V1) {
388d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  Function *F = CI->getCalledFunction();
389d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  const std::string& Name = F->getName();
390d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  bool isLong = (Name.at(18) == 'l');
391d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  bool isSigned = (Name.at(19) == 's');
392d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson
393d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  if (isSigned) {
394d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson    if (isLong)
395d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      V0 = new SExtInst(Arg0, CI->getType(), "", CI);
396d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson    else
397d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      V0 = Arg0;
398d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson    V1 = new SExtInst(Arg1, CI->getType(), "", CI);
399d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  } else {
400d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson    if (isLong)
401d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      V0 = new ZExtInst(Arg0, CI->getType(), "", CI);
402d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson    else
403d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      V0 = Arg0;
404d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson    V1 = new ZExtInst(Arg1, CI->getType(), "", CI);
405d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson  }
406d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson}
407d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson
408eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson/// CallVABD - As part of expanding a call to one of the old NEON vabdl, vaba,
409eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson/// or vabal intrinsics, construct a call to a vabd intrinsic.  Examine the
410eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson/// name of the old intrinsic to determine whether to use a signed or unsigned
411eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson/// vabd intrinsic.  Get the type from the old call instruction, adjusted for
412eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson/// half-size vector elements if the old intrinsic was vabdl or vabal.
413eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilsonstatic Instruction *CallVABD(CallInst *CI, Value *Arg0, Value *Arg1) {
414eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  Function *F = CI->getCalledFunction();
415eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  const std::string& Name = F->getName();
416eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  bool isLong = (Name.at(18) == 'l');
417eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  bool isSigned = (Name.at(isLong ? 19 : 18) == 's');
418eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson
419eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  Intrinsic::ID intID;
420eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  if (isSigned)
421eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson    intID = Intrinsic::arm_neon_vabds;
422eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  else
423eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson    intID = Intrinsic::arm_neon_vabdu;
424eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson
425eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  const Type *Ty = CI->getType();
426eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  if (isLong)
427eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson    Ty = VectorType::getTruncatedElementVectorType(cast<const VectorType>(Ty));
428eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson
429eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  Function *VABD = Intrinsic::getDeclaration(F->getParent(), intID, &Ty, 1);
430eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  Value *Operands[2];
431eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  Operands[0] = Arg0;
432eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  Operands[1] = Arg1;
433eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  return CallInst::Create(VABD, Operands, Operands+2,
434eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson                          "upgraded."+CI->getName(), CI);
435eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson}
436eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson
4376994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// UpgradeIntrinsicCall - Upgrade a call to an old intrinsic to be a call the
4386994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// upgraded intrinsic. All argument and return casting must be provided in
4396994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// order to seamlessly integrate with existing context.
4406994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruthvoid llvm::UpgradeIntrinsicCall(CallInst *CI, Function *NewFn) {
4416994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  Function *F = CI->getCalledFunction();
4421d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson  LLVMContext &C = CI->getContext();
443bb6eabf4f5b518a333ab4cedce910962ff935e3aGabor Greif  ImmutableCallSite CS(CI);
444bb6eabf4f5b518a333ab4cedce910962ff935e3aGabor Greif
4456994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  assert(F && "CallInst has no function associated with it.");
446f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng
447f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  if (!NewFn) {
448b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson    // Get the Function's name.
449b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson    const std::string& Name = F->getName();
450b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson
451b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson    // Upgrade ARM NEON intrinsics.
452b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson    if (Name.compare(5, 9, "arm.neon.", 9) == 0) {
453b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      Instruction *NewI;
454d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      Value *V0, *V1;
455b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      if (Name.compare(14, 7, "vmovls.", 7) == 0) {
456b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        NewI = new SExtInst(CI->getArgOperand(0), CI->getType(),
457b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson                            "upgraded." + CI->getName(), CI);
458b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      } else if (Name.compare(14, 7, "vmovlu.", 7) == 0) {
459b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        NewI = new ZExtInst(CI->getArgOperand(0), CI->getType(),
460b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson                            "upgraded." + CI->getName(), CI);
461d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      } else if (Name.compare(14, 4, "vadd", 4) == 0) {
462d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        ExtendNEONArgs(CI, CI->getArgOperand(0), CI->getArgOperand(1), V0, V1);
463d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        NewI = BinaryOperator::CreateAdd(V0, V1, "upgraded."+CI->getName(), CI);
464d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      } else if (Name.compare(14, 4, "vsub", 4) == 0) {
465d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        ExtendNEONArgs(CI, CI->getArgOperand(0), CI->getArgOperand(1), V0, V1);
466d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        NewI = BinaryOperator::CreateSub(V0, V1,"upgraded."+CI->getName(),CI);
467d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      } else if (Name.compare(14, 4, "vmul", 4) == 0) {
468d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        ExtendNEONArgs(CI, CI->getArgOperand(0), CI->getArgOperand(1), V0, V1);
469d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        NewI = BinaryOperator::CreateMul(V0, V1,"upgraded."+CI->getName(),CI);
470d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      } else if (Name.compare(14, 4, "vmla", 4) == 0) {
471d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        ExtendNEONArgs(CI, CI->getArgOperand(1), CI->getArgOperand(2), V0, V1);
472d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        Instruction *MulI = BinaryOperator::CreateMul(V0, V1, "", CI);
473d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        NewI = BinaryOperator::CreateAdd(CI->getArgOperand(0), MulI,
474d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson                                         "upgraded."+CI->getName(), CI);
475d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson      } else if (Name.compare(14, 4, "vmls", 4) == 0) {
476d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        ExtendNEONArgs(CI, CI->getArgOperand(1), CI->getArgOperand(2), V0, V1);
477d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        Instruction *MulI = BinaryOperator::CreateMul(V0, V1, "", CI);
478d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson        NewI = BinaryOperator::CreateSub(CI->getArgOperand(0), MulI,
479d0b69cf1198dadbb7bdfc385334b67f60f756539Bob Wilson                                         "upgraded."+CI->getName(), CI);
480eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson      } else if (Name.compare(14, 4, "vabd", 4) == 0) {
481eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson        NewI = CallVABD(CI, CI->getArgOperand(0), CI->getArgOperand(1));
482eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson        NewI = new ZExtInst(NewI, CI->getType(), "upgraded."+CI->getName(), CI);
483eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson      } else if (Name.compare(14, 4, "vaba", 4) == 0) {
484eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson        NewI = CallVABD(CI, CI->getArgOperand(1), CI->getArgOperand(2));
485eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson        if (Name.at(18) == 'l')
486eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson          NewI = new ZExtInst(NewI, CI->getType(), "", CI);
487eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson        NewI = BinaryOperator::CreateAdd(CI->getArgOperand(0), NewI,
488eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson                                         "upgraded."+CI->getName(), CI);
489973a074345add36c046c0f0bfea0156a532ab479Bob Wilson      } else if (Name.compare(14, 6, "vmovn.", 6) == 0) {
490973a074345add36c046c0f0bfea0156a532ab479Bob Wilson        NewI = new TruncInst(CI->getArgOperand(0), CI->getType(),
491973a074345add36c046c0f0bfea0156a532ab479Bob Wilson                             "upgraded." + CI->getName(), CI);
492b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      } else {
493b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        llvm_unreachable("Unknown arm.neon function for CallInst upgrade.");
494b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      }
495b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      // Replace any uses of the old CallInst.
496b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      if (!CI->use_empty())
497b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson        CI->replaceAllUsesWith(NewI);
498b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      CI->eraseFromParent();
499b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson      return;
500b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson    }
501b31a11b466281b7e01cfde007b2041eefa2341e4Bob Wilson
5024797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng    bool isLoadH = false, isLoadL = false, isMovL = false;
503e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng    bool isMovSD = false, isShufPD = false;
504e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng    bool isUnpckhPD = false, isUnpcklPD = false;
505a31593901de573813d1d8e7884a152011641a713Evan Cheng    bool isPunpckhQPD = false, isPunpcklQPD = false;
50603d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    if (F->getName() == "llvm.x86.sse2.loadh.pd")
5074797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng      isLoadH = true;
50803d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() == "llvm.x86.sse2.loadl.pd")
5094797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng      isLoadL = true;
51003d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() == "llvm.x86.sse2.movl.dq")
5114797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng      isMovL = true;
51203d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() == "llvm.x86.sse2.movs.d")
513e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      isMovSD = true;
51403d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() == "llvm.x86.sse2.shuf.pd")
515e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      isShufPD = true;
51603d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() == "llvm.x86.sse2.unpckh.pd")
517e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      isUnpckhPD = true;
51803d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() == "llvm.x86.sse2.unpckl.pd")
519e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      isUnpcklPD = true;
52003d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() ==  "llvm.x86.sse2.punpckh.qdq")
521a31593901de573813d1d8e7884a152011641a713Evan Cheng      isPunpckhQPD = true;
52203d7651c3652e1f0cc86e79b26585d86818da9cfDaniel Dunbar    else if (F->getName() ==  "llvm.x86.sse2.punpckl.qdq")
523a31593901de573813d1d8e7884a152011641a713Evan Cheng      isPunpcklQPD = true;
5244797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng
525e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng    if (isLoadH || isLoadL || isMovL || isMovSD || isShufPD ||
526a31593901de573813d1d8e7884a152011641a713Evan Cheng        isUnpckhPD || isUnpcklPD || isPunpckhQPD || isPunpcklQPD) {
527f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      std::vector<Constant*> Idxs;
528f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif      Value *Op0 = CI->getArgOperand(0);
529e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      ShuffleVectorInst *SI = NULL;
5304797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng      if (isLoadH || isLoadL) {
5319e9a0d5fc26878e51a58a8b57900fcbf952c2691Owen Anderson        Value *Op1 = UndefValue::get(Op0->getType());
532f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif        Value *Addr = new BitCastInst(CI->getArgOperand(1),
533ac53a0b272452013124bfc70480aea5e41b60f40Duncan Sands                                  Type::getDoublePtrTy(C),
5344797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng                                      "upgraded.", CI);
5354797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Value *Load = new LoadInst(Addr, "upgraded.", false, 8, CI);
5361d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Value *Idx = ConstantInt::get(Type::getInt32Ty(C), 0);
5374797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Op1 = InsertElementInst::Create(Op1, Load, Idx, "upgraded.", CI);
5384797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng
5394797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        if (isLoadH) {
5401d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 0));
5411d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 2));
5424797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        } else {
5431d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 2));
5441d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 1));
5454797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        }
546af7ec975870f92245f1f1484ac80a1e2db6a0afaOwen Anderson        Value *Mask = ConstantVector::get(Idxs);
5474797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        SI = new ShuffleVectorInst(Op0, Op1, Mask, "upgraded.", CI);
548e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      } else if (isMovL) {
5491d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Constant *Zero = ConstantInt::get(Type::getInt32Ty(C), 0);
5504797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Idxs.push_back(Zero);
5514797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Idxs.push_back(Zero);
5524797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Idxs.push_back(Zero);
5534797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Idxs.push_back(Zero);
554af7ec975870f92245f1f1484ac80a1e2db6a0afaOwen Anderson        Value *ZeroV = ConstantVector::get(Idxs);
555f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng
5564797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        Idxs.clear();
5571d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 4));
5581d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 5));
5591d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 2));
5601d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 3));
561af7ec975870f92245f1f1484ac80a1e2db6a0afaOwen Anderson        Value *Mask = ConstantVector::get(Idxs);
5624797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng        SI = new ShuffleVectorInst(ZeroV, Op0, Mask, "upgraded.", CI);
563a31593901de573813d1d8e7884a152011641a713Evan Cheng      } else if (isMovSD ||
564a31593901de573813d1d8e7884a152011641a713Evan Cheng                 isUnpckhPD || isUnpcklPD || isPunpckhQPD || isPunpcklQPD) {
565f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif        Value *Op1 = CI->getArgOperand(1);
566e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng        if (isMovSD) {
5671d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 2));
5681d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 1));
569a31593901de573813d1d8e7884a152011641a713Evan Cheng        } else if (isUnpckhPD || isPunpckhQPD) {
5701d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 1));
5711d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 3));
572e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng        } else {
5731d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 0));
5741d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson          Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), 2));
575e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng        }
576af7ec975870f92245f1f1484ac80a1e2db6a0afaOwen Anderson        Value *Mask = ConstantVector::get(Idxs);
577e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng        SI = new ShuffleVectorInst(Op0, Op1, Mask, "upgraded.", CI);
578e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      } else if (isShufPD) {
579f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif        Value *Op1 = CI->getArgOperand(1);
580a399781289092fcdceb58b21174229f4373c4191Gabor Greif        unsigned MaskVal =
581a399781289092fcdceb58b21174229f4373c4191Gabor Greif                        cast<ConstantInt>(CI->getArgOperand(2))->getZExtValue();
5821d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C), MaskVal & 1));
5831d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson        Idxs.push_back(ConstantInt::get(Type::getInt32Ty(C),
584f81b57694b3c34a79b1464ffd21e6768c8d22662Owen Anderson                                               ((MaskVal >> 1) & 1)+2));
585af7ec975870f92245f1f1484ac80a1e2db6a0afaOwen Anderson        Value *Mask = ConstantVector::get(Idxs);
586e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng        SI = new ShuffleVectorInst(Op0, Op1, Mask, "upgraded.", CI);
5874797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng      }
588f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng
589e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng      assert(SI && "Unexpected!");
590e716bb1c59fe64c663d1d352e0e3889a28dbaca2Evan Cheng
591f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      // Handle any uses of the old CallInst.
592f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      if (!CI->use_empty())
593f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        //  Replace all uses of the old call with the new cast which has the
594f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        //  correct type.
595f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng        CI->replaceAllUsesWith(SI);
596f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng
597f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      //  Clean up the old call now that it has been completely upgraded.
598f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng      CI->eraseFromParent();
5998258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher    } else if (F->getName() == "llvm.x86.sse41.pmulld") {
6008258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      // Upgrade this set of intrinsics into vector multiplies.
601f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif      Instruction *Mul = BinaryOperator::CreateMul(CI->getArgOperand(0),
602f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif                                                   CI->getArgOperand(1),
6038258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher                                                   CI->getName(),
6048258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher                                                   CI);
6058258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      // Fix up all the uses with our new multiply.
6068258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      if (!CI->use_empty())
6078258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher        CI->replaceAllUsesWith(Mul);
6088258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher
6098258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      // Remove upgraded multiply.
6108258d0b4bfd5fe40c29fa19e24c23ba3ac157e23Eric Christopher      CI->eraseFromParent();
6116d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher    } else if (F->getName() == "llvm.x86.ssse3.palign.r") {
612cfbb7d43299a2ce94b83ced4a1cbcfe69e387b52Gabor Greif      Value *Op1 = CI->getArgOperand(0);
613cfbb7d43299a2ce94b83ced4a1cbcfe69e387b52Gabor Greif      Value *Op2 = CI->getArgOperand(1);
614cfbb7d43299a2ce94b83ced4a1cbcfe69e387b52Gabor Greif      Value *Op3 = CI->getArgOperand(2);
6156d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      unsigned shiftVal = cast<ConstantInt>(Op3)->getZExtValue();
6166d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      Value *Rep;
6176d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      IRBuilder<> Builder(C);
6186d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      Builder.SetInsertPoint(CI->getParent(), CI);
6196d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6206d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // If palignr is shifting the pair of input vectors less than 9 bytes,
6216d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // emit a shuffle instruction.
6226d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      if (shiftVal <= 8) {
6236d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *IntTy = Type::getInt32Ty(C);
6246d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *EltTy = Type::getInt8Ty(C);
6256d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *VecTy = VectorType::get(EltTy, 8);
6266d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6276d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op2 = Builder.CreateBitCast(Op2, VecTy);
6286d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op1 = Builder.CreateBitCast(Op1, VecTy);
6296d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6306d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        llvm::SmallVector<llvm::Constant*, 8> Indices;
6316d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        for (unsigned i = 0; i != 8; ++i)
6326d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher          Indices.push_back(ConstantInt::get(IntTy, shiftVal + i));
6336d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6346d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Value *SV = ConstantVector::get(Indices.begin(), Indices.size());
6356d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Builder.CreateShuffleVector(Op2, Op1, SV, "palignr");
6366d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Builder.CreateBitCast(Rep, F->getReturnType());
6376d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      }
6386d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6396d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // If palignr is shifting the pair of input vectors more than 8 but less
6406d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // than 16 bytes, emit a logical right shift of the destination.
6416d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      else if (shiftVal < 16) {
6426d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        // MMX has these as 1 x i64 vectors for some odd optimization reasons.
6436d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *EltTy = Type::getInt64Ty(C);
6446d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *VecTy = VectorType::get(EltTy, 1);
6456d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6466d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op1 = Builder.CreateBitCast(Op1, VecTy, "cast");
6476d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op2 = ConstantInt::get(VecTy, (shiftVal-8) * 8);
6486d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6496d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        // create i32 constant
6506d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Function *I =
6516d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher          Intrinsic::getDeclaration(F->getParent(), Intrinsic::x86_mmx_psrl_q);
6526d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Builder.CreateCall2(I, Op1, Op2, "palignr");
6536d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      }
6546d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6556d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // If palignr is shifting the pair of vectors more than 32 bytes, emit zero.
6566d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      else {
6576d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Constant::getNullValue(F->getReturnType());
6586d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      }
6596d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6606d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // Replace any uses with our new instruction.
6616d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      if (!CI->use_empty())
6626d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        CI->replaceAllUsesWith(Rep);
6636d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6646d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // Remove upgraded instruction.
6656d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      CI->eraseFromParent();
6666d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6676d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher    } else if (F->getName() == "llvm.x86.ssse3.palign.r.128") {
668cfbb7d43299a2ce94b83ced4a1cbcfe69e387b52Gabor Greif      Value *Op1 = CI->getArgOperand(0);
669cfbb7d43299a2ce94b83ced4a1cbcfe69e387b52Gabor Greif      Value *Op2 = CI->getArgOperand(1);
670cfbb7d43299a2ce94b83ced4a1cbcfe69e387b52Gabor Greif      Value *Op3 = CI->getArgOperand(2);
6716d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      unsigned shiftVal = cast<ConstantInt>(Op3)->getZExtValue();
6726d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      Value *Rep;
6736d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      IRBuilder<> Builder(C);
6746d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      Builder.SetInsertPoint(CI->getParent(), CI);
6756d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6766d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // If palignr is shifting the pair of input vectors less than 17 bytes,
6776d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // emit a shuffle instruction.
6786d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      if (shiftVal <= 16) {
6796d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *IntTy = Type::getInt32Ty(C);
6806d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *EltTy = Type::getInt8Ty(C);
6816d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *VecTy = VectorType::get(EltTy, 16);
6826d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6836d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op2 = Builder.CreateBitCast(Op2, VecTy);
6846d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op1 = Builder.CreateBitCast(Op1, VecTy);
6856d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6866d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        llvm::SmallVector<llvm::Constant*, 16> Indices;
6876d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        for (unsigned i = 0; i != 16; ++i)
6886d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher          Indices.push_back(ConstantInt::get(IntTy, shiftVal + i));
6896d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6906d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Value *SV = ConstantVector::get(Indices.begin(), Indices.size());
6916d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Builder.CreateShuffleVector(Op2, Op1, SV, "palignr");
6926d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Builder.CreateBitCast(Rep, F->getReturnType());
6936d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      }
6946d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
6956d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // If palignr is shifting the pair of input vectors more than 16 but less
6966d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // than 32 bytes, emit a logical right shift of the destination.
6976d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      else if (shiftVal < 32) {
6986d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *EltTy = Type::getInt64Ty(C);
6996d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *VecTy = VectorType::get(EltTy, 2);
7006d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        const Type *IntTy = Type::getInt32Ty(C);
7016d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
7026d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op1 = Builder.CreateBitCast(Op1, VecTy, "cast");
7036d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Op2 = ConstantInt::get(IntTy, (shiftVal-16) * 8);
7046d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
7056d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        // create i32 constant
7066d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Function *I =
7076d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher          Intrinsic::getDeclaration(F->getParent(), Intrinsic::x86_sse2_psrl_dq);
7086d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Builder.CreateCall2(I, Op1, Op2, "palignr");
7096d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      }
7106d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
7116d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // If palignr is shifting the pair of vectors more than 32 bytes, emit zero.
7126d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      else {
7136d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        Rep = Constant::getNullValue(F->getReturnType());
7146d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      }
7156d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
7166d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // Replace any uses with our new instruction.
7176d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      if (!CI->use_empty())
7186d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher        CI->replaceAllUsesWith(Rep);
7196d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
7206d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      // Remove upgraded instruction.
7216d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher      CI->eraseFromParent();
7226d972fd087a29dcb063b86e3b81957d9e19ff8f1Eric Christopher
723a5cecd0a130f7ebc4787f8f5b3e8959e41786673Evan Cheng    } else {
724c23197a26f34f559ea9797de51e187087c039c42Torok Edwin      llvm_unreachable("Unknown function for CallInst upgrade.");
725f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng    }
726f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng    return;
727f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  }
728f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng
729051a950000e21935165db56695e35bade668193bGabor Greif  switch (NewFn->getIntrinsicID()) {
730eb0c3d372906df9c61a31651a0ba278034447e94Bob Wilson  default: llvm_unreachable("Unknown function for CallInst upgrade.");
7317a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld1:
7327a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld2:
7337a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld3:
7347a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld4:
7357a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst1:
7367a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst2:
7377a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst3:
7387a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst4:
7397a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld2lane:
7407a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld3lane:
7417a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vld4lane:
7427a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst2lane:
7437a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst3lane:
7447a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  case Intrinsic::arm_neon_vst4lane: {
7457a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    // Add a default alignment argument of 1.
7467a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    SmallVector<Value*, 8> Operands(CS.arg_begin(), CS.arg_end());
7477a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    Operands.push_back(ConstantInt::get(Type::getInt32Ty(C), 1));
7487a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    CallInst *NewCI = CallInst::Create(NewFn, Operands.begin(), Operands.end(),
7497a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson                                       CI->getName(), CI);
7507a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    NewCI->setTailCall(CI->isTailCall());
7517a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    NewCI->setCallingConv(CI->getCallingConv());
7527a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson
7537a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    //  Handle any uses of the old CallInst.
7547a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    if (!CI->use_empty())
7557a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      //  Replace all uses of the old call with the new cast which has the
7567a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      //  correct type.
7577a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson      CI->replaceAllUsesWith(NewCI);
7587a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson
7597a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    //  Clean up the old call now that it has been completely upgraded.
7607a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    CI->eraseFromParent();
7617a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson    break;
7627a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson  }
7637a9ef44b3b4ddd2dd9a7f92fc8b46c5e5bed6a81Bob Wilson
764d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psll_d:
765d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psll_q:
766d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psll_w:
767d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psra_d:
768d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psra_w:
769d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psrl_d:
770d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psrl_q:
771d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  case Intrinsic::x86_mmx_psrl_w: {
77258d74910c6b82e622ecbb57d6644d48fec5a5c0fChris Lattner    Value *Operands[2];
773d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
774f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif    Operands[0] = CI->getArgOperand(0);
775d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
776d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    // Cast the second parameter to the correct type.
777f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif    BitCastInst *BC = new BitCastInst(CI->getArgOperand(1),
778d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson                                      NewFn->getFunctionType()->getParamType(1),
7794797f61657fc32d2e4e806f9f8faadf3fee3e64cEvan Cheng                                      "upgraded.", CI);
78058d74910c6b82e622ecbb57d6644d48fec5a5c0fChris Lattner    Operands[1] = BC;
781d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
782d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    //  Construct a new CallInst
783051a950000e21935165db56695e35bade668193bGabor Greif    CallInst *NewCI = CallInst::Create(NewFn, Operands, Operands+2,
784051a950000e21935165db56695e35bade668193bGabor Greif                                       "upgraded."+CI->getName(), CI);
785d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    NewCI->setTailCall(CI->isTailCall());
786d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    NewCI->setCallingConv(CI->getCallingConv());
787d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
788d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    //  Handle any uses of the old CallInst.
789d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    if (!CI->use_empty())
790d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  Replace all uses of the old call with the new cast which has the
791d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      //  correct type.
792d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson      CI->replaceAllUsesWith(NewCI);
793d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson
794d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    //  Clean up the old call now that it has been completely upgraded.
795d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    CI->eraseFromParent();
796d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson    break;
797d04764a8acabe0b3f0452b3099bc5964ba783884Anders Carlsson  }
7986994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  case Intrinsic::ctlz:
7996994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  case Intrinsic::ctpop:
800051a950000e21935165db56695e35bade668193bGabor Greif  case Intrinsic::cttz: {
801bb6eabf4f5b518a333ab4cedce910962ff935e3aGabor Greif    //  Build a small vector of the original arguments.
802bb6eabf4f5b518a333ab4cedce910962ff935e3aGabor Greif    SmallVector<Value*, 8> Operands(CS.arg_begin(), CS.arg_end());
8036994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8046994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  Construct a new CallInst
805051a950000e21935165db56695e35bade668193bGabor Greif    CallInst *NewCI = CallInst::Create(NewFn, Operands.begin(), Operands.end(),
806051a950000e21935165db56695e35bade668193bGabor Greif                                       "upgraded."+CI->getName(), CI);
8076994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    NewCI->setTailCall(CI->isTailCall());
8086994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    NewCI->setCallingConv(CI->getCallingConv());
8096994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8106994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  Handle any uses of the old CallInst.
8116994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    if (!CI->use_empty()) {
8126994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  Check for sign extend parameter attributes on the return values.
8130598866c052147c31b808391f58434ce3dbfb838Devang Patel      bool SrcSExt = NewFn->getAttributes().paramHasAttr(0, Attribute::SExt);
8140598866c052147c31b808391f58434ce3dbfb838Devang Patel      bool DestSExt = F->getAttributes().paramHasAttr(0, Attribute::SExt);
8156994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8166994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  Construct an appropriate cast from the new return type to the old.
8177cbd8a3e92221437048b484d5ef9c0a22d0f8c58Gabor Greif      CastInst *RetCast = CastInst::Create(
8186994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth                            CastInst::getCastOpcode(NewCI, SrcSExt,
8196994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth                                                    F->getReturnType(),
8206994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth                                                    DestSExt),
8216994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth                            NewCI, F->getReturnType(),
8226994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth                            NewCI->getName(), CI);
8236994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      NewCI->moveBefore(RetCast);
8246994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8256994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  Replace all uses of the old call with the new cast which has the
8266994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      //  correct type.
8276994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      CI->replaceAllUsesWith(RetCast);
8286994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    }
8296994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8306994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    //  Clean up the old call now that it has been completely upgraded.
8316994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    CI->eraseFromParent();
832051a950000e21935165db56695e35bade668193bGabor Greif  }
833051a950000e21935165db56695e35bade668193bGabor Greif  break;
834b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands  case Intrinsic::eh_selector:
835b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands  case Intrinsic::eh_typeid_for: {
836b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    // Only the return type changed.
837bb6eabf4f5b518a333ab4cedce910962ff935e3aGabor Greif    SmallVector<Value*, 8> Operands(CS.arg_begin(), CS.arg_end());
838b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    CallInst *NewCI = CallInst::Create(NewFn, Operands.begin(), Operands.end(),
839b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands                                       "upgraded." + CI->getName(), CI);
840b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    NewCI->setTailCall(CI->isTailCall());
841b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    NewCI->setCallingConv(CI->getCallingConv());
842b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands
843b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    //  Handle any uses of the old CallInst.
844b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    if (!CI->use_empty()) {
845b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      //  Construct an appropriate cast from the new return type to the old.
846b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      CastInst *RetCast =
847b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands        CastInst::Create(CastInst::getCastOpcode(NewCI, true,
848b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands                                                 F->getReturnType(), true),
849b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands                         NewCI, F->getReturnType(), NewCI->getName(), CI);
850b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands      CI->replaceAllUsesWith(RetCast);
851b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    }
852b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands    CI->eraseFromParent();
853b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands  }
854b01bbdcc1af27bd90b552bb1b62b48916e0d4be3Duncan Sands  break;
85520adc9dc4650313f017b27d9818eb2176238113dMon P Wang  case Intrinsic::memcpy:
85620adc9dc4650313f017b27d9818eb2176238113dMon P Wang  case Intrinsic::memmove:
85720adc9dc4650313f017b27d9818eb2176238113dMon P Wang  case Intrinsic::memset: {
85820adc9dc4650313f017b27d9818eb2176238113dMon P Wang    // Add isVolatile
85920adc9dc4650313f017b27d9818eb2176238113dMon P Wang    const llvm::Type *I1Ty = llvm::Type::getInt1Ty(CI->getContext());
860f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif    Value *Operands[5] = { CI->getArgOperand(0), CI->getArgOperand(1),
861f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif                           CI->getArgOperand(2), CI->getArgOperand(3),
86220adc9dc4650313f017b27d9818eb2176238113dMon P Wang                           llvm::ConstantInt::get(I1Ty, 0) };
86320adc9dc4650313f017b27d9818eb2176238113dMon P Wang    CallInst *NewCI = CallInst::Create(NewFn, Operands, Operands+5,
86420adc9dc4650313f017b27d9818eb2176238113dMon P Wang                                       CI->getName(), CI);
86520adc9dc4650313f017b27d9818eb2176238113dMon P Wang    NewCI->setTailCall(CI->isTailCall());
86620adc9dc4650313f017b27d9818eb2176238113dMon P Wang    NewCI->setCallingConv(CI->getCallingConv());
86720adc9dc4650313f017b27d9818eb2176238113dMon P Wang    //  Handle any uses of the old CallInst.
86820adc9dc4650313f017b27d9818eb2176238113dMon P Wang    if (!CI->use_empty())
86920adc9dc4650313f017b27d9818eb2176238113dMon P Wang      //  Replace all uses of the old call with the new cast which has the
87020adc9dc4650313f017b27d9818eb2176238113dMon P Wang      //  correct type.
87120adc9dc4650313f017b27d9818eb2176238113dMon P Wang      CI->replaceAllUsesWith(NewCI);
87220adc9dc4650313f017b27d9818eb2176238113dMon P Wang
87320adc9dc4650313f017b27d9818eb2176238113dMon P Wang    //  Clean up the old call now that it has been completely upgraded.
87420adc9dc4650313f017b27d9818eb2176238113dMon P Wang    CI->eraseFromParent();
87520adc9dc4650313f017b27d9818eb2176238113dMon P Wang    break;
87620adc9dc4650313f017b27d9818eb2176238113dMon P Wang  }
8776994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  }
8786994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth}
8796994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8806994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// This tests each Function to determine if it needs upgrading. When we find
8816994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// one we are interested in, we then upgrade all calls to reflect the new
8826994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth// function.
8836994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruthvoid llvm::UpgradeCallsToIntrinsic(Function* F) {
8846994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  assert(F && "Illegal attempt to upgrade a non-existent intrinsic.");
8856994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth
8866994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  // Upgrade the function and check if it is a totaly new function.
887f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  Function* NewFn;
888f9b83fcf95e8a280d7b117af8858596fe5b10d94Evan Cheng  if (UpgradeIntrinsicFunction(F, NewFn)) {
8896994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    if (NewFn != F) {
8906994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      // Replace all uses to the old function with the new one if necessary.
8916994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      for (Value::use_iterator UI = F->use_begin(), UE = F->use_end();
8926994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth           UI != UE; ) {
8936994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth        if (CallInst* CI = dyn_cast<CallInst>(*UI++))
8946994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth          UpgradeIntrinsicCall(CI, NewFn);
8956994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      }
8966994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      // Remove old function, no longer used, from the module.
8976994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth      F->eraseFromParent();
8986994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth    }
8996994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth  }
9006994040a952e5fb27605eb3cf29ed86c4e59cf62Chandler Carruth}
901e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel
902771150accba7ab3480746a451710ac81f950fac2Victor Hernandez/// This function strips all debug info intrinsics, except for llvm.dbg.declare.
903771150accba7ab3480746a451710ac81f950fac2Victor Hernandez/// If an llvm.dbg.declare intrinsic is invalid, then this function simply
904771150accba7ab3480746a451710ac81f950fac2Victor Hernandez/// strips that use.
905e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patelvoid llvm::CheckDebugInfoIntrinsics(Module *M) {
906e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel
907e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel
908e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  if (Function *FuncStart = M->getFunction("llvm.dbg.func.start")) {
90944a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    while (!FuncStart->use_empty()) {
91044a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CallInst *CI = cast<CallInst>(FuncStart->use_back());
91144a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CI->eraseFromParent();
912e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel    }
91344a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    FuncStart->eraseFromParent();
914e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  }
91544a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel
916e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  if (Function *StopPoint = M->getFunction("llvm.dbg.stoppoint")) {
91744a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    while (!StopPoint->use_empty()) {
91844a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CallInst *CI = cast<CallInst>(StopPoint->use_back());
91944a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CI->eraseFromParent();
920e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel    }
92144a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    StopPoint->eraseFromParent();
922e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  }
923e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel
924e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  if (Function *RegionStart = M->getFunction("llvm.dbg.region.start")) {
92544a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    while (!RegionStart->use_empty()) {
92644a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CallInst *CI = cast<CallInst>(RegionStart->use_back());
92744a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CI->eraseFromParent();
928e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel    }
92944a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    RegionStart->eraseFromParent();
930e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  }
931e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel
932e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  if (Function *RegionEnd = M->getFunction("llvm.dbg.region.end")) {
93344a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    while (!RegionEnd->use_empty()) {
93444a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CallInst *CI = cast<CallInst>(RegionEnd->use_back());
93544a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel      CI->eraseFromParent();
936e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel    }
93744a29e066a24e88bdf127e88be4380a5f259c4b4Devang Patel    RegionEnd->eraseFromParent();
938e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  }
939e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel
940e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  if (Function *Declare = M->getFunction("llvm.dbg.declare")) {
941e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel    if (!Declare->use_empty()) {
942e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel      DbgDeclareInst *DDI = cast<DbgDeclareInst>(Declare->use_back());
943f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif      if (!isa<MDNode>(DDI->getArgOperand(0)) ||
944f2937ac4eddb5ced78a1d73206de020c6d9e440fGabor Greif          !isa<MDNode>(DDI->getArgOperand(1))) {
945e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel        while (!Declare->use_empty()) {
946e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel          CallInst *CI = cast<CallInst>(Declare->use_back());
947e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel          CI->eraseFromParent();
948e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel        }
949e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel        Declare->eraseFromParent();
950e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel      }
951e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel    }
952e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel  }
953e4b275610a7a05b7ee4c0378a906a6330e4c4ab0Devang Patel}
954