@@ -3,7 +3,7 @@ pub(crate) mod insert_use;
33
44use std:: { iter, ops} ;
55
6- use hir:: { Adt , Crate , Enum , ScopeDef , Semantics , Trait , Type } ;
6+ use hir:: { Adt , Crate , Enum , Module , ScopeDef , Semantics , Trait , Type } ;
77use ide_db:: RootDatabase ;
88use itertools:: Itertools ;
99use rustc_hash:: FxHashSet ;
@@ -274,15 +274,79 @@ impl TryEnum {
274274/// somewhat similar to the known paths infra inside hir, but it different; We
275275/// want to make sure that IDE specific paths don't become interesting inside
276276/// the compiler itself as well.
277- pub ( crate ) struct FamousDefs < ' a , ' b > ( pub ( crate ) & ' a Semantics < ' b , RootDatabase > , pub ( crate ) Crate ) ;
277+ pub struct FamousDefs < ' a , ' b > ( pub & ' a Semantics < ' b , RootDatabase > , pub Crate ) ;
278278
279279#[ allow( non_snake_case) ]
280280impl FamousDefs < ' _ , ' _ > {
281- #[ cfg( test) ]
282- pub ( crate ) const FIXTURE : & ' static str = r#"//- /libcore.rs crate:core
281+ pub const FIXTURE : & ' static str = r#"//- /libcore.rs crate:core
283282pub mod convert {
284283 pub trait From<T> {
285- fn from(T) -> Self;
284+ fn from(t: T) -> Self;
285+ }
286+ }
287+
288+ pub mod iter {
289+ pub use self::traits::{collect::IntoIterator, iterator::Iterator};
290+ mod traits {
291+ pub(crate) mod iterator {
292+ use crate::option::Option;
293+ pub trait Iterator {
294+ type Item;
295+ fn next(&mut self) -> Option<Self::Item>;
296+ fn by_ref(&mut self) -> &mut Self {
297+ self
298+ }
299+ fn take(self, n: usize) -> crate::iter::Take<Self> {
300+ crate::iter::Take { inner: self }
301+ }
302+ }
303+
304+ impl<I: Iterator> Iterator for &mut I {
305+ type Item = I::Item;
306+ fn next(&mut self) -> Option<I::Item> {
307+ (**self).next()
308+ }
309+ }
310+ }
311+ pub(crate) mod collect {
312+ pub trait IntoIterator {
313+ type Item;
314+ }
315+ }
316+ }
317+
318+ pub use self::sources::*;
319+ pub(crate) mod sources {
320+ use super::Iterator;
321+ use crate::option::Option::{self, *};
322+ pub struct Repeat<A> {
323+ element: A,
324+ }
325+
326+ pub fn repeat<T>(elt: T) -> Repeat<T> {
327+ Repeat { element: elt }
328+ }
329+
330+ impl<A> Iterator for Repeat<A> {
331+ type Item = A;
332+
333+ fn next(&mut self) -> Option<A> {
334+ None
335+ }
336+ }
337+ }
338+
339+ pub use self::adapters::*;
340+ pub(crate) mod adapters {
341+ use super::Iterator;
342+ use crate::option::Option::{self, *};
343+ pub struct Take<I> { pub(crate) inner: I }
344+ impl<I> Iterator for Take<I> where I: Iterator {
345+ type Item = <I as Iterator>::Item;
346+ fn next(&mut self) -> Option<<I as Iterator>::Item> {
347+ None
348+ }
349+ }
286350 }
287351}
288352
@@ -291,7 +355,7 @@ pub mod option {
291355}
292356
293357pub mod prelude {
294- pub use crate::{convert::From, option::Option::{self, *}};
358+ pub use crate::{convert::From, iter::{IntoIterator, Iterator}, option::Option::{self, *}};
295359}
296360#[prelude_import]
297361pub use prelude::*;
@@ -305,6 +369,14 @@ pub use prelude::*;
305369 self . find_enum ( "core:option:Option" )
306370 }
307371
372+ pub fn core_iter_Iterator ( & self ) -> Option < Trait > {
373+ self . find_trait ( "core:iter:traits:iterator:Iterator" )
374+ }
375+
376+ pub fn core_iter ( & self ) -> Option < Module > {
377+ self . find_module ( "core:iter" )
378+ }
379+
308380 fn find_trait ( & self , path : & str ) -> Option < Trait > {
309381 match self . find_def ( path) ? {
310382 hir:: ScopeDef :: ModuleDef ( hir:: ModuleDef :: Trait ( it) ) => Some ( it) ,
@@ -319,31 +391,41 @@ pub use prelude::*;
319391 }
320392 }
321393
394+ fn find_module ( & self , path : & str ) -> Option < Module > {
395+ match self . find_def ( path) ? {
396+ hir:: ScopeDef :: ModuleDef ( hir:: ModuleDef :: Module ( it) ) => Some ( it) ,
397+ _ => None ,
398+ }
399+ }
400+
322401 fn find_def ( & self , path : & str ) -> Option < ScopeDef > {
323402 let db = self . 0 . db ;
324403 let mut path = path. split ( ':' ) ;
325404 let trait_ = path. next_back ( ) ?;
326405 let std_crate = path. next ( ) ?;
327- let std_crate = self
406+ let std_crate = if self
328407 . 1
329- . dependencies ( db)
330- . into_iter ( )
331- . find ( |dep| & dep. name . to_string ( ) == std_crate) ?
332- . krate ;
333-
408+ . declaration_name ( db)
409+ . map ( |name| name. to_string ( ) == std_crate)
410+ . unwrap_or ( false )
411+ {
412+ self . 1
413+ } else {
414+ self . 1 . dependencies ( db) . into_iter ( ) . find ( |dep| dep. name . to_string ( ) == std_crate) ?. krate
415+ } ;
334416 let mut module = std_crate. root_module ( db) ;
335417 for segment in path {
336418 module = module. children ( db) . find_map ( |child| {
337419 let name = child. name ( db) ?;
338- if & name. to_string ( ) == segment {
420+ if name. to_string ( ) == segment {
339421 Some ( child)
340422 } else {
341423 None
342424 }
343425 } ) ?;
344426 }
345427 let def =
346- module. scope ( db, None ) . into_iter ( ) . find ( |( name, _def) | & name. to_string ( ) == trait_) ?. 1 ;
428+ module. scope ( db, None ) . into_iter ( ) . find ( |( name, _def) | name. to_string ( ) == trait_) ?. 1 ;
347429 Some ( def)
348430 }
349431}
0 commit comments