summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Analysis/ModuleSummaryAnalysis.cpp
diff options
context:
space:
mode:
authorPeter Collingbourne <peter@pcc.me.uk>2017-09-01 16:24:02 +0000
committerPeter Collingbourne <peter@pcc.me.uk>2017-09-01 16:24:02 +0000
commit5e8b94c137d1a6f182dbb5afe0f739724c2dddd7 (patch)
treeb8c6d7885390e5a0f3f477ffad408067c01ea42a /llvm/lib/Analysis/ModuleSummaryAnalysis.cpp
parent6b54c7e11beb2e050de4f912d182938ce81f4221 (diff)
downloadbcm5719-llvm-5e8b94c137d1a6f182dbb5afe0f739724c2dddd7.tar.gz
bcm5719-llvm-5e8b94c137d1a6f182dbb5afe0f739724c2dddd7.zip
ModuleSummaryAnalysis: Correctly handle refs from function inline asm to module inline asm.
If a function contains inline asm and the module-level inline asm contains the definition of a local symbol, prevent the function from being imported in case the function-level inline asm refers to a symbol in the module-level inline asm. Differential Revision: https://reviews.llvm.org/D37370 llvm-svn: 312332
Diffstat (limited to 'llvm/lib/Analysis/ModuleSummaryAnalysis.cpp')
-rw-r--r--llvm/lib/Analysis/ModuleSummaryAnalysis.cpp110
1 files changed, 56 insertions, 54 deletions
diff --git a/llvm/lib/Analysis/ModuleSummaryAnalysis.cpp b/llvm/lib/Analysis/ModuleSummaryAnalysis.cpp
index 886dac8314e..4950780ae75 100644
--- a/llvm/lib/Analysis/ModuleSummaryAnalysis.cpp
+++ b/llvm/lib/Analysis/ModuleSummaryAnalysis.cpp
@@ -198,7 +198,7 @@ static void addIntrinsicToSummary(
static void
computeFunctionSummary(ModuleSummaryIndex &Index, const Module &M,
const Function &F, BlockFrequencyInfo *BFI,
- ProfileSummaryInfo *PSI, bool HasLocalsInUsed,
+ ProfileSummaryInfo *PSI, bool HasLocalsInUsedOrAsm,
DenseSet<GlobalValue::GUID> &CantBePromoted) {
// Summary not currently supported for anonymous functions, they should
// have been named.
@@ -234,7 +234,7 @@ computeFunctionSummary(ModuleSummaryIndex &Index, const Module &M,
// a local value from inline assembly to ensure we don't export a
// reference (which would require renaming and promotion of the
// referenced value).
- if (HasLocalsInUsed && CI && CI->isInlineAsm())
+ if (HasLocalsInUsedOrAsm && CI && CI->isInlineAsm())
HasInlineAsmMaybeReferencingInternal = true;
auto *CalledValue = CS.getCalledValue();
@@ -382,6 +382,58 @@ ModuleSummaryIndex llvm::buildModuleSummaryIndex(
}
}
+ bool HasLocalInlineAsmSymbol = false;
+ if (!M.getModuleInlineAsm().empty()) {
+ // Collect the local values defined by module level asm, and set up
+ // summaries for these symbols so that they can be marked as NoRename,
+ // to prevent export of any use of them in regular IR that would require
+ // renaming within the module level asm. Note we don't need to create a
+ // summary for weak or global defs, as they don't need to be flagged as
+ // NoRename, and defs in module level asm can't be imported anyway.
+ // Also, any values used but not defined within module level asm should
+ // be listed on the llvm.used or llvm.compiler.used global and marked as
+ // referenced from there.
+ ModuleSymbolTable::CollectAsmSymbols(
+ M, [&](StringRef Name, object::BasicSymbolRef::Flags Flags) {
+ // Symbols not marked as Weak or Global are local definitions.
+ if (Flags & (object::BasicSymbolRef::SF_Weak |
+ object::BasicSymbolRef::SF_Global))
+ return;
+ HasLocalInlineAsmSymbol = true;
+ GlobalValue *GV = M.getNamedValue(Name);
+ if (!GV)
+ return;
+ assert(GV->isDeclaration() && "Def in module asm already has definition");
+ GlobalValueSummary::GVFlags GVFlags(GlobalValue::InternalLinkage,
+ /* NotEligibleToImport = */ true,
+ /* Live = */ true);
+ CantBePromoted.insert(GlobalValue::getGUID(Name));
+ // Create the appropriate summary type.
+ if (Function *F = dyn_cast<Function>(GV)) {
+ std::unique_ptr<FunctionSummary> Summary =
+ llvm::make_unique<FunctionSummary>(
+ GVFlags, 0,
+ FunctionSummary::FFlags{
+ F->hasFnAttribute(Attribute::ReadNone),
+ F->hasFnAttribute(Attribute::ReadOnly),
+ F->hasFnAttribute(Attribute::NoRecurse),
+ F->returnDoesNotAlias()},
+ ArrayRef<ValueInfo>{}, ArrayRef<FunctionSummary::EdgeTy>{},
+ ArrayRef<GlobalValue::GUID>{},
+ ArrayRef<FunctionSummary::VFuncId>{},
+ ArrayRef<FunctionSummary::VFuncId>{},
+ ArrayRef<FunctionSummary::ConstVCall>{},
+ ArrayRef<FunctionSummary::ConstVCall>{});
+ Index.addGlobalValueSummary(Name, std::move(Summary));
+ } else {
+ std::unique_ptr<GlobalVarSummary> Summary =
+ llvm::make_unique<GlobalVarSummary>(GVFlags,
+ ArrayRef<ValueInfo>{});
+ Index.addGlobalValueSummary(Name, std::move(Summary));
+ }
+ });
+ }
+
// Compute summaries for all functions defined in module, and save in the
// index.
for (auto &F : M) {
@@ -399,7 +451,8 @@ ModuleSummaryIndex llvm::buildModuleSummaryIndex(
BFI = BFIPtr.get();
}
- computeFunctionSummary(Index, M, F, BFI, PSI, !LocalsUsed.empty(),
+ computeFunctionSummary(Index, M, F, BFI, PSI,
+ !LocalsUsed.empty() || HasLocalInlineAsmSymbol,
CantBePromoted);
}
@@ -437,57 +490,6 @@ ModuleSummaryIndex llvm::buildModuleSummaryIndex(
setLiveRoot(Index, "llvm.global_dtors");
setLiveRoot(Index, "llvm.global.annotations");
- if (!M.getModuleInlineAsm().empty()) {
- // Collect the local values defined by module level asm, and set up
- // summaries for these symbols so that they can be marked as NoRename,
- // to prevent export of any use of them in regular IR that would require
- // renaming within the module level asm. Note we don't need to create a
- // summary for weak or global defs, as they don't need to be flagged as
- // NoRename, and defs in module level asm can't be imported anyway.
- // Also, any values used but not defined within module level asm should
- // be listed on the llvm.used or llvm.compiler.used global and marked as
- // referenced from there.
- ModuleSymbolTable::CollectAsmSymbols(
- M, [&M, &Index, &CantBePromoted](StringRef Name,
- object::BasicSymbolRef::Flags Flags) {
- // Symbols not marked as Weak or Global are local definitions.
- if (Flags & (object::BasicSymbolRef::SF_Weak |
- object::BasicSymbolRef::SF_Global))
- return;
- GlobalValue *GV = M.getNamedValue(Name);
- if (!GV)
- return;
- assert(GV->isDeclaration() && "Def in module asm already has definition");
- GlobalValueSummary::GVFlags GVFlags(GlobalValue::InternalLinkage,
- /* NotEligibleToImport = */ true,
- /* Live = */ true);
- CantBePromoted.insert(GlobalValue::getGUID(Name));
- // Create the appropriate summary type.
- if (Function *F = dyn_cast<Function>(GV)) {
- std::unique_ptr<FunctionSummary> Summary =
- llvm::make_unique<FunctionSummary>(
- GVFlags, 0,
- FunctionSummary::FFlags{
- F->hasFnAttribute(Attribute::ReadNone),
- F->hasFnAttribute(Attribute::ReadOnly),
- F->hasFnAttribute(Attribute::NoRecurse),
- F->returnDoesNotAlias()},
- ArrayRef<ValueInfo>{}, ArrayRef<FunctionSummary::EdgeTy>{},
- ArrayRef<GlobalValue::GUID>{},
- ArrayRef<FunctionSummary::VFuncId>{},
- ArrayRef<FunctionSummary::VFuncId>{},
- ArrayRef<FunctionSummary::ConstVCall>{},
- ArrayRef<FunctionSummary::ConstVCall>{});
- Index.addGlobalValueSummary(Name, std::move(Summary));
- } else {
- std::unique_ptr<GlobalVarSummary> Summary =
- llvm::make_unique<GlobalVarSummary>(GVFlags,
- ArrayRef<ValueInfo>{});
- Index.addGlobalValueSummary(Name, std::move(Summary));
- }
- });
- }
-
bool IsThinLTO = true;
if (auto *MD =
mdconst::extract_or_null<ConstantInt>(M.getModuleFlag("ThinLTO")))
OpenPOWER on IntegriCloud