diff options
-rw-r--r-- | llvm/lib/CodeGen/Analysis.cpp | 6 | ||||
-rw-r--r-- | llvm/test/CodeGen/X86/tail-call-deref.ll | 36 |
2 files changed, 41 insertions, 1 deletions
diff --git a/llvm/lib/CodeGen/Analysis.cpp b/llvm/lib/CodeGen/Analysis.cpp index 023c2367af0..4b738ca0e94 100644 --- a/llvm/lib/CodeGen/Analysis.cpp +++ b/llvm/lib/CodeGen/Analysis.cpp @@ -567,12 +567,16 @@ bool llvm::attributesPermitTailCall(const Function *F, const Instruction *I, AttrBuilder CalleeAttrs(cast<CallInst>(I)->getAttributes(), AttributeList::ReturnIndex); - // NoAlias and NonNull are completely benign as far as calling convention + // Following attributes are completely benign as far as calling convention // goes, they shouldn't affect whether the call is a tail call. CallerAttrs.removeAttribute(Attribute::NoAlias); CalleeAttrs.removeAttribute(Attribute::NoAlias); CallerAttrs.removeAttribute(Attribute::NonNull); CalleeAttrs.removeAttribute(Attribute::NonNull); + CallerAttrs.removeAttribute(Attribute::Dereferenceable); + CalleeAttrs.removeAttribute(Attribute::Dereferenceable); + CallerAttrs.removeAttribute(Attribute::DereferenceableOrNull); + CalleeAttrs.removeAttribute(Attribute::DereferenceableOrNull); if (CallerAttrs.contains(Attribute::ZExt)) { if (!CalleeAttrs.contains(Attribute::ZExt)) diff --git a/llvm/test/CodeGen/X86/tail-call-deref.ll b/llvm/test/CodeGen/X86/tail-call-deref.ll new file mode 100644 index 00000000000..5df7cf4da8e --- /dev/null +++ b/llvm/test/CodeGen/X86/tail-call-deref.ll @@ -0,0 +1,36 @@ +; NOTE: Assertions have been autogenerated by utils/update_llc_test_checks.py +; RUN: llc -mtriple=x86_64-linux < %s | FileCheck %s + +declare i8* @foo() + +define dereferenceable(8) i8* @test1() nounwind { +; CHECK-LABEL: test1: +; CHECK: # %bb.0: +; CHECK-NEXT: jmp foo # TAILCALL + %ret = tail call i8* @foo() + ret i8* %ret +} + +define i8* @test2() nounwind { +; CHECK-LABEL: test2: +; CHECK: # %bb.0: +; CHECK-NEXT: jmp foo # TAILCALL + %ret = tail call dereferenceable(8) i8* @foo() + ret i8* %ret +} + +define dereferenceable_or_null(8) i8* @test3() nounwind { +; CHECK-LABEL: test3: +; CHECK: # %bb.0: +; CHECK-NEXT: jmp foo # TAILCALL + %ret = tail call i8* @foo() + ret i8* %ret +} + +define i8* @test4() nounwind { +; CHECK-LABEL: test4: +; CHECK: # %bb.0: +; CHECK-NEXT: jmp foo # TAILCALL + %ret = tail call dereferenceable_or_null(8) i8* @foo() + ret i8* %ret +} |