mirror of
https://github.com/RPCS3/llvm-mirror.git
synced 2025-01-31 20:51:52 +01:00
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 llvm-svn: 329015
This commit is contained in:
parent
9f659ebeb6
commit
47aac24633
@ -1826,6 +1826,10 @@ bool llvm::InlineFunction(CallSite CS, InlineFunctionInfo &IFI,
|
||||
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, InlineFunctionInfo &IFI,
|
||||
// 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);
|
||||
|
@ -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
|
||||
|
Loading…
x
Reference in New Issue
Block a user