1
- use umpl;
1
+ use umpl:: { self , parser :: Thing } ;
2
2
3
3
use std:: { error:: Error , fmt} ;
4
4
@@ -10,6 +10,16 @@ pub struct UMPLFunction {
10
10
pub ( crate ) lines : ( usize , usize ) ,
11
11
pub ( crate ) name : String ,
12
12
pub ( crate ) body : String ,
13
+ pub ( crate ) args_count : usize ,
14
+ pub ( crate ) parents : Vec < UMPLParentFunction > ,
15
+ }
16
+ #[ derive( Debug , Clone , PartialEq , Eq ) ]
17
+ pub struct UMPLParentFunction {
18
+ pub ( crate ) lines : ( usize , usize ) ,
19
+ pub ( crate ) name : String ,
20
+ pub ( crate ) top : String ,
21
+ pub ( crate ) bottom : String ,
22
+ pub ( crate ) args_count : usize ,
13
23
}
14
24
15
25
impl fmt:: Display for UMPLFunction {
@@ -43,8 +53,55 @@ pub(crate) fn find_function_in_file(
43
53
let tokens = lexed. scan_tokens ( ) ;
44
54
let mut parsed = umpl:: parser:: Parser :: new ( tokens) ;
45
55
let ast = parsed. parse ( ) ;
46
- for node in ast { }
47
- Err ( "" ) ?
56
+ let res = find_function_recurse ( name, ast, & vec ! [ ] ) ;
57
+ if res. len ( ) > 0 {
58
+ return Ok ( res) ;
59
+ }
60
+ Err ( "no function found" ) ?
61
+ }
62
+
63
+ fn find_function_recurse ( name : & str , ast : Vec < Thing > , current : & Vec < UMPLParentFunction > ) -> Vec < ( UMPLFunction ) > {
64
+ let mut results = Vec :: new ( ) ;
65
+ for node in ast {
66
+ match node {
67
+ Thing :: Function ( fns) => {
68
+ if fns. name . to_string ( ) == name {
69
+ let new_fn = UMPLFunction {
70
+ lines : ( fns. line as usize , fns. end_line as usize ) ,
71
+ name : fns. name . to_string ( ) ,
72
+ // TODO: get the function body
73
+ body : String :: new ( ) ,
74
+ args_count : fns. num_arguments as usize ,
75
+ parents : current. clone ( )
76
+ } ;
77
+ results. push ( new_fn) ;
78
+ } else {
79
+ let mut new_current = current. clone ( ) ;
80
+ // turn into a parent function
81
+ let pfn = UMPLParentFunction {
82
+ lines : ( fns. line as usize , fns. end_line as usize ) ,
83
+ name : fns. name . to_string ( ) ,
84
+ // TODO: get the top and bottom lines
85
+ top : String :: new ( ) ,
86
+ bottom : String :: new ( ) ,
87
+ args_count : fns. num_arguments as usize
88
+ } ;
89
+ new_current. push ( pfn) ;
90
+ results. append ( & mut find_function_recurse ( name, fns. body , & new_current) ) ;
91
+ }
92
+ }
93
+ Thing :: LoopStatement ( loops) => {
94
+ results. append ( & mut find_function_recurse ( name, loops. body , current) ) ;
95
+ }
96
+ Thing :: IfStatement ( ifs) => {
97
+ results. append ( & mut find_function_recurse ( name, ifs. body_true , current) ) ;
98
+ results. append ( & mut find_function_recurse ( name, ifs. body_false , current) ) ;
99
+ }
100
+ _ => { }
101
+ }
102
+ }
103
+ results
104
+
48
105
}
49
106
50
107
#[ derive( Debug , Clone , PartialEq , Eq ) ]
@@ -54,4 +111,4 @@ impl UMPLFilter {
54
111
pub fn matches ( & self , function : & UMPLFunction ) -> bool {
55
112
false
56
113
}
57
- }
114
+ }
0 commit comments