forked from OSchip/llvm-project
FunctionAttrs: Factor out a function for querying memory access of a specific copy of a function. NFC.
This will later be used by ThinLTOBitcodeWriter to add copies of readnone functions to the regular LTO module. Differential Revision: https://reviews.llvm.org/D29695 llvm-svn: 295008
This commit is contained in:
parent
3291877656
commit
c45f7f3eb4
|
@ -20,6 +20,19 @@
|
|||
|
||||
namespace llvm {
|
||||
|
||||
class AAResults;
|
||||
|
||||
/// The three kinds of memory access relevant to 'readonly' and
|
||||
/// 'readnone' attributes.
|
||||
enum MemoryAccessKind {
|
||||
MAK_ReadNone = 0,
|
||||
MAK_ReadOnly = 1,
|
||||
MAK_MayWrite = 2
|
||||
};
|
||||
|
||||
/// Returns the memory access properties of this copy of the function.
|
||||
MemoryAccessKind computeFunctionBodyMemoryAccess(Function &F, AAResults &AAR);
|
||||
|
||||
/// Computes function attributes in post-order over the call graph.
|
||||
///
|
||||
/// By operating in post-order, this pass computes precise attributes for
|
||||
|
|
|
@ -61,27 +61,23 @@ namespace {
|
|||
typedef SmallSetVector<Function *, 8> SCCNodeSet;
|
||||
}
|
||||
|
||||
namespace {
|
||||
/// The three kinds of memory access relevant to 'readonly' and
|
||||
/// 'readnone' attributes.
|
||||
enum MemoryAccessKind {
|
||||
MAK_ReadNone = 0,
|
||||
MAK_ReadOnly = 1,
|
||||
MAK_MayWrite = 2
|
||||
};
|
||||
}
|
||||
|
||||
static MemoryAccessKind checkFunctionMemoryAccess(Function &F, AAResults &AAR,
|
||||
/// Returns the memory access attribute for function F using AAR for AA results,
|
||||
/// where SCCNodes is the current SCC.
|
||||
///
|
||||
/// If ThisBody is true, this function may examine the function body and will
|
||||
/// return a result pertaining to this copy of the function. If it is false, the
|
||||
/// result will be based only on AA results for the function declaration; it
|
||||
/// will be assumed that some other (perhaps less optimized) version of the
|
||||
/// function may be selected at link time.
|
||||
static MemoryAccessKind checkFunctionMemoryAccess(Function &F, bool ThisBody,
|
||||
AAResults &AAR,
|
||||
const SCCNodeSet &SCCNodes) {
|
||||
FunctionModRefBehavior MRB = AAR.getModRefBehavior(&F);
|
||||
if (MRB == FMRB_DoesNotAccessMemory)
|
||||
// Already perfect!
|
||||
return MAK_ReadNone;
|
||||
|
||||
// Non-exact function definitions may not be selected at link time, and an
|
||||
// alternative version that writes to memory may be selected. See the comment
|
||||
// on GlobalValue::isDefinitionExact for more details.
|
||||
if (!F.hasExactDefinition()) {
|
||||
if (!ThisBody) {
|
||||
if (AliasAnalysis::onlyReadsMemory(MRB))
|
||||
return MAK_ReadOnly;
|
||||
|
||||
|
@ -180,6 +176,11 @@ static MemoryAccessKind checkFunctionMemoryAccess(Function &F, AAResults &AAR,
|
|||
return ReadsMemory ? MAK_ReadOnly : MAK_ReadNone;
|
||||
}
|
||||
|
||||
MemoryAccessKind llvm::computeFunctionBodyMemoryAccess(Function &F,
|
||||
AAResults &AAR) {
|
||||
return checkFunctionMemoryAccess(F, /*ThisBody=*/true, AAR, {});
|
||||
}
|
||||
|
||||
/// Deduce readonly/readnone attributes for the SCC.
|
||||
template <typename AARGetterT>
|
||||
static bool addReadAttrs(const SCCNodeSet &SCCNodes, AARGetterT &&AARGetter) {
|
||||
|
@ -190,7 +191,11 @@ static bool addReadAttrs(const SCCNodeSet &SCCNodes, AARGetterT &&AARGetter) {
|
|||
// Call the callable parameter to look up AA results for this function.
|
||||
AAResults &AAR = AARGetter(*F);
|
||||
|
||||
switch (checkFunctionMemoryAccess(*F, AAR, SCCNodes)) {
|
||||
// Non-exact function definitions may not be selected at link time, and an
|
||||
// alternative version that writes to memory may be selected. See the
|
||||
// comment on GlobalValue::isDefinitionExact for more details.
|
||||
switch (checkFunctionMemoryAccess(*F, F->hasExactDefinition(),
|
||||
AAR, SCCNodes)) {
|
||||
case MAK_MayWrite:
|
||||
return false;
|
||||
case MAK_ReadOnly:
|
||||
|
|
Loading…
Reference in New Issue