diff options
| author | Pete Cooper <peter_cooper@apple.com> | 2019-01-03 01:38:08 +0000 |
|---|---|---|
| committer | Pete Cooper <peter_cooper@apple.com> | 2019-01-03 01:38:08 +0000 |
| commit | 697281df42916d736cc23e74c2a2b2275786c43f (patch) | |
| tree | b9ee5c2c9551079578769dc8bf5a081b65cc8df5 /llvm/lib/Transforms | |
| parent | ddc62017ea18ea08afc6c4b1e5c57198f1222e36 (diff) | |
| download | bcm5719-llvm-697281df42916d736cc23e74c2a2b2275786c43f.tar.gz bcm5719-llvm-697281df42916d736cc23e74c2a2b2275786c43f.zip | |
Teach ObjCARC optimizer about equivalent PHIs when eliminating autoreleaseRV/retainRV pairs
OptimizeAutoreleaseRVCall skips optimizing llvm.objc.autoreleaseReturnValue if it
sees a user which is llvm.objc.retainAutoreleasedReturnValue, and if they have
equivalent arguments (either identical or equivalent PHIs). It then assumes that
ObjCARCOpt::OptimizeRetainRVCall will optimize the pair instead.
Trouble is, ObjCARCOpt::OptimizeRetainRVCall doesn't know about equivalent PHIs
so optimizes in a different way and we are left with an unoptimized llvm.objc.autoreleaseReturnValue.
This teaches ObjCARCOpt::OptimizeRetainRVCall to also understand PHI equivalence.
rdar://problem/47005143
Reviewed By: ahatanak
Differential Revision: https://reviews.llvm.org/D56235
llvm-svn: 350284
Diffstat (limited to 'llvm/lib/Transforms')
| -rw-r--r-- | llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp | 13 |
1 files changed, 12 insertions, 1 deletions
diff --git a/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp b/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp index 6ffaadc2b5f..9a02174556f 100644 --- a/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp +++ b/llvm/lib/Transforms/ObjCARC/ObjCARCOpts.cpp @@ -600,6 +600,17 @@ ObjCARCOpt::OptimizeRetainRVCall(Function &F, Instruction *RetainRV) { } } + // Track PHIs which are equivalent to our Arg. + SmallDenseSet<const Value*, 2> EquivalentArgs; + EquivalentArgs.insert(Arg); + + // Add PHIs that are equivalent to Arg to ArgUsers. + if (const PHINode *PN = dyn_cast<PHINode>(Arg)) { + SmallVector<const Value *, 2> ArgUsers; + getEquivalentPHIs(*PN, ArgUsers); + EquivalentArgs.insert(ArgUsers.begin(), ArgUsers.end()); + } + // Check for being preceded by an objc_autoreleaseReturnValue on the same // pointer. In this case, we can delete the pair. BasicBlock::iterator I = RetainRV->getIterator(), @@ -609,7 +620,7 @@ ObjCARCOpt::OptimizeRetainRVCall(Function &F, Instruction *RetainRV) { --I; while (I != Begin && IsNoopInstruction(&*I)); if (GetBasicARCInstKind(&*I) == ARCInstKind::AutoreleaseRV && - GetArgRCIdentityRoot(&*I) == Arg) { + EquivalentArgs.count(GetArgRCIdentityRoot(&*I))) { Changed = true; ++NumPeeps; |

