llvmbot wrote:

<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-clang

Author: Paweł Bylica (chfast)

<details>
<summary>Changes</summary>

After a musttail call, the function epilog emitted a redundant return in a dead 
block. This happened because EnsureInsertPoint() created a new block after the 
musttail's ClearInsertionPoint(), and EmitFunctionEpilog then added a return to 
it.

Remove EnsureInsertPoint() after the musttail return so the insert point stays 
cleared. Guard EmitFunctionEpilog and the return value store in EmitReturnStmt 
with HaveInsertPoint() checks.

This is a reworked version of #<!-- -->134282, addressing review feedback.

Fixes #<!-- -->104770.

---
Full diff: https://github.com/llvm/llvm-project/pull/191198.diff


6 Files Affected:

- (modified) clang/lib/CodeGen/CGCall.cpp (+4-1) 
- (modified) clang/lib/CodeGen/CGExprComplex.cpp (+3-1) 
- (modified) clang/lib/CodeGen/CGStmt.cpp (+3) 
- (modified) clang/test/CodeGenCXX/attr-musttail.cpp (+2-2) 
- (modified) clang/test/CodeGenCXX/fake-use-musttail.cpp (+1-5) 
- (added) clang/test/CodeGenCXX/musttail-epilog.cpp (+32) 


``````````diff
diff --git a/clang/lib/CodeGen/CGCall.cpp b/clang/lib/CodeGen/CGCall.cpp
index c0e2456891e9d..db6ce0ace8c86 100644
--- a/clang/lib/CodeGen/CGCall.cpp
+++ b/clang/lib/CodeGen/CGCall.cpp
@@ -4104,6 +4104,10 @@ llvm::Value 
*CodeGenFunction::EmitCMSEClearRecord(llvm::Value *Src,
 void CodeGenFunction::EmitFunctionEpilog(
     const CGFunctionInfo &FI, bool EmitRetDbgLoc, SourceLocation EndLoc,
     uint64_t RetKeyInstructionsSourceAtom) {
+  // Nothing to do if the function body already emitted a return.
+  if (!HaveInsertPoint())
+    return;
+
   if (FI.isNoReturn()) {
     // Noreturn functions don't return.
     EmitUnreachable(EndLoc);
@@ -6271,7 +6275,6 @@ RValue CodeGenFunction::EmitCall(const CGFunctionInfo 
&CallInfo,
     else
       Builder.CreateRet(CI);
     Builder.ClearInsertionPoint();
-    EnsureInsertPoint();
     return GetUndefRValue(RetTy);
   }
 
diff --git a/clang/lib/CodeGen/CGExprComplex.cpp 
b/clang/lib/CodeGen/CGExprComplex.cpp
index 757663eb50f58..e70c75752d561 100644
--- a/clang/lib/CodeGen/CGExprComplex.cpp
+++ b/clang/lib/CodeGen/CGExprComplex.cpp
@@ -1491,7 +1491,9 @@ void CodeGenFunction::EmitComplexExprIntoLValue(const 
Expr *E, LValue dest,
          "Invalid complex expression to emit");
   ComplexExprEmitter Emitter(*this);
   ComplexPairTy Val = Emitter.Visit(const_cast<Expr *>(E));
-  Emitter.EmitStoreOfComplex(Val, dest, isInit);
+  // The call may have already emitted a return (e.g. musttail).
+  if (HaveInsertPoint())
+    Emitter.EmitStoreOfComplex(Val, dest, isInit);
 }
 
 /// EmitStoreOfComplex - Store a complex number into the specified l-value.
diff --git a/clang/lib/CodeGen/CGStmt.cpp b/clang/lib/CodeGen/CGStmt.cpp
index a75d3dc64c6b4..a55d53cf0c0a5 100644
--- a/clang/lib/CodeGen/CGStmt.cpp
+++ b/clang/lib/CodeGen/CGStmt.cpp
@@ -1644,6 +1644,9 @@ void CodeGenFunction::EmitReturnStmt(const ReturnStmt &S) 
{
     switch (getEvaluationKind(RV->getType())) {
     case TEK_Scalar: {
       llvm::Value *Ret = EmitScalarExpr(RV);
+      // The call may have already emitted a return (e.g. musttail).
+      if (!HaveInsertPoint())
+        break;
       if (CurFnInfo->getReturnInfo().getKind() == ABIArgInfo::Indirect) {
         EmitStoreOfScalar(Ret, MakeAddrLValue(ReturnValue, RV->getType()),
                           /*isInit*/ true);
diff --git a/clang/test/CodeGenCXX/attr-musttail.cpp 
b/clang/test/CodeGenCXX/attr-musttail.cpp
index c0081ec232e4a..1d908e2c785f1 100644
--- a/clang/test/CodeGenCXX/attr-musttail.cpp
+++ b/clang/test/CodeGenCXX/attr-musttail.cpp
@@ -7,11 +7,11 @@ int Baz(int);
 
 int Func1(int x) {
   if (x) {
-    // CHECK: %call = musttail call noundef i32 @_Z3Bari(i32 noundef %1)
+    // CHECK: %call = musttail call noundef i32 @_Z3Bari(i32 noundef %{{.*}})
     // CHECK-NEXT: ret i32 %call
     [[clang::musttail]] return Bar(x);
   } else {
-    [[clang::musttail]] return Baz(x); // CHECK: %call1 = musttail call 
noundef i32 @_Z3Bazi(i32 noundef %3)
+    [[clang::musttail]] return Baz(x); // CHECK: %call1 = musttail call 
noundef i32 @_Z3Bazi(i32 noundef %{{.*}})
   }
 }
 
diff --git a/clang/test/CodeGenCXX/fake-use-musttail.cpp 
b/clang/test/CodeGenCXX/fake-use-musttail.cpp
index 9d341ab52f1c8..ac7f8a1f17c61 100644
--- a/clang/test/CodeGenCXX/fake-use-musttail.cpp
+++ b/clang/test/CodeGenCXX/fake-use-musttail.cpp
@@ -16,11 +16,7 @@ extern "C" char *bar(int *);
 // CHECK-NEXT:    notail call void (...) @llvm.fake.use(ptr [[FAKE_USE]])
 // CHECK-NEXT:    [[CALL:%.*]] = musttail call ptr @bar(ptr noundef [[TMP0]])
 // CHECK-NEXT:    ret ptr [[CALL]]
-
-// CHECK:       [[BB1:.*:]]
-// CHECK-NEXT:    [[FAKE_USE1:%.*]] = load ptr, ptr [[E_ADDR]]
-// CHECK-NEXT:    notail call void (...) @llvm.fake.use(ptr [[FAKE_USE1]])
-// CHECK-NEXT:    ret ptr undef
+// CHECK-NOT:     ret ptr
 //
 extern "C" const char *foo(int *e) {
   [[clang::musttail]] return bar(e);
diff --git a/clang/test/CodeGenCXX/musttail-epilog.cpp 
b/clang/test/CodeGenCXX/musttail-epilog.cpp
new file mode 100644
index 0000000000000..566dff65e8748
--- /dev/null
+++ b/clang/test/CodeGenCXX/musttail-epilog.cpp
@@ -0,0 +1,32 @@
+// RUN: %clang_cc1 -emit-llvm %s -triple x86_64-unknown-linux-gnu -o - | 
FileCheck %s
+
+// After a musttail call, the function epilog should not emit a redundant
+// return statement in a dead block.
+
+int F1(short);
+void V1(int);
+double _Complex C1(short);
+
+// CHECK-LABEL: define {{.*}} @_Z5test1s(
+// CHECK: musttail call
+// CHECK-NEXT: ret i32
+// CHECK-NOT: ret i32
+int test1(short P0) {
+  [[clang::musttail]] return F1(P0);
+}
+
+// CHECK-LABEL: define {{.*}} @_Z5test2i(
+// CHECK: musttail call
+// CHECK-NEXT: ret void
+// CHECK-NOT: ret void
+void test2(int x) {
+  [[clang::musttail]] return V1(x);
+}
+
+// CHECK-LABEL: define {{.*}} @_Z5test3s(
+// CHECK: musttail call
+// CHECK-NEXT: ret { double, double }
+// CHECK-NOT: ret { double, double }
+double _Complex test3(short P0) {
+  [[clang::musttail]] return C1(P0);
+}

``````````

</details>


https://github.com/llvm/llvm-project/pull/191198
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to