diff options
author | Dan Gohman <gohman@apple.com> | 2012-06-25 19:47:37 +0000 |
---|---|---|
committer | Dan Gohman <gohman@apple.com> | 2012-06-25 19:47:37 +0000 |
commit | 58fb3401fa63174cd37281d167b16d90e84a47be (patch) | |
tree | 43df538c7f8323faf73ce797f5d6853052caa759 /lib/Transforms | |
parent | a4e6397fd9f2fbbd6affdfb0738813918cb21da0 (diff) |
Fix the objc_autoreleasedReturnValue optimization code to locate
the call correctly even in the case where it is an invoke. This
fixes rdar://11714057.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@159157 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Transforms')
-rw-r--r-- | lib/Transforms/Scalar/ObjCARC.cpp | 19 |
1 files changed, 17 insertions, 2 deletions
diff --git a/lib/Transforms/Scalar/ObjCARC.cpp b/lib/Transforms/Scalar/ObjCARC.cpp index d89996a1ff..87e17c7f90 100644 --- a/lib/Transforms/Scalar/ObjCARC.cpp +++ b/lib/Transforms/Scalar/ObjCARC.cpp @@ -4064,8 +4064,22 @@ bool ObjCARCContract::runOnFunction(Function &F) { if (!RetainRVMarker) break; BasicBlock::iterator BBI = Inst; - --BBI; - while (isNoopInstruction(BBI)) --BBI; + BasicBlock *InstParent = Inst->getParent(); + + // Step up to see if the call immediately precedes the RetainRV call. + // If it's an invoke, we have to cross a block boundary. And we have + // to carefully dodge no-op instructions. + do { + if (&*BBI == InstParent->begin()) { + BasicBlock *Pred = InstParent->getSinglePredecessor(); + if (!Pred) + goto decline_rv_optimization; + BBI = Pred->getTerminator(); + break; + } + --BBI; + } while (isNoopInstruction(BBI)); + if (&*BBI == GetObjCArg(Inst)) { Changed = true; InlineAsm *IA = @@ -4075,6 +4089,7 @@ bool ObjCARCContract::runOnFunction(Function &F) { /*Constraints=*/"", /*hasSideEffects=*/true); CallInst::Create(IA, "", Inst); } + decline_rv_optimization: break; } case IC_InitWeak: { |