12
12
//! WARNING: this does not keep track of the region depth.
13
13
14
14
use ty:: { self , Ty } ;
15
- use std:: iter:: Iterator ;
16
- use std:: vec:: IntoIter ;
15
+ use rustc_data_structures:: small_vec:: SmallVec ;
16
+ use rustc_data_structures:: accumulate_vec:: IntoIter as AccIntoIter ;
17
+
18
+ // The TypeWalker's stack is hot enough that it's worth going to some effort to
19
+ // avoid heap allocations.
20
+ pub type TypeWalkerArray < ' tcx > = [ Ty < ' tcx > ; 8 ] ;
21
+ pub type TypeWalkerStack < ' tcx > = SmallVec < TypeWalkerArray < ' tcx > > ;
17
22
18
23
pub struct TypeWalker < ' tcx > {
19
- stack : Vec < Ty < ' tcx > > ,
24
+ stack : TypeWalkerStack < ' tcx > ,
20
25
last_subtree : usize ,
21
26
}
22
27
23
28
impl < ' tcx > TypeWalker < ' tcx > {
24
29
pub fn new ( ty : Ty < ' tcx > ) -> TypeWalker < ' tcx > {
25
- TypeWalker { stack : vec ! [ ty ] , last_subtree : 1 , }
30
+ TypeWalker { stack : SmallVec :: one ( ty ) , last_subtree : 1 , }
26
31
}
27
32
28
33
/// Skips the subtree of types corresponding to the last type
@@ -61,8 +66,8 @@ impl<'tcx> Iterator for TypeWalker<'tcx> {
61
66
}
62
67
}
63
68
64
- pub fn walk_shallow < ' tcx > ( ty : Ty < ' tcx > ) -> IntoIter < Ty < ' tcx > > {
65
- let mut stack = vec ! [ ] ;
69
+ pub fn walk_shallow < ' tcx > ( ty : Ty < ' tcx > ) -> AccIntoIter < TypeWalkerArray < ' tcx > > {
70
+ let mut stack = SmallVec :: new ( ) ;
66
71
push_subtypes ( & mut stack, ty) ;
67
72
stack. into_iter ( )
68
73
}
@@ -73,7 +78,7 @@ pub fn walk_shallow<'tcx>(ty: Ty<'tcx>) -> IntoIter<Ty<'tcx>> {
73
78
// known to be significant to any code, but it seems like the
74
79
// natural order one would expect (basically, the order of the
75
80
// types as they are written).
76
- fn push_subtypes < ' tcx > ( stack : & mut Vec < Ty < ' tcx > > , parent_ty : Ty < ' tcx > ) {
81
+ fn push_subtypes < ' tcx > ( stack : & mut TypeWalkerStack < ' tcx > , parent_ty : Ty < ' tcx > ) {
77
82
match parent_ty. sty {
78
83
ty:: TyBool | ty:: TyChar | ty:: TyInt ( _) | ty:: TyUint ( _) | ty:: TyFloat ( _) |
79
84
ty:: TyStr | ty:: TyInfer ( _) | ty:: TyParam ( _) | ty:: TyNever | ty:: TyError => {
@@ -112,7 +117,7 @@ fn push_subtypes<'tcx>(stack: &mut Vec<Ty<'tcx>>, parent_ty: Ty<'tcx>) {
112
117
}
113
118
}
114
119
115
- fn push_sig_subtypes < ' tcx > ( stack : & mut Vec < Ty < ' tcx > > , sig : & ty:: PolyFnSig < ' tcx > ) {
120
+ fn push_sig_subtypes < ' tcx > ( stack : & mut TypeWalkerStack < ' tcx > , sig : & ty:: PolyFnSig < ' tcx > ) {
116
121
stack. push ( sig. 0 . output ) ;
117
122
stack. extend ( sig. 0 . inputs . iter ( ) . cloned ( ) . rev ( ) ) ;
118
123
}
0 commit comments