# UNDF: UNDF-2026-000000154 diff --git a/llvm/lib/Transforms/Utils/LCSSA.cpp b/llvm/lib/Transforms/Utils/LCSSA.cpp index 1a2b3c4..2d3e4f5 100644 --- a/llvm/lib/Transforms/Utils/LCSSA.cpp +++ b/llvm/lib/Transforms/Utils/LCSSA.cpp @@ -65,9 +65,12 @@ static cl::opt cl::desc("Verify loop lcssa form (time consuming)")); /// Return true if the specified block is in the list. +// CWE-407 fix: caller now passes a SmallPtrSet for O(1) membership instead of +// a SmallVectorImpl whose is_contained was O(X) per use in the worklist loop. static bool isExitBlock(BasicBlock *BB, - const SmallVectorImpl &ExitBlocks) { - return is_contained(ExitBlocks, BB); + const SmallPtrSetImpl &ExitBlockSet) { + return ExitBlockSet.count(BB); // CWE-407 fix: O(1) } // Cache the Loop ExitBlocks computed during the analysis. We expect to get a @@ -74,7 +77,9 @@ static bool isExitBlock(BasicBlock *BB, // expensive, and we're not mutating the loop structure. -using LoopExitBlocksTy = SmallDenseMap>; +// CWE-407 fix: store both a vector (for iteration) and a set (for O(1) lookup). +using LoopExitVecTy = SmallVector; +using LoopExitSetTy = SmallPtrSet; +using LoopExitBlocksTy = SmallDenseMap>; /// For every instruction from the worklist, check to see if it has any uses /// that are outside the current loop. If so, insert LCSSA PHI nodes and @@ -97,13 +103,17 @@ formLCSSAForInstructionsImpl(SmallVectorImpl &Worklist, auto [It, Inserted] = LoopExitBlocks.try_emplace(L); if (Inserted) - L->getExitBlocks(It->second); - const SmallVectorImpl &ExitBlocks = It->second; + { + L->getExitBlocks(It->second.first); + It->second.second.insert(It->second.first.begin(), + It->second.first.end()); + } + const LoopExitVecTy &ExitBlocks = It->second.first; + const SmallPtrSetImpl &ExitBlockSet = It->second.second; if (ExitBlocks.empty()) continue; @@ -225,7 +235,7 @@ formLCSSAForInstructionsImpl(SmallVectorImpl &Worklist, if (isa(UserBB->begin()) && isExitBlock(UserBB, ExitBlocks)) { + if (isa(UserBB->begin()) && isExitBlock(UserBB, ExitBlockSet)) { UseToRewrite->set(&UserBB->front()); continue; }