1- use std:: process:: id;
2-
31use crate :: {
42 ps:: {
53 LoopStatus :: { Dead , Inifite , OneTurn } ,
@@ -107,6 +105,7 @@ impl<'a> RuleMut<'a> for ForStatementCondition {
107105/// # Example
108106/// ```
109107/// use minusone::tree::{HashMapStorage, Tree};
108+ /// use minusone::engine::CleanEngine;
110109/// use minusone::ps::build_powershell_tree;
111110/// use minusone::ps::linter::Linter;
112111/// use minusone::ps::forward::Forward;
@@ -125,8 +124,9 @@ impl<'a> RuleMut<'a> for ForStatementCondition {
125124///
126125/// let mut ps_litter_view = Linter::default();
127126/// tree.apply(&mut ps_litter_view).unwrap();
127+ /// let clean = CleanEngine::from_powershell(&ps_litter_view.output).unwrap().clean().unwrap();
128128///
129- /// assert_eq!(ps_litter_view.output , "42");
129+ /// assert_eq!(clean.trim() , "42");
130130/// ```
131131#[ derive( Default ) ]
132132pub struct ForStatementFlowControl {
@@ -144,7 +144,14 @@ impl<'a> RuleMut<'a> for ForStatementFlowControl {
144144 _flow : crate :: tree:: ControlFlow ,
145145 ) -> crate :: error:: MinusOneResult < ( ) > {
146146 if matches ! ( node. view( ) . kind( ) , "while_statement" | "for_statement" ) {
147- self . loop_id = Some ( node. id ( ) ) ;
147+ if self . loop_id . is_none ( ) {
148+ self . loop_id = Some ( node. id ( ) ) ;
149+ } else {
150+ // We don't support nested loops
151+ self . loop_id = None ;
152+ self . iterators . clear ( ) ;
153+ self . statment_count = 0 ;
154+ }
148155 }
149156
150157 Ok ( ( ) )
@@ -162,12 +169,14 @@ impl<'a> RuleMut<'a> for ForStatementFlowControl {
162169 self . iterators . clear ( ) ;
163170 self . statment_count = 0 ;
164171 }
165- // Track control flow statments
166172 "flow_control_statement" => {
167- // TODO: Review control flow count if we are in imbricated loops
168- self . statment_count += 1 ;
173+ // Update the statement count only if in followed loop
174+ // Skip in nested loops
175+ if self . loop_id . is_some ( ) {
176+ self . statment_count += 1 ;
177+ }
169178
170- // Infer dead code afer flow control in a loop
179+ // Infer dead code afer flow control in a loop, even in nested ones
171180 let following_children_ids: Vec < usize > = view
172181 . parent ( )
173182 . unwrap ( )
@@ -180,7 +189,12 @@ impl<'a> RuleMut<'a> for ForStatementFlowControl {
180189 }
181190 }
182191 "assignment_expression"
183- if view. get_parent_of_types ( vec ! [ "for_initializer" ] ) . is_some ( ) =>
192+ if view. get_parent_of_types ( vec ! [ "for_initializer" ] ) . is_some ( )
193+ && self . loop_id . is_some ( )
194+ && view
195+ . get_parent_of_types ( vec ! [ "for_statement" ] )
196+ . map ( |n| n. id ( ) )
197+ == self . loop_id =>
184198 {
185199 if let ( Some ( left) , Some ( right) ) = ( view. child ( 0 ) , view. child ( 2 ) ) {
186200 if let Some ( Powershell :: Raw ( value) ) = right. data ( ) {
@@ -203,6 +217,7 @@ impl<'a> RuleMut<'a> for ForStatementFlowControl {
203217 "statement_block" => {
204218 let parent = view. parent ( ) . unwrap ( ) ;
205219 if matches ! ( parent. kind( ) , "while_statement" | "for_statement" )
220+ && self . loop_id == Some ( parent. id ( ) )
206221 && parent. data ( ) . is_none ( )
207222 && self . statment_count == 1
208223 {
0 commit comments