[llvm] r329015 - Treat inlining a notail call as a regular, non-tail call

Reid Kleckner via llvm-commits llvm-commits at lists.llvm.org
Mon Apr 2 14:23:16 PDT 2018


Author: rnk
Date: Mon Apr  2 14:23:16 2018
New Revision: 329015

URL: http://llvm.org/viewvc/llvm-project?rev=329015&view=rev
Log:
Treat inlining a notail call as a regular, non-tail call

Otherwise, we end up inlining a musttail call into a non-tail position,
which breaks verifier invariants.

Fixes PR31014

Modified:
    llvm/trunk/lib/Transforms/Utils/InlineFunction.cpp
    llvm/trunk/test/Transforms/Inline/inline-tail.ll

Modified: llvm/trunk/lib/Transforms/Utils/InlineFunction.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Utils/InlineFunction.cpp?rev=329015&r1=329014&r2=329015&view=diff
==============================================================================
--- llvm/trunk/lib/Transforms/Utils/InlineFunction.cpp (original)
+++ llvm/trunk/lib/Transforms/Utils/InlineFunction.cpp Mon Apr  2 14:23:16 2018
@@ -1826,6 +1826,10 @@ bool llvm::InlineFunction(CallSite CS, I
     if (CallInst *CI = dyn_cast<CallInst>(TheCall))
       CallSiteTailKind = CI->getTailCallKind();
 
+    // For inlining purposes, the "notail" marker is the same as no marker.
+    if (CallSiteTailKind == CallInst::TCK_NoTail)
+      CallSiteTailKind = CallInst::TCK_None;
+
     for (Function::iterator BB = FirstNewBlock, E = Caller->end(); BB != E;
          ++BB) {
       for (auto II = BB->begin(); II != BB->end();) {
@@ -1885,6 +1889,8 @@ bool llvm::InlineFunction(CallSite CS, I
         //    f -> musttail g ->     tail f  ==>  f ->     tail f
         //    f ->          g -> musttail f  ==>  f ->          f
         //    f ->          g ->     tail f  ==>  f ->          f
+        //
+        // Inlined notail calls should remain notail calls.
         CallInst::TailCallKind ChildTCK = CI->getTailCallKind();
         if (ChildTCK != CallInst::TCK_NoTail)
           ChildTCK = std::min(CallSiteTailKind, ChildTCK);

Modified: llvm/trunk/test/Transforms/Inline/inline-tail.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/Transforms/Inline/inline-tail.ll?rev=329015&r1=329014&r2=329015&view=diff
==============================================================================
--- llvm/trunk/test/Transforms/Inline/inline-tail.ll (original)
+++ llvm/trunk/test/Transforms/Inline/inline-tail.ll Mon Apr  2 14:23:16 2018
@@ -196,3 +196,24 @@ define i32 @test_notail() {
   %rv = tail call i32 @notail()
   ret i32 %rv
 }
+
+; PR31014: Inlining a musttail call through a notail call site should remove
+; any tail marking, otherwise we break verifier invariants.
+
+declare void @do_ret(i32)
+
+define void @test_notail_inline_musttail(i32 %a) {
+  notail call void @inline_musttail(i32 %a)
+  musttail call void @do_ret(i32 %a)
+  ret void
+}
+
+define internal void @inline_musttail(i32 %a) {
+  musttail call void @do_ret(i32 %a)
+  ret void
+}
+
+; CHECK-LABEL: define void @test_notail_inline_musttail(i32 %a)
+; CHECK:   {{^ *}}call void @do_ret(i32 %a)
+; CHECK:   musttail call void @do_ret(i32 %a)
+; CHECK:   ret void




More information about the llvm-commits mailing list