summaryrefslogtreecommitdiff
path: root/lib/Analysis/BasicAliasAnalysis.cpp
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2018-08-18 08:26:46 +0000
committerDimitry Andric <dim@FreeBSD.org>2018-08-18 08:26:46 +0000
commitd0a9cbdae159210824ddf2da138e2dcaecbe1cd4 (patch)
treec539e15a2dbf52df82eb2a72fb6581db604faab4 /lib/Analysis/BasicAliasAnalysis.cpp
parentac3a3c134038429abacef8c5d8069674f98d6b34 (diff)
Notes
Diffstat (limited to 'lib/Analysis/BasicAliasAnalysis.cpp')
-rw-r--r--lib/Analysis/BasicAliasAnalysis.cpp13
1 files changed, 7 insertions, 6 deletions
diff --git a/lib/Analysis/BasicAliasAnalysis.cpp b/lib/Analysis/BasicAliasAnalysis.cpp
index 1a24ae3dba15..f9ecbc043261 100644
--- a/lib/Analysis/BasicAliasAnalysis.cpp
+++ b/lib/Analysis/BasicAliasAnalysis.cpp
@@ -801,14 +801,15 @@ ModRefInfo BasicAAResult::getModRefInfo(ImmutableCallSite CS,
const Value *Object = GetUnderlyingObject(Loc.Ptr, DL);
- // If this is a tail call and Loc.Ptr points to a stack location, we know that
- // the tail call cannot access or modify the local stack.
- // We cannot exclude byval arguments here; these belong to the caller of
- // the current function not to the current function, and a tail callee
- // may reference them.
+ // Calls marked 'tail' cannot read or write allocas from the current frame
+ // because the current frame might be destroyed by the time they run. However,
+ // a tail call may use an alloca with byval. Calling with byval copies the
+ // contents of the alloca into argument registers or stack slots, so there is
+ // no lifetime issue.
if (isa<AllocaInst>(Object))
if (const CallInst *CI = dyn_cast<CallInst>(CS.getInstruction()))
- if (CI->isTailCall())
+ if (CI->isTailCall() &&
+ !CI->getAttributes().hasAttrSomewhere(Attribute::ByVal))
return ModRefInfo::NoModRef;
// If the pointer is to a locally allocated object that does not escape,