]> granicus.if.org Git - clang/commitdiff
Handle default arguments when calling copy constructors for bases or members when...
authorAnders Carlsson <andersca@mac.com>
Tue, 30 Mar 2010 02:57:48 +0000 (02:57 +0000)
committerAnders Carlsson <andersca@mac.com>
Tue, 30 Mar 2010 02:57:48 +0000 (02:57 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@99864 91177308-0d34-0410-b5e6-96231b3b80d8

lib/CodeGen/CGClass.cpp
test/CodeGenCXX/copy-constructor-synthesis.cpp

index ebefba24115e16deb446f4fca3da7da640bf7d0c..8d565f6d4174e8719cc44df500e2e6df4c1c6859 100644 (file)
@@ -549,10 +549,30 @@ void CodeGenFunction::EmitClassMemberwiseCopy(
     // Push the Src ptr.
     CallArgs.push_back(std::make_pair(RValue::get(Src),
                        BaseCopyCtor->getParamDecl(0)->getType()));
+
+    unsigned OldNumLiveTemporaries = LiveTemporaries.size();
+
+    // If the copy constructor has default arguments, emit them.
+    for (unsigned I = 1, E = BaseCopyCtor->getNumParams(); I < E; ++I) {
+      const ParmVarDecl *Param = BaseCopyCtor->getParamDecl(I);
+      const Expr *DefaultArgExpr = Param->getDefaultArg();
+      
+      assert(DefaultArgExpr && "Ctor parameter must have default arg!");
+
+      QualType ArgType = Param->getType();
+      CallArgs.push_back(std::make_pair(EmitCallArg(DefaultArgExpr, ArgType),
+                                        ArgType));
+
+    }
+
     const FunctionProtoType *FPT =
       BaseCopyCtor->getType()->getAs<FunctionProtoType>();
     EmitCall(CGM.getTypes().getFunctionInfo(CallArgs, FPT),
              Callee, ReturnValueSlot(), CallArgs, BaseCopyCtor);
+    
+    // Pop temporaries.
+    while (LiveTemporaries.size() > OldNumLiveTemporaries)
+      PopCXXTemporary();
   }
 }
 
index 35bd83a7d025b7f7ba1c4475b31de5dba5898250..3af40cb4ec1f52ddbf98c5c3e1402bb8b8efcfe5 100644 (file)
@@ -110,3 +110,46 @@ struct B : A {
 void f(const B &b1) {
   B b2(b1);
 }
+
+// PR6628
+namespace PR6628 {
+
+struct T {
+  T();
+  ~T();
+
+  double d;
+};
+
+struct A {
+  A(const A &other, const T &t = T(), const T& t2 = T());
+};
+
+struct B : A {
+  A a1;
+  A a2;
+};
+
+// Force the copy constructor to be synthesized.
+void f(B b1) {
+  B b2 = b1;
+}
+
+// CHECK: define linkonce_odr void @_ZN6PR66281BC2ERKS0_
+// CHECK: call void @_ZN6PR66281TC1Ev
+// CHECK: call void @_ZN6PR66281TC1Ev
+// CHECK: call void @_ZN6PR66281AC2ERKS0_RKNS_1TES5_
+// CHECK: call void @_ZN6PR66281TD1Ev
+// CHECK: call void @_ZN6PR66281TD1Ev
+// CHECK: call void @_ZN6PR66281TC1Ev
+// CHECK: call void @_ZN6PR66281TC1Ev
+// CHECK: call void @_ZN6PR66281AC1ERKS0_RKNS_1TES5_
+// CHECK: call void @_ZN6PR66281TD1Ev
+// CHECK: call void @_ZN6PR66281TD1Ev
+// CHECK: call void @_ZN6PR66281TC1Ev
+// CHECK: call void @_ZN6PR66281TC1Ev
+// CHECK: call void @_ZN6PR66281AC1ERKS0_RKNS_1TES5_
+// CHECK: call void @_ZN6PR66281TD1Ev
+// CHECK: call void @_ZN6PR66281TD1Ev
+}
+