@@ -6,7 +6,7 @@ use std::{u32, vec};
66use ruff_text_size:: { Ranged , TextRange , TextSize } ;
77use ruff_python_ast:: { Alias , Expr , Identifier , Stmt , StmtAnnAssign , StmtAssign , StmtClassDef , StmtExpr , StmtFor , StmtFunctionDef , StmtIf , StmtReturn , StmtTry , StmtWhile , StmtWith } ;
88use lsp_types:: { Diagnostic , DiagnosticSeverity , NumberOrString , Position , Range } ;
9- use tracing:: { debug, trace} ;
9+ use tracing:: { debug, trace, warn } ;
1010
1111use crate :: constants:: * ;
1212use crate :: core:: import_resolver:: resolve_import_stmt;
@@ -306,20 +306,26 @@ impl PythonArchEval {
306306 if let Some ( variable_rc) = variable {
307307 let parent = variable_rc. borrow ( ) . parent ( ) . unwrap ( ) . upgrade ( ) . unwrap ( ) . clone ( ) ;
308308 if assign. annotation . is_some ( ) {
309- let ( eval, diags) = Evaluation :: eval_from_ast ( session, & assign. annotation . as_ref ( ) . unwrap ( ) , parent, & ann_assign_stmt. range . start ( ) ) ;
309+ let ( eval, diags) = Evaluation :: eval_from_ast ( session, & assign. annotation . as_ref ( ) . unwrap ( ) , parent. clone ( ) , & ann_assign_stmt. range . start ( ) ) ;
310310 variable_rc. borrow_mut ( ) . set_evaluations ( eval) ;
311311 self . diagnostics . extend ( diags) ;
312312 } else if assign. value . is_some ( ) {
313- let ( eval, diags) = Evaluation :: eval_from_ast ( session, & assign. value . as_ref ( ) . unwrap ( ) , parent, & ann_assign_stmt. range . start ( ) ) ;
313+ let ( eval, diags) = Evaluation :: eval_from_ast ( session, & assign. value . as_ref ( ) . unwrap ( ) , parent. clone ( ) , & ann_assign_stmt. range . start ( ) ) ;
314314 variable_rc. borrow_mut ( ) . set_evaluations ( eval) ;
315315 self . diagnostics . extend ( diags) ;
316316 } else {
317317 panic ! ( "either value or annotation should exists" ) ;
318318 }
319319 let mut dep_to_add = vec ! [ ] ;
320- let v_mut = variable_rc . borrow_mut ( ) ;
321- for evaluation in v_mut . evaluations ( ) . unwrap ( ) . iter ( ) {
320+ let mut evals_to_drop : Vec < usize > = vec ! [ ] ;
321+ for ( ix , evaluation) in variable_rc . borrow ( ) . evaluations ( ) . unwrap ( ) . iter ( ) . enumerate ( ) {
322322 if let Some ( sym) = evaluation. symbol . get_symbol_as_weak ( session, & mut None , & mut self . diagnostics , None ) . weak . upgrade ( ) {
323+ if Rc :: ptr_eq ( & sym, & variable_rc) {
324+ // TODO: investigate deps, and fix cyclic evals
325+ warn ! ( "Found cyclic evaluation symbol: {}, parent: {}" , sym. borrow( ) . name( ) , parent. borrow( ) . name( ) ) ;
326+ evals_to_drop. push ( ix) ;
327+ continue ;
328+ }
323329 if let Some ( file) = sym. borrow ( ) . get_file ( ) . clone ( ) {
324330 let sym_file = file. upgrade ( ) . unwrap ( ) . clone ( ) ;
325331 if !Rc :: ptr_eq ( & self . file , & sym_file) {
@@ -335,7 +341,10 @@ impl PythonArchEval {
335341 }
336342 }
337343 }
338- drop ( v_mut) ;
344+ let mut v_mut = variable_rc. borrow_mut ( ) ;
345+ for ix in evals_to_drop. into_iter ( ) {
346+ v_mut. evaluations_mut ( ) . unwrap ( ) . remove ( ix) ;
347+ }
339348 for dep in dep_to_add {
340349 self . file . borrow_mut ( ) . add_dependency ( & mut dep. borrow_mut ( ) , self . current_step , BuildSteps :: ARCH ) ;
341350 }
@@ -351,13 +360,19 @@ impl PythonArchEval {
351360 let variable = self . sym_stack . last ( ) . unwrap ( ) . borrow_mut ( ) . get_positioned_symbol ( & assign. target . id . to_string ( ) , & assign. target . range ) ;
352361 if let Some ( variable_rc) = variable {
353362 let parent = variable_rc. borrow ( ) . parent ( ) . as_ref ( ) . unwrap ( ) . upgrade ( ) . unwrap ( ) . clone ( ) ;
354- let ( eval, diags) = Evaluation :: eval_from_ast ( session, & assign. value . as_ref ( ) . unwrap ( ) , parent, & assign_stmt. range . start ( ) ) ;
363+ let ( eval, diags) = Evaluation :: eval_from_ast ( session, & assign. value . as_ref ( ) . unwrap ( ) , parent. clone ( ) , & assign_stmt. range . start ( ) ) ;
355364 variable_rc. borrow_mut ( ) . set_evaluations ( eval) ;
356365 self . diagnostics . extend ( diags) ;
357366 let mut dep_to_add = vec ! [ ] ;
358- let v_mut = variable_rc . borrow_mut ( ) ;
359- for evaluation in v_mut . evaluations ( ) . unwrap ( ) . iter ( ) {
367+ let mut evals_to_drop : Vec < usize > = vec ! [ ] ;
368+ for ( ix , evaluation) in variable_rc . borrow ( ) . evaluations ( ) . unwrap ( ) . iter ( ) . enumerate ( ) {
360369 if let Some ( sym) = evaluation. symbol . get_symbol_as_weak ( session, & mut None , & mut self . diagnostics , None ) . weak . upgrade ( ) {
370+ if Rc :: ptr_eq ( & sym, & variable_rc) {
371+ // TODO: investigate deps, and fix cyclic evals
372+ warn ! ( "Found cyclic evaluation symbol: {}, parent: {}" , sym. borrow( ) . name( ) , parent. borrow( ) . name( ) ) ;
373+ evals_to_drop. push ( ix) ;
374+ continue ;
375+ }
361376 if let Some ( file) = sym. borrow ( ) . get_file ( ) . clone ( ) {
362377 let sym_file = file. upgrade ( ) . unwrap ( ) . clone ( ) ;
363378 if !Rc :: ptr_eq ( & self . file , & sym_file) {
@@ -373,7 +388,10 @@ impl PythonArchEval {
373388 }
374389 }
375390 }
376- drop ( v_mut) ;
391+ let mut v_mut = variable_rc. borrow_mut ( ) ;
392+ for ix in evals_to_drop. into_iter ( ) {
393+ v_mut. evaluations_mut ( ) . unwrap ( ) . remove ( ix) ;
394+ }
377395 for dep in dep_to_add {
378396 self . file . borrow_mut ( ) . add_dependency ( & mut dep. borrow_mut ( ) , self . current_step , BuildSteps :: ARCH ) ;
379397 }
0 commit comments