11use crate :: diagnostics:: { ExtractionStep , emit_extraction_diagnostics} ;
22use crate :: rust_analyzer:: path_to_file_id;
3- use crate :: translate:: ResolvePaths ;
3+ use crate :: translate:: { ResolvePaths , SourceKind } ;
44use crate :: trap:: TrapId ;
55use anyhow:: Context ;
66use archive:: Archiver ;
@@ -12,6 +12,7 @@ use ra_ap_paths::{AbsPathBuf, Utf8PathBuf};
1212use ra_ap_project_model:: { CargoConfig , ProjectManifest } ;
1313use ra_ap_vfs:: Vfs ;
1414use rust_analyzer:: { ParseResult , RustAnalyzer } ;
15+ use std:: collections:: HashSet ;
1516use std:: time:: Instant ;
1617use std:: {
1718 collections:: HashMap ,
@@ -47,9 +48,14 @@ impl<'a> Extractor<'a> {
4748 }
4849 }
4950
50- fn extract ( & mut self , rust_analyzer : & RustAnalyzer , file : & Path , resolve_paths : ResolvePaths ) {
51+ fn extract (
52+ & mut self ,
53+ rust_analyzer : & RustAnalyzer ,
54+ file : & Path ,
55+ resolve_paths : ResolvePaths ,
56+ source_kind : SourceKind ,
57+ ) {
5158 self . archiver . archive ( file) ;
52-
5359 let before_parse = Instant :: now ( ) ;
5460 let ParseResult {
5561 ast,
@@ -71,6 +77,7 @@ impl<'a> Extractor<'a> {
7177 line_index,
7278 semantics_info. as_ref ( ) . ok ( ) ,
7379 resolve_paths,
80+ source_kind,
7481 ) ;
7582
7683 for err in errors {
@@ -110,15 +117,27 @@ impl<'a> Extractor<'a> {
110117 semantics : & Semantics < ' _ , RootDatabase > ,
111118 vfs : & Vfs ,
112119 resolve_paths : ResolvePaths ,
120+ source_kind : SourceKind ,
113121 ) {
114- self . extract ( & RustAnalyzer :: new ( vfs, semantics) , file, resolve_paths) ;
122+ self . extract (
123+ & RustAnalyzer :: new ( vfs, semantics) ,
124+ file,
125+ resolve_paths,
126+ source_kind,
127+ ) ;
115128 }
116129
117- pub fn extract_without_semantics ( & mut self , file : & Path , reason : & str ) {
130+ pub fn extract_without_semantics (
131+ & mut self ,
132+ file : & Path ,
133+ source_kind : SourceKind ,
134+ reason : & str ,
135+ ) {
118136 self . extract (
119137 & RustAnalyzer :: WithoutSemantics { reason } ,
120138 file,
121139 ResolvePaths :: No ,
140+ source_kind,
122141 ) ;
123142 }
124143
@@ -246,7 +265,7 @@ fn main() -> anyhow::Result<()> {
246265 continue ' outer;
247266 }
248267 }
249- extractor. extract_without_semantics ( file, "no manifest found" ) ;
268+ extractor. extract_without_semantics ( file, SourceKind :: Source , "no manifest found" ) ;
250269 }
251270 let cwd = cwd ( ) ?;
252271 let ( cargo_config, load_cargo_config) = cfg. to_cargo_config ( & cwd) ;
@@ -255,6 +274,7 @@ fn main() -> anyhow::Result<()> {
255274 } else {
256275 ResolvePaths :: Yes
257276 } ;
277+ let mut processed_files = HashSet :: new ( ) ;
258278 for ( manifest, files) in map. values ( ) . filter ( |( _, files) | !files. is_empty ( ) ) {
259279 if let Some ( ( ref db, ref vfs) ) =
260280 extractor. load_manifest ( manifest, & cargo_config, & load_cargo_config)
@@ -266,16 +286,43 @@ fn main() -> anyhow::Result<()> {
266286 . push ( ExtractionStep :: crate_graph ( before_crate_graph) ) ;
267287 let semantics = Semantics :: new ( db) ;
268288 for file in files {
289+ processed_files. insert ( ( * file) . to_owned ( ) ) ;
269290 match extractor. load_source ( file, & semantics, vfs) {
270- Ok ( ( ) ) => {
271- extractor. extract_with_semantics ( file, & semantics, vfs, resolve_paths)
291+ Ok ( ( ) ) => extractor. extract_with_semantics (
292+ file,
293+ & semantics,
294+ vfs,
295+ resolve_paths,
296+ SourceKind :: Source ,
297+ ) ,
298+ Err ( reason) => {
299+ extractor. extract_without_semantics ( file, SourceKind :: Source , & reason)
272300 }
273- Err ( reason) => extractor. extract_without_semantics ( file, & reason) ,
274301 } ;
275302 }
303+ for ( _, file) in vfs. iter ( ) {
304+ if let Some ( file) = file. as_path ( ) . map ( <_ as AsRef < Path > >:: as_ref) {
305+ if file. extension ( ) . is_some_and ( |ext| ext == "rs" )
306+ && processed_files. insert ( file. to_owned ( ) )
307+ {
308+ extractor. extract_with_semantics (
309+ file,
310+ & semantics,
311+ vfs,
312+ resolve_paths,
313+ SourceKind :: Library ,
314+ ) ;
315+ extractor. archiver . archive ( file) ;
316+ }
317+ }
318+ }
276319 } else {
277320 for file in files {
278- extractor. extract_without_semantics ( file, "unable to load manifest" ) ;
321+ extractor. extract_without_semantics (
322+ file,
323+ SourceKind :: Source ,
324+ "unable to load manifest" ,
325+ ) ;
279326 }
280327 }
281328 }
@@ -286,7 +333,7 @@ fn main() -> anyhow::Result<()> {
286333 let entry = entry. context ( "failed to read builtins directory" ) ?;
287334 let path = entry. path ( ) ;
288335 if path. extension ( ) . is_some_and ( |ext| ext == "rs" ) {
289- extractor. extract_without_semantics ( & path, "" ) ;
336+ extractor. extract_without_semantics ( & path, SourceKind :: Library , "" ) ;
290337 }
291338 }
292339
0 commit comments