From 534ba90a1b865f3731aa56423e8f02d49ff62ec7 Mon Sep 17 00:00:00 2001 From: Fariborz Jahanian Date: Fri, 13 Nov 2009 22:29:45 +0000 Subject: [PATCH] Code gen. For virtual destructor call on array objects (still part of pr5472). git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@88712 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/CodeGen/CGCXX.cpp | 11 ++++++++++- lib/CodeGen/CGCXXExpr.cpp | 1 - test/CodeGenCXX/array-operator-delete-call.cpp | 11 +++++++++++ 3 files changed, 21 insertions(+), 2 deletions(-) diff --git a/lib/CodeGen/CGCXX.cpp b/lib/CodeGen/CGCXX.cpp index c23ad59764..bcb0b5c5c3 100644 --- a/lib/CodeGen/CGCXX.cpp +++ b/lib/CodeGen/CGCXX.cpp @@ -567,7 +567,16 @@ CodeGenFunction::EmitCXXAggrDestructorCall(const CXXDestructorDecl *D, Counter = Builder.CreateLoad(IndexPtr); Counter = Builder.CreateSub(Counter, One); llvm::Value *Address = Builder.CreateInBoundsGEP(This, Counter, "arrayidx"); - EmitCXXDestructorCall(D, Dtor_Complete, Address); + if (D->isVirtual()) { + const llvm::Type *Ty = + CGM.getTypes().GetFunctionType(CGM.getTypes().getFunctionInfo(D), + /*isVariadic=*/false); + + llvm::Value *Callee = BuildVirtualCall(D, Dtor_Deleting, Address, Ty); + EmitCXXMemberCall(D, Callee, Address, 0, 0); + } + else + EmitCXXDestructorCall(D, Dtor_Complete, Address); EmitBlock(ContinueBlock); diff --git a/lib/CodeGen/CGCXXExpr.cpp b/lib/CodeGen/CGCXXExpr.cpp index aa8acab4e6..abf8d16524 100644 --- a/lib/CodeGen/CGCXXExpr.cpp +++ b/lib/CodeGen/CGCXXExpr.cpp @@ -293,7 +293,6 @@ void CodeGenFunction::EmitCXXDeleteExpr(const CXXDeleteExpr *E) { Builder.CreateIntCast(NumElements, llvm::Type::getInt64Ty(VMContext), false, "count.tmp"); - assert (!Dtor->isVirtual() && "delete [] with virtual dtors NYI"); EmitCXXAggrDestructorCall(Dtor, NumElements, Ptr); Ptr = AllocatedObjectPtr; } diff --git a/test/CodeGenCXX/array-operator-delete-call.cpp b/test/CodeGenCXX/array-operator-delete-call.cpp index d394aa1673..c23d33632a 100644 --- a/test/CodeGenCXX/array-operator-delete-call.cpp +++ b/test/CodeGenCXX/array-operator-delete-call.cpp @@ -13,9 +13,16 @@ struct S { int iS; }; +struct V { + V() : iV (++count) { printf("V::V(%d)\n", iV); } + virtual ~V() { printf("V::~V(%d)\n", iV); } + int iV; +}; + struct COST { S *cost; + V *vcost; unsigned *cost_val; ~COST(); @@ -26,6 +33,7 @@ struct COST COST::COST() { cost = new S[3]; + vcost = new V[4]; cost_val = new unsigned[10]; } @@ -34,6 +42,9 @@ COST::~COST() if (cost) { delete [] cost; } + if (vcost) { + delete [] vcost; + } if (cost_val) delete [] cost_val; } -- 2.50.1