diff options
Diffstat (limited to 'llvm/lib/Transforms')
-rw-r--r-- | llvm/lib/Transforms/IPO/ArgumentPromotion.cpp | 6 | ||||
-rw-r--r-- | llvm/lib/Transforms/IPO/FunctionAttrs.cpp | 6 | ||||
-rw-r--r-- | llvm/lib/Transforms/IPO/GlobalOpt.cpp | 5 |
3 files changed, 15 insertions, 2 deletions
diff --git a/llvm/lib/Transforms/IPO/ArgumentPromotion.cpp b/llvm/lib/Transforms/IPO/ArgumentPromotion.cpp index d3a7b0e76fe..461c4e12cbd 100644 --- a/llvm/lib/Transforms/IPO/ArgumentPromotion.cpp +++ b/llvm/lib/Transforms/IPO/ArgumentPromotion.cpp @@ -817,6 +817,12 @@ promoteArguments(Function *F, function_ref<AAResults &(Function &F)> AARGetter, unsigned MaxElements, Optional<function_ref<void(CallSite OldCS, CallSite NewCS)>> ReplaceCallSite) { + // Don't perform argument promotion for naked functions; otherwise we can end + // up removing parameters that are seemingly 'not used' as they are referred + // to in the assembly. + if(F->hasFnAttribute(Attribute::Naked)) + return nullptr; + // Make sure that it is local to this module. if (!F->hasLocalLinkage()) return nullptr; diff --git a/llvm/lib/Transforms/IPO/FunctionAttrs.cpp b/llvm/lib/Transforms/IPO/FunctionAttrs.cpp index 5352e32479b..353daece48e 100644 --- a/llvm/lib/Transforms/IPO/FunctionAttrs.cpp +++ b/llvm/lib/Transforms/IPO/FunctionAttrs.cpp @@ -1136,7 +1136,8 @@ PreservedAnalyses PostOrderFunctionAttrsPass::run(LazyCallGraph::SCC &C, bool HasUnknownCall = false; for (LazyCallGraph::Node &N : C) { Function &F = N.getFunction(); - if (F.hasFnAttribute(Attribute::OptimizeNone)) { + if (F.hasFnAttribute(Attribute::OptimizeNone) || + F.hasFnAttribute(Attribute::Naked)) { // Treat any function we're trying not to optimize as if it were an // indirect call and omit it from the node set used below. HasUnknownCall = true; @@ -1221,7 +1222,8 @@ static bool runImpl(CallGraphSCC &SCC, AARGetterT AARGetter) { bool ExternalNode = false; for (CallGraphNode *I : SCC) { Function *F = I->getFunction(); - if (!F || F->hasFnAttribute(Attribute::OptimizeNone)) { + if (!F || F->hasFnAttribute(Attribute::OptimizeNone) || + F->hasFnAttribute(Attribute::Naked)) { // External node or function we're trying not to optimize - we both avoid // transform them and avoid leveraging information they provide. ExternalNode = true; diff --git a/llvm/lib/Transforms/IPO/GlobalOpt.cpp b/llvm/lib/Transforms/IPO/GlobalOpt.cpp index 9dfb61d3d73..274ecf0a099 100644 --- a/llvm/lib/Transforms/IPO/GlobalOpt.cpp +++ b/llvm/lib/Transforms/IPO/GlobalOpt.cpp @@ -2221,6 +2221,11 @@ OptimizeFunctions(Module &M, TargetLibraryInfo *TLI, for (Module::iterator FI = M.begin(), E = M.end(); FI != E; ) { Function *F = &*FI++; + // Don't perform global opt pass on naked functions; we don't want fast + // calling conventions for naked functions. + if (F->hasFnAttribute(Attribute::Naked)) + continue; + // Functions without names cannot be referenced outside this module. if (!F->hasName() && !F->isDeclaration() && !F->hasLocalLinkage()) F->setLinkage(GlobalValue::InternalLinkage); |