- LLVMContext &Context = F->getContext();
-
- assert(F && "CallInst has no function associated with it.");
-
- if (!NewFn) {
- bool isLoadH = false, isLoadL = false, isMovL = false;
- bool isMovSD = false, isShufPD = false;
- bool isUnpckhPD = false, isUnpcklPD = false;
- bool isPunpckhQPD = false, isPunpcklQPD = false;
- if (strcmp(F->getNameStart(), "llvm.x86.sse2.loadh.pd") == 0)
- isLoadH = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.loadl.pd") == 0)
- isLoadL = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.movl.dq") == 0)
- isMovL = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.movs.d") == 0)
- isMovSD = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.shuf.pd") == 0)
- isShufPD = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.unpckh.pd") == 0)
- isUnpckhPD = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.unpckl.pd") == 0)
- isUnpcklPD = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.punpckh.qdq") == 0)
- isPunpckhQPD = true;
- else if (strcmp(F->getNameStart(), "llvm.x86.sse2.punpckl.qdq") == 0)
- isPunpcklQPD = true;
-
- if (isLoadH || isLoadL || isMovL || isMovSD || isShufPD ||
- isUnpckhPD || isUnpcklPD || isPunpckhQPD || isPunpcklQPD) {
- std::vector<Constant*> Idxs;
- Value *Op0 = CI->getOperand(1);
- ShuffleVectorInst *SI = NULL;
- if (isLoadH || isLoadL) {
- Value *Op1 = Context.getUndef(Op0->getType());
- Value *Addr = new BitCastInst(CI->getOperand(2),
- Context.getPointerTypeUnqual(Type::DoubleTy),
- "upgraded.", CI);
- Value *Load = new LoadInst(Addr, "upgraded.", false, 8, CI);
- Value *Idx = Context.getConstantInt(Type::Int32Ty, 0);
- Op1 = InsertElementInst::Create(Op1, Load, Idx, "upgraded.", CI);
-
- if (isLoadH) {
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 0));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 2));
- } else {
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 2));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 1));
- }
- Value *Mask = Context.getConstantVector(Idxs);
- SI = new ShuffleVectorInst(Op0, Op1, Mask, "upgraded.", CI);
- } else if (isMovL) {
- Constant *Zero = Context.getConstantInt(Type::Int32Ty, 0);
- Idxs.push_back(Zero);
- Idxs.push_back(Zero);
- Idxs.push_back(Zero);
- Idxs.push_back(Zero);
- Value *ZeroV = Context.getConstantVector(Idxs);
-
- Idxs.clear();
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 4));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 5));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 2));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 3));
- Value *Mask = Context.getConstantVector(Idxs);
- SI = new ShuffleVectorInst(ZeroV, Op0, Mask, "upgraded.", CI);
- } else if (isMovSD ||
- isUnpckhPD || isUnpcklPD || isPunpckhQPD || isPunpcklQPD) {
- Value *Op1 = CI->getOperand(2);
- if (isMovSD) {
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 2));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 1));
- } else if (isUnpckhPD || isPunpckhQPD) {
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 1));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 3));
- } else {
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 0));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, 2));
- }
- Value *Mask = Context.getConstantVector(Idxs);
- SI = new ShuffleVectorInst(Op0, Op1, Mask, "upgraded.", CI);
- } else if (isShufPD) {
- Value *Op1 = CI->getOperand(2);
- unsigned MaskVal = cast<ConstantInt>(CI->getOperand(3))->getZExtValue();
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty, MaskVal & 1));
- Idxs.push_back(Context.getConstantInt(Type::Int32Ty,
- ((MaskVal >> 1) & 1)+2));
- Value *Mask = Context.getConstantVector(Idxs);
- SI = new ShuffleVectorInst(Op0, Op1, Mask, "upgraded.", CI);
- }