@@ -5,7 +5,7 @@ use std::{
55 sync:: mpsc:: { self , Sender } ,
66} ;
77
8- use anyhow:: { Context , Result } ;
8+ use anyhow:: Result ;
99use dashmap:: DashSet ;
1010
1111use crate :: {
@@ -43,8 +43,8 @@ impl HermesArtifact {
4343 }
4444}
4545
46- /// 1. Scans and rules all reachable source files, printing any errors
47- /// encountered. Collects all items with Hermes annotations .
46+ /// Scans the workspace to identify Hermes entry points (`/// ```lean` blocks)
47+ /// and collects targets for verification .
4848pub fn scan_workspace ( roots : & Roots ) -> Result < Vec < HermesArtifact > > {
4949 log:: trace!( "scan_workspace({:?})" , roots) ;
5050
@@ -117,7 +117,7 @@ pub fn scan_workspace(roots: &Roots) -> Result<Vec<HermesArtifact>> {
117117 . roots
118118 . iter ( )
119119 . filter_map ( |target| {
120- let manifest_path = find_package_root ( & target. src_path ) . ok ( ) ? . join ( "Cargo.toml" ) ;
120+ let manifest_path = target. manifest_path . clone ( ) ;
121121 let start_from = entry_points. remove ( & target. name ) ?;
122122
123123 Some ( HermesArtifact {
@@ -130,20 +130,6 @@ pub fn scan_workspace(roots: &Roots) -> Result<Vec<HermesArtifact>> {
130130 . collect ( ) )
131131}
132132
133- /// Walks up the directory tree from the source file to find the directory
134- /// containing Cargo.toml.
135- fn find_package_root ( src_path : & Path ) -> Result < PathBuf > {
136- let mut current = src_path;
137- while let Some ( parent) = current. parent ( ) {
138- if parent. join ( "Cargo.toml" ) . exists ( ) {
139- return Ok ( parent. to_path_buf ( ) ) ;
140- }
141- current = parent;
142- }
143- // This is highly unlikely if the path came from cargo metadata.
144- anyhow:: bail!( "Could not find Cargo.toml in any parent of {:?}" , src_path)
145- }
146-
147133fn process_file_recursive < ' a > (
148134 scope : & rayon:: Scope < ' a > ,
149135 src_path : & Path ,
@@ -160,78 +146,61 @@ fn process_file_recursive<'a>(
160146 }
161147
162148 // Walking the AST is enough to collect new modules.
163- let result = ( || -> Result < Vec < ( PathBuf , String ) > > {
164- // Walk the AST, collecting new modules to process.
165- let ( _source_code, unloaded_modules) =
166- parse:: read_file_and_scan_compilation_unit ( src_path, |_src, item_result| {
167- match item_result {
168- Ok ( parsed_item) => {
169- if let Some ( item_name) = parsed_item. item . name ( ) {
170- // Calculate the full path to this item.
171- let mut full_path = module_prefix. clone ( ) ;
172- full_path. extend ( parsed_item. module_path ) ;
173- full_path. push ( item_name) ;
174-
175- let _ = path_tx. send ( ( name. clone ( ) , full_path. join ( "::" ) ) ) ;
176- }
177- }
178- Err ( e) => {
179- // A parsing error means we either:
180- // 1. Lost the module graph, causing missing files later.
181- // 2. Lost a specification, causing unsound verification.
182- // We must abort the build.
183- let _ = err_tx. send ( anyhow:: anyhow!( e) ) ;
149+ // Walk the AST, collecting new modules to process.
150+ let ( _source_code, unloaded_modules) =
151+ match parse:: read_file_and_scan_compilation_unit ( src_path, |_src, item_result| {
152+ match item_result {
153+ Ok ( parsed_item) => {
154+ if let Some ( item_name) = parsed_item. item . name ( ) {
155+ // Calculate the full path to this item.
156+ let mut full_path = module_prefix. clone ( ) ;
157+ full_path. extend ( parsed_item. module_path ) ;
158+ full_path. push ( item_name) ;
159+
160+ let _ = path_tx. send ( ( name. clone ( ) , full_path. join ( "::" ) ) ) ;
184161 }
185162 }
186- } )
187- . context ( format ! ( "Failed to parse {:?}" , src_path) ) ?;
188-
189- // Resolve and queue child modules for processing.
190- let base_dir = src_path. parent ( ) . unwrap ( ) ;
191- let mut next_paths = Vec :: new ( ) ;
192- for module in unloaded_modules {
193- if let Some ( mod_path) =
194- resolve_module_path ( base_dir, & module. name , module. path_attr . as_deref ( ) )
195- {
196- next_paths. push ( ( mod_path, module. name ) ) ;
197- } else {
198- // This is an expected condition – it shows up when modules are
199- // conditionally compiled. Instead of implementing conditional
200- // compilation ourselves, we can just let rustc error later if
201- // this is actually an error.
202- log:: debug!( "Could not resolve module '{}' in {:?}" , module. name, src_path) ;
163+ Err ( e) => {
164+ // A parsing error means we either:
165+ // 1. Lost the module graph, causing missing files later.
166+ // 2. Lost a specification, causing unsound verification.
167+ // We must abort the build.
168+ let _ = err_tx. send ( anyhow:: anyhow!( e) ) ;
169+ }
203170 }
204- }
205-
206- Ok ( next_paths)
207- } ) ( ) ;
208-
209- match result {
210- Ok ( children) => {
171+ } ) {
172+ Ok ( res) => res,
173+ Err ( e) => {
174+ let _ = err_tx
175+ . send ( anyhow:: anyhow!( e) . context ( format ! ( "Failed to parse {:?}" , src_path) ) ) ;
176+ return ;
177+ }
178+ } ;
179+
180+ // Resolve and queue child modules for processing.
181+ let base_dir = src_path. parent ( ) . unwrap ( ) ;
182+ for module in unloaded_modules {
183+ if let Some ( mod_path) =
184+ resolve_module_path ( base_dir, & module. name , module. path_attr . as_deref ( ) )
185+ {
211186 // Spawn new tasks for discovered modules.
212- for ( child_path, mod_name) in children {
213- let ( err_tx, path_tx) = ( err_tx. clone ( ) , path_tx. clone ( ) ) ;
187+ let ( err_tx, path_tx) = ( err_tx. clone ( ) , path_tx. clone ( ) ) ;
214188
215- let mut new_prefix = module_prefix. clone ( ) ;
216- new_prefix. push ( mod_name ) ;
189+ let mut new_prefix = module_prefix. clone ( ) ;
190+ new_prefix. push ( module . name ) ;
217191
218- let name = name. clone ( ) ;
219- scope. spawn ( move |s| {
220- process_file_recursive (
221- s,
222- & child_path,
223- config,
224- visited,
225- err_tx,
226- path_tx,
227- new_prefix,
228- name,
229- )
230- } )
231- }
232- }
233- Err ( e) => {
234- let _ = err_tx. send ( e) ;
192+ let name = name. clone ( ) ;
193+ scope. spawn ( move |s| {
194+ process_file_recursive (
195+ s, & mod_path, config, visited, err_tx, path_tx, new_prefix, name,
196+ )
197+ } )
198+ } else {
199+ // This is an expected condition – it shows up when modules are
200+ // conditionally compiled. Instead of implementing conditional
201+ // compilation ourselves, we can just let rustc error later if
202+ // this is actually an error.
203+ log:: debug!( "Could not resolve module '{}' in {:?}" , module. name, src_path) ;
235204 }
236205 }
237206}
0 commit comments