[llvm-commits] [llvm] r42864 - in /llvm/trunk: lib/Transforms/Scalar/InstructionCombining.cpp test/Transforms/InstCombine/2007-10-10-EliminateMemCpy.ll

Devang Patel dpatel at apple.com
Thu Oct 11 10:22:00 PDT 2007


Author: dpatel
Date: Thu Oct 11 12:21:57 2007
New Revision: 42864

URL: http://llvm.org/viewvc/llvm-project?rev=42864&view=rev
Log:
Lower memcpy if it makes sense.

Added:
    llvm/trunk/test/Transforms/InstCombine/2007-10-10-EliminateMemCpy.ll
Modified:
    llvm/trunk/lib/Transforms/Scalar/InstructionCombining.cpp

Modified: llvm/trunk/lib/Transforms/Scalar/InstructionCombining.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/InstructionCombining.cpp?rev=42864&r1=42863&r2=42864&view=diff

==============================================================================
--- llvm/trunk/lib/Transforms/Scalar/InstructionCombining.cpp (original)
+++ llvm/trunk/lib/Transforms/Scalar/InstructionCombining.cpp Thu Oct 11 12:21:57 2007
@@ -7669,6 +7669,52 @@
         MI->setAlignment(ConstantInt::get(Type::Int32Ty, Align));
         Changed = true;
       }
+
+      // If MemCpyInst length is 1/2/4/8 bytes then replace memcpy with load/store
+      ConstantInt *MemOpLength = dyn_cast<ConstantInt>(CI.getOperand(3));
+      if (isa<MemCpyInst>(MI))
+        if (MemOpLength) {
+        unsigned Size = MemOpLength->getZExtValue();
+        unsigned Align = cast<ConstantInt>(CI.getOperand(4))->getZExtValue();
+        const PointerType *PTy = cast<PointerType>(CI.getOperand(1)->getType());
+        const Type *MTy = PTy->getElementType();
+        PointerType *NewPtrTy = NULL;
+        if (MTy == Type::Int8Ty) {
+          if (Size == 8)
+            NewPtrTy = PointerType::get(Type::Int64Ty);
+          else if (Size == 4)
+            NewPtrTy = PointerType::get(Type::Int32Ty);
+          else if (Size == 2)
+            NewPtrTy = PointerType::get(Type::Int16Ty);
+          else if (Size == 1)
+            NewPtrTy = PointerType::get(Type::Int8Ty);
+        } else if (MTy == Type::Int16Ty) {
+          if (Size == 4)
+            NewPtrTy = PointerType::get(Type::Int64Ty);
+          else if (Size == 2)
+            NewPtrTy = PointerType::get(Type::Int32Ty);
+          else if (Size == 1)
+            NewPtrTy = PointerType::get(Type::Int16Ty);
+        } else if (MTy == Type::Int32Ty) {
+          if (Size == 2)
+            NewPtrTy = PointerType::get(Type::Int64Ty);
+          else if (Size == 1)
+            NewPtrTy = PointerType::get(Type::Int32Ty);
+        } else if (MTy == Type::Int64Ty) {
+          if (Size == 1)
+            NewPtrTy = PointerType::get(Type::Int64Ty);
+        }
+        if (NewPtrTy)
+        {
+          Value *Src = InsertCastBefore(Instruction::BitCast, CI.getOperand(2), NewPtrTy, CI);
+          Value *Dest = InsertCastBefore(Instruction::BitCast, CI.getOperand(1), NewPtrTy, CI);
+          Value *L = new LoadInst(Src, "tmp", false, Align, &CI);
+          Value *NS = new StoreInst(L, Dest, false, Align, &CI);
+          CI.replaceAllUsesWith(NS);
+          Changed = true;
+          return EraseInstFromFunction(CI);
+        }
+      }
     } else if (isa<MemSetInst>(MI)) {
       unsigned Alignment = GetOrEnforceKnownAlignment(MI->getDest(), TD);
       if (MI->getAlignment()->getZExtValue() < Alignment) {

Added: llvm/trunk/test/Transforms/InstCombine/2007-10-10-EliminateMemCpy.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/InstCombine/2007-10-10-EliminateMemCpy.ll?rev=42864&view=auto

==============================================================================
--- llvm/trunk/test/Transforms/InstCombine/2007-10-10-EliminateMemCpy.ll (added)
+++ llvm/trunk/test/Transforms/InstCombine/2007-10-10-EliminateMemCpy.ll Thu Oct 11 12:21:57 2007
@@ -0,0 +1,18 @@
+; RUN: llvm-as < %s | opt -instcombine | llvm-dis | not grep call
+ at .str = internal constant [4 x i8] c"xyz\00"		; <[4 x i8]*> [#uses=1]
+
+define void @foo(i8* %P) {
+entry:
+	%P_addr = alloca i8*		; <i8**> [#uses=2]
+	%"alloca point" = bitcast i32 0 to i32		; <i32> [#uses=0]
+	store i8* %P, i8** %P_addr
+	%tmp = load i8** %P_addr, align 4		; <i8*> [#uses=1]
+	%tmp1 = getelementptr [4 x i8]* @.str, i32 0, i32 0		; <i8*> [#uses=1]
+	call void @llvm.memcpy.i32( i8* %tmp, i8* %tmp1, i32 4, i32 1 )
+	br label %return
+
+return:		; preds = %entry
+	ret void
+}
+
+declare void @llvm.memcpy.i32(i8*, i8*, i32, i32)





More information about the llvm-commits mailing list