@@ -1193,10 +1193,8 @@ private function processStmtNode(
11931193
11941194 if ($ alwaysIterates ) {
11951195 $ isAlwaysTerminating = count ($ finalScopeResult ->getExitPointsByType (Break_::class)) === 0 ;
1196- } elseif ($ isIterableAtLeastOnce ) {
1197- $ isAlwaysTerminating = $ finalScopeResult ->isAlwaysTerminating ();
11981196 } else {
1199- $ isAlwaysTerminating = false ;
1197+ $ isAlwaysTerminating = $ isIterableAtLeastOnce && $ finalScopeResult -> isAlwaysTerminating () ;
12001198 }
12011199 $ condScope = $ condResult ->getFalseyScope ();
12021200 if (!$ isIterableAtLeastOnce ) {
@@ -1313,6 +1311,7 @@ private function processStmtNode(
13131311 }
13141312
13151313 $ bodyScope = $ initScope ;
1314+ $ alwaysIterates = $ stmt ->cond === [] && $ context ->isTopLevel ();
13161315 $ isIterableAtLeastOnce = TrinaryLogic::createYes ();
13171316 foreach ($ stmt ->cond as $ condExpr ) {
13181317 $ condResult = $ this ->processExprNode ($ stmt , $ condExpr , $ bodyScope , static function (): void {
@@ -1410,10 +1409,16 @@ private function processStmtNode(
14101409 }
14111410 }
14121411
1412+ if ($ alwaysIterates ) {
1413+ $ isAlwaysTerminating = count ($ finalScopeResult ->getExitPointsByType (Break_::class)) === 0 ;
1414+ } else {
1415+ $ isAlwaysTerminating = false ; // $finalScopeResult->isAlwaysTerminating() && $isAlwaysIterable
1416+ }
1417+
14131418 return new StatementResult (
14141419 $ finalScope ,
14151420 $ finalScopeResult ->hasYield () || $ hasYield ,
1416- false /* $finalScopeResult-> isAlwaysTerminating() && $isAlwaysIterable*/ ,
1421+ $ isAlwaysTerminating ,
14171422 $ finalScopeResult ->getExitPointsForOuterLoop (),
14181423 array_merge ($ throwPoints , $ finalScopeResult ->getThrowPoints ()),
14191424 array_merge ($ impurePoints , $ finalScopeResult ->getImpurePoints ()),
0 commit comments