fix PR4963: folding insertvalue would sometimes turn a packed struct into
authorChris Lattner <sabre@nondot.org>
Tue, 15 Sep 2009 06:28:12 +0000 (06:28 +0000)
committerChris Lattner <sabre@nondot.org>
Tue, 15 Sep 2009 06:28:12 +0000 (06:28 +0000)
an unpacked one.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@81845 91177308-0d34-0410-b5e6-96231b3b80d8

lib/VMCore/ConstantFold.cpp
test/Assembler/insertextractvalue.ll

index 9c9ac0437dc83e726c5fb11414bee5b8f587283d..8641f77b7a611dc0a36656f90affa57003774194 100644 (file)
@@ -499,17 +499,19 @@ Constant *llvm::ConstantFoldInsertValueInstruction(LLVMContext &Context,
 
   if (isa<UndefValue>(Agg)) {
     // Insertion of constant into aggregate undef
-    // Optimize away insertion of undef
+    // Optimize away insertion of undef.
     if (isa<UndefValue>(Val))
       return const_cast<Constant*>(Agg);
+    
     // Otherwise break the aggregate undef into multiple undefs and do
-    // the insertion
+    // the insertion.
     const CompositeType *AggTy = cast<CompositeType>(Agg->getType());
     unsigned numOps;
     if (const ArrayType *AR = dyn_cast<ArrayType>(AggTy))
       numOps = AR->getNumElements();
     else
       numOps = cast<StructType>(AggTy)->getNumElements();
+    
     std::vector<Constant*> Ops(numOps); 
     for (unsigned i = 0; i < numOps; ++i) {
       const Type *MemberTy = AggTy->getTypeAtIndex(i);
@@ -520,24 +522,27 @@ Constant *llvm::ConstantFoldInsertValueInstruction(LLVMContext &Context,
         UndefValue::get(MemberTy);
       Ops[i] = const_cast<Constant*>(Op);
     }
-    if (isa<StructType>(AggTy))
-      return ConstantStruct::get(Context, Ops);
-    else
-      return ConstantArray::get(cast<ArrayType>(AggTy), Ops);
+    
+    if (const StructType* ST = dyn_cast<StructType>(AggTy))
+      return ConstantStruct::get(Context, Ops, ST->isPacked());
+    return ConstantArray::get(cast<ArrayType>(AggTy), Ops);
   }
+  
   if (isa<ConstantAggregateZero>(Agg)) {
     // Insertion of constant into aggregate zero
-    // Optimize away insertion of zero
+    // Optimize away insertion of zero.
     if (Val->isNullValue())
       return const_cast<Constant*>(Agg);
+    
     // Otherwise break the aggregate zero into multiple zeros and do
-    // the insertion
+    // the insertion.
     const CompositeType *AggTy = cast<CompositeType>(Agg->getType());
     unsigned numOps;
     if (const ArrayType *AR = dyn_cast<ArrayType>(AggTy))
       numOps = AR->getNumElements();
     else
       numOps = cast<StructType>(AggTy)->getNumElements();
+    
     std::vector<Constant*> Ops(numOps);
     for (unsigned i = 0; i < numOps; ++i) {
       const Type *MemberTy = AggTy->getTypeAtIndex(i);
@@ -549,13 +554,14 @@ Constant *llvm::ConstantFoldInsertValueInstruction(LLVMContext &Context,
         Constant::getNullValue(MemberTy);
       Ops[i] = const_cast<Constant*>(Op);
     }
-    if (isa<StructType>(AggTy))
-      return ConstantStruct::get(Context, Ops);
-    else
-      return ConstantArray::get(cast<ArrayType>(AggTy), Ops);
+    
+    if (const StructType* ST = dyn_cast<StructType>(AggTy))
+      return ConstantStruct::get(Context, Ops, ST->isPacked());
+    return ConstantArray::get(cast<ArrayType>(AggTy), Ops);
   }
+  
   if (isa<ConstantStruct>(Agg) || isa<ConstantArray>(Agg)) {
-    // Insertion of constant into aggregate constant
+    // Insertion of constant into aggregate constant.
     std::vector<Constant*> Ops(Agg->getNumOperands());
     for (unsigned i = 0; i < Agg->getNumOperands(); ++i) {
       const Constant *Op =
@@ -565,12 +571,10 @@ Constant *llvm::ConstantFoldInsertValueInstruction(LLVMContext &Context,
         Agg->getOperand(i);
       Ops[i] = const_cast<Constant*>(Op);
     }
-    Constant *C;
-    if (isa<StructType>(Agg->getType()))
-      C = ConstantStruct::get(Context, Ops);
-    else
-      C = ConstantArray::get(cast<ArrayType>(Agg->getType()), Ops);
-    return C;
+    
+    if (const StructType* ST = dyn_cast<StructType>(Agg->getType()))
+      return ConstantStruct::get(Context, Ops, ST->isPacked());
+    return ConstantArray::get(cast<ArrayType>(Agg->getType()), Ops);
   }
 
   return 0;
@@ -585,7 +589,7 @@ Constant *llvm::ConstantFoldBinaryInstruction(LLVMContext &Context,
   if (C1->getType() == Type::getPPC_FP128Ty(Context))
     return 0;
 
-  // Handle UndefValue up front
+  // Handle UndefValue up front.
   if (isa<UndefValue>(C1) || isa<UndefValue>(C2)) {
     switch (Opcode) {
     case Instruction::Xor:
index 3581238aa4c1cdb8283b1c5444b4e2b670257f35..2f5521fba87254e5ec374642aac83992aba5adcb 100644 (file)
@@ -21,3 +21,9 @@ define float @dar({{i32},{float, double}}* %p) nounwind {
   store {{i32},{float, double}} insertvalue ({{i32},{float, double}} zeroinitializer, double 20.0, 1, 1), {{i32},{float, double}}* %p
   ret float extractvalue ({{i32},{float, double}} zeroinitializer, 1, 0)
 }
+
+
+; PR4963
+define <{ i32, i32 }> @test57() {
+  ret <{ i32, i32 }> insertvalue (<{ i32, i32 }> zeroinitializer, i32 4, 1)
+}