From b8da7a046d3ec13974004291b100b4bfc80db836 Mon Sep 17 00:00:00 2001 From: Mike Stump Date: Thu, 5 Nov 2009 06:12:26 +0000 Subject: [PATCH] Refine covariant return value adjustments for thunks when null pointers are returned. llvm-svn: 86120 --- clang/lib/CodeGen/CGCXX.cpp | 20 +++++++++++++++++++- clang/test/CodeGenCXX/virt.cpp | 6 +++++- 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/clang/lib/CodeGen/CGCXX.cpp b/clang/lib/CodeGen/CGCXX.cpp index d4adbad1e45e..fd90dc06d505 100644 --- a/clang/lib/CodeGen/CGCXX.cpp +++ b/clang/lib/CodeGen/CGCXX.cpp @@ -811,7 +811,25 @@ llvm::Constant *CodeGenFunction::GenerateCovariantThunk(llvm::Function *Fn, Callee, CallArgs, MD); if (nv_r || v_r) { // Do the return result adjustment. - RV = RValue::get(DynamicTypeAdjust(RV.getScalarVal(), nv_r, v_r)); + llvm::BasicBlock *NonZeroBlock = createBasicBlock(); + llvm::BasicBlock *ZeroBlock = createBasicBlock(); + llvm::BasicBlock *ContBlock = createBasicBlock(); + + const llvm::Type *Ty = RV.getScalarVal()->getType(); + llvm::Value *Zero = llvm::Constant::getNullValue(Ty); + Builder.CreateCondBr(Builder.CreateICmpNE(RV.getScalarVal(), Zero), + NonZeroBlock, ZeroBlock); + EmitBlock(NonZeroBlock); + llvm::Value *NZ = DynamicTypeAdjust(RV.getScalarVal(), nv_r, v_r); + EmitBranch(ContBlock); + EmitBlock(ZeroBlock); + llvm::Value *Z = RV.getScalarVal(); + EmitBlock(ContBlock); + llvm::PHINode *RVOrZero = Builder.CreatePHI(Ty); + RVOrZero->reserveOperandSpace(2); + RVOrZero->addIncoming(NZ, NonZeroBlock); + RVOrZero->addIncoming(Z, ZeroBlock); + RV = RValue::get(RVOrZero); } if (!ResultType->isVoidType()) diff --git a/clang/test/CodeGenCXX/virt.cpp b/clang/test/CodeGenCXX/virt.cpp index a85b2dfe477e..193a96ddd589 100644 --- a/clang/test/CodeGenCXX/virt.cpp +++ b/clang/test/CodeGenCXX/virt.cpp @@ -1076,12 +1076,16 @@ void test16_D::bar() { } // CHECK-LPOPT64-NEXT: subq $8, %rsp // CHECK-LPOPT64-NEXT:Llabel // CHECK-LPOPT64-NEXT: call __ZN8test16_D4foo1Ev -// FIXME: We need a == 0 check here +// CHECK-LPOPT64-NEXT: testq %rax, %rax +// CHECK-LPOPT64-NEXT: je LBB102_2 // CHECK-LPOPT64-NEXT: movq 16(%rax), %rcx // CHECK-LPOPT64-NEXT: movq -32(%rcx), %rcx // CHECK-LPOPT64-NEXT: leaq 16(%rcx,%rax), %rax // CHECK-LPOPT64-NEXT: addq $8, %rsp // CHECK-LPOPT64-NEXT: ret +// CHECK-LPOPT64-NEXT:LBB102_2: +// CHECK-LPOPT64-NEXT: addq $8, %rsp +// CHECK-LPOPT64-NEXT: ret class test17_B1 { -- GitLab