diff --git a/llvm/lib/Transforms/Scalar/LoopDeletion.cpp b/llvm/lib/Transforms/Scalar/LoopDeletion.cpp --- a/llvm/lib/Transforms/Scalar/LoopDeletion.cpp +++ b/llvm/lib/Transforms/Scalar/LoopDeletion.cpp @@ -58,6 +58,11 @@ return LoopDeletionResult::Unmodified; } +static bool loopHasAddressTaken(Loop *L) { + return any_of(L->blocks(), + [](BasicBlock *BB) { return BB->hasAddressTaken(); }); +} + /// Determines if a loop is dead. /// /// This assumes that we've already checked for unique exit and exiting blocks, @@ -453,6 +458,11 @@ return LoopDeletionResult::Unmodified; } + if (loopHasAddressTaken(L)) { + LLVM_DEBUG(dbgs() << "Loop has address taken, cannot delete.\n"); + return LoopDeletionResult::Unmodified; + } + BasicBlock *ExitBlock = L->getUniqueExitBlock(); if (ExitBlock && isLoopNeverExecuted(L)) { diff --git a/llvm/test/Transforms/LoopDeletion/blockaddress.ll b/llvm/test/Transforms/LoopDeletion/blockaddress.ll --- a/llvm/test/Transforms/LoopDeletion/blockaddress.ll +++ b/llvm/test/Transforms/LoopDeletion/blockaddress.ll @@ -6,11 +6,13 @@ declare void @g(ptr) ;. -; CHECK: @[[BA:[a-zA-Z0-9_$"\\.-]+]] = private constant ptr inttoptr (i32 1 to ptr) +; CHECK: @[[BA:[a-zA-Z0-9_$"\\.-]+]] = private constant ptr blockaddress(@f, [[BB:%.*]]) ;. define void @f() { ; CHECK-LABEL: @f( ; CHECK-NEXT: entry: +; CHECK-NEXT: br label [[BB:%.*]] +; CHECK: bb: ; CHECK-NEXT: br label [[BB2:%.*]] ; CHECK: bb2: ; CHECK-NEXT: call void @g(ptr @ba)