diff options
author | Giorgis Georgakoudis <georgakoudis1@llnl.gov> | 2020-07-07 22:43:24 -0700 |
---|---|---|
committer | Giorgis Georgakoudis <georgakoudis1@llnl.gov> | 2020-07-14 13:08:49 -0700 |
commit | aef60af34ec3fd2a03b69d69b031e1d34070f6d5 (patch) | |
tree | 53b6a4d81d7a8018e1bab9c7efc7c35a65e111d1 /llvm/lib/IR/Function.cpp | |
parent | b98f414a04e19202669a4273e620bc12b5054413 (diff) | |
download | llvm-aef60af34ec3fd2a03b69d69b031e1d34070f6d5.zip llvm-aef60af34ec3fd2a03b69d69b031e1d34070f6d5.tar.gz llvm-aef60af34ec3fd2a03b69d69b031e1d34070f6d5.tar.bz2 |
[CallGraph] Ignore callback uses
Summary:
Ignore callback uses when adding a callback function
in the CallGraph. Callback functions are typically
created when outlining, e.g. for OpenMP, so they have
internal scope and linkage. They should not be added
to the ExternalCallingNode since they are only callable
by the specified caller function at creation time.
A CGSCC pass, such as OpenMPOpt, may need to update
the CallGraph by adding a new outlined callback function.
Without ignoring callback uses, adding breaks CGSCC
pass restrictions and results to a broken CallGraph.
Reviewers: jdoerfert
Subscribers: hiraditya, sstefan1, llvm-commits
Tags: #llvm
Differential Revision: https://reviews.llvm.org/D83370
Diffstat (limited to 'llvm/lib/IR/Function.cpp')
-rw-r--r-- | llvm/lib/IR/Function.cpp | 14 |
1 files changed, 12 insertions, 2 deletions
diff --git a/llvm/lib/IR/Function.cpp b/llvm/lib/IR/Function.cpp index 0ec0cce..10d535e 100644 --- a/llvm/lib/IR/Function.cpp +++ b/llvm/lib/IR/Function.cpp @@ -20,6 +20,7 @@ #include "llvm/ADT/SmallVector.h" #include "llvm/ADT/StringExtras.h" #include "llvm/ADT/StringRef.h" +#include "llvm/IR/AbstractCallSite.h" #include "llvm/IR/Argument.h" #include "llvm/IR/Attributes.h" #include "llvm/IR/BasicBlock.h" @@ -1484,12 +1485,21 @@ Optional<Function *> Intrinsic::remangleIntrinsicFunction(Function *F) { } /// hasAddressTaken - returns true if there are any uses of this function -/// other than direct calls or invokes to it. -bool Function::hasAddressTaken(const User* *PutOffender) const { +/// other than direct calls or invokes to it. Optionally ignores callback +/// uses. +bool Function::hasAddressTaken(const User **PutOffender, + bool IgnoreCallbackUses) const { for (const Use &U : uses()) { const User *FU = U.getUser(); if (isa<BlockAddress>(FU)) continue; + + if (IgnoreCallbackUses) { + AbstractCallSite ACS(&U); + if (ACS && ACS.isCallbackCall()) + continue; + } + const auto *Call = dyn_cast<CallBase>(FU); if (!Call) { if (PutOffender) |