Skip to content

Commit 59eaf07

Browse files
committed
MiniSet introduced, a simple SSO set
1 parent 9bff6fc commit 59eaf07

File tree

5 files changed

+58
-15
lines changed

5 files changed

+58
-15
lines changed

Cargo.lock

+9-2
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,12 @@ dependencies = [
9696
"nodrop",
9797
]
9898

99+
[[package]]
100+
name = "arrayvec"
101+
version = "0.5.1"
102+
source = "registry+https://github.com/rust-lang/crates.io-index"
103+
checksum = "cff77d8686867eceff3105329d4698d96c2391c176d5d03adc90c7389162b5b8"
104+
99105
[[package]]
100106
name = "atty"
101107
version = "0.2.11"
@@ -175,7 +181,7 @@ version = "0.2.18"
175181
source = "registry+https://github.com/rust-lang/crates.io-index"
176182
checksum = "5d6d530bdd2d52966a6d03b7a964add7ae1a288d25214066fd4b600f0f796400"
177183
dependencies = [
178-
"arrayvec",
184+
"arrayvec 0.4.7",
179185
"constant_time_eq",
180186
]
181187

@@ -804,7 +810,7 @@ version = "0.7.2"
804810
source = "registry+https://github.com/rust-lang/crates.io-index"
805811
checksum = "fedcd6772e37f3da2a9af9bf12ebe046c0dfe657992377b4df982a2b54cd37a9"
806812
dependencies = [
807-
"arrayvec",
813+
"arrayvec 0.4.7",
808814
"cfg-if",
809815
"crossbeam-utils 0.6.5",
810816
"lazy_static 1.4.0",
@@ -4082,6 +4088,7 @@ name = "rustc_middle"
40824088
version = "0.0.0"
40834089
dependencies = [
40844090
"arena",
4091+
"arrayvec 0.5.1",
40854092
"bitflags",
40864093
"byteorder",
40874094
"chalk-ir",

src/librustc_infer/infer/outlives/verify.rs

+5-5
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ use crate::infer::outlives::env::RegionBoundPairs;
22
use crate::infer::{GenericKind, VerifyBound};
33
use crate::traits;
44
use rustc_data_structures::captures::Captures;
5-
use rustc_data_structures::fx::FxHashSet;
65
use rustc_hir::def_id::DefId;
76
use rustc_middle::ty::subst::{GenericArg, GenericArgKind, InternalSubsts, Subst};
7+
use rustc_middle::ty::walk::MiniSet;
88
use rustc_middle::ty::{self, Ty, TyCtxt};
99

1010
/// The `TypeOutlives` struct has the job of "lowering" a `T: 'a`
@@ -33,7 +33,7 @@ impl<'cx, 'tcx> VerifyBoundCx<'cx, 'tcx> {
3333
/// Returns a "verify bound" that encodes what we know about
3434
/// `generic` and the regions it outlives.
3535
pub fn generic_bound(&self, generic: GenericKind<'tcx>) -> VerifyBound<'tcx> {
36-
let mut visited = FxHashSet::default();
36+
let mut visited = MiniSet::new();
3737
match generic {
3838
GenericKind::Param(param_ty) => self.param_bound(param_ty),
3939
GenericKind::Projection(projection_ty) => {
@@ -45,7 +45,7 @@ impl<'cx, 'tcx> VerifyBoundCx<'cx, 'tcx> {
4545
fn type_bound(
4646
&self,
4747
ty: Ty<'tcx>,
48-
visited: &mut FxHashSet<GenericArg<'tcx>>,
48+
visited: &mut MiniSet<GenericArg<'tcx>>,
4949
) -> VerifyBound<'tcx> {
5050
match ty.kind {
5151
ty::Param(p) => self.param_bound(p),
@@ -149,7 +149,7 @@ impl<'cx, 'tcx> VerifyBoundCx<'cx, 'tcx> {
149149
pub fn projection_bound(
150150
&self,
151151
projection_ty: ty::ProjectionTy<'tcx>,
152-
visited: &mut FxHashSet<GenericArg<'tcx>>,
152+
visited: &mut MiniSet<GenericArg<'tcx>>,
153153
) -> VerifyBound<'tcx> {
154154
debug!("projection_bound(projection_ty={:?})", projection_ty);
155155

@@ -187,7 +187,7 @@ impl<'cx, 'tcx> VerifyBoundCx<'cx, 'tcx> {
187187
fn recursive_bound(
188188
&self,
189189
parent: GenericArg<'tcx>,
190-
visited: &mut FxHashSet<GenericArg<'tcx>>,
190+
visited: &mut MiniSet<GenericArg<'tcx>>,
191191
) -> VerifyBound<'tcx> {
192192
let mut bounds = parent
193193
.walk_shallow(visited)

src/librustc_middle/Cargo.toml

+1
Original file line numberDiff line numberDiff line change
@@ -32,5 +32,6 @@ rustc_span = { path = "../librustc_span" }
3232
byteorder = { version = "1.3" }
3333
chalk-ir = "0.10.0"
3434
smallvec = { version = "1.0", features = ["union", "may_dangle"] }
35+
arrayvec = { version = "0.5.1", default-features = false }
3536
measureme = "0.7.1"
3637
rustc_session = { path = "../librustc_session" }

src/librustc_middle/ty/outlives.rs

+5-5
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44

55
use crate::ty::subst::{GenericArg, GenericArgKind};
66
use crate::ty::{self, Ty, TyCtxt, TypeFoldable};
7-
use rustc_data_structures::fx::FxHashSet;
7+
use crate::ty::walk::MiniSet;
88
use smallvec::SmallVec;
99

1010
#[derive(Debug)]
@@ -51,7 +51,7 @@ impl<'tcx> TyCtxt<'tcx> {
5151
/// Push onto `out` all the things that must outlive `'a` for the condition
5252
/// `ty0: 'a` to hold. Note that `ty0` must be a **fully resolved type**.
5353
pub fn push_outlives_components(self, ty0: Ty<'tcx>, out: &mut SmallVec<[Component<'tcx>; 4]>) {
54-
let mut visited = FxHashSet::default();
54+
let mut visited = MiniSet::new();
5555
compute_components(self, ty0, out, &mut visited);
5656
debug!("components({:?}) = {:?}", ty0, out);
5757
}
@@ -61,7 +61,7 @@ fn compute_components(
6161
tcx: TyCtxt<'tcx>,
6262
ty: Ty<'tcx>,
6363
out: &mut SmallVec<[Component<'tcx>; 4]>,
64-
visited: &mut FxHashSet<GenericArg<'tcx>>,
64+
visited: &mut MiniSet<GenericArg<'tcx>>,
6565
) {
6666
// Descend through the types, looking for the various "base"
6767
// components and collecting them into `out`. This is not written
@@ -142,7 +142,7 @@ fn compute_components(
142142
// OutlivesProjectionComponents. Continue walking
143143
// through and constrain Pi.
144144
let mut subcomponents = smallvec![];
145-
let mut subvisited = FxHashSet::default();
145+
let mut subvisited = MiniSet::new();
146146
compute_components_recursive(tcx, ty.into(), &mut subcomponents, &mut subvisited);
147147
out.push(Component::EscapingProjection(subcomponents.into_iter().collect()));
148148
}
@@ -194,7 +194,7 @@ fn compute_components_recursive(
194194
tcx: TyCtxt<'tcx>,
195195
parent: GenericArg<'tcx>,
196196
out: &mut SmallVec<[Component<'tcx>; 4]>,
197-
visited: &mut FxHashSet<GenericArg<'tcx>>,
197+
visited: &mut MiniSet<GenericArg<'tcx>>,
198198
) {
199199
for child in parent.walk_shallow(visited) {
200200
match child.unpack() {

src/librustc_middle/ty/walk.rs

+38-3
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,41 @@ use crate::ty;
55
use crate::ty::subst::{GenericArg, GenericArgKind};
66
use rustc_data_structures::fx::FxHashSet;
77
use smallvec::{self, SmallVec};
8+
use arrayvec::ArrayVec;
9+
use std::hash::Hash;
10+
11+
pub enum MiniSet<T> {
12+
Array(ArrayVec<[T; 64]>),
13+
Set(FxHashSet<T>),
14+
}
15+
16+
impl<T: Eq + Hash + Copy> MiniSet<T> {
17+
pub fn new() -> Self {
18+
MiniSet::Array(ArrayVec::new())
19+
}
20+
21+
pub fn insert(&mut self, elem: T) -> bool {
22+
match self {
23+
MiniSet::Array(array) => {
24+
if array.iter().any(|e| *e == elem) {
25+
false
26+
} else {
27+
if !array.is_full() {
28+
unsafe {
29+
array.push_unchecked(elem);
30+
}
31+
} else {
32+
let mut set: FxHashSet<T> = array.iter().copied().collect();
33+
set.insert(elem);
34+
*self = MiniSet::Set(set);
35+
}
36+
true
37+
}
38+
},
39+
MiniSet::Set(set) => set.insert(elem)
40+
}
41+
}
42+
}
843

944
// The TypeWalker's stack is hot enough that it's worth going to some effort to
1045
// avoid heap allocations.
@@ -13,7 +48,7 @@ type TypeWalkerStack<'tcx> = SmallVec<[GenericArg<'tcx>; 8]>;
1348
pub struct TypeWalker<'tcx> {
1449
stack: TypeWalkerStack<'tcx>,
1550
last_subtree: usize,
16-
visited: FxHashSet<GenericArg<'tcx>>,
51+
visited: MiniSet<GenericArg<'tcx>>,
1752
}
1853

1954
/// An iterator for walking the type tree.
@@ -26,7 +61,7 @@ pub struct TypeWalker<'tcx> {
2661
/// skips any types that are already there.
2762
impl<'tcx> TypeWalker<'tcx> {
2863
pub fn new(root: GenericArg<'tcx>) -> Self {
29-
Self { stack: smallvec![root], last_subtree: 1, visited: FxHashSet::default() }
64+
Self { stack: smallvec![root], last_subtree: 1, visited: MiniSet::new() }
3065
}
3166

3267
/// Skips the subtree corresponding to the last type
@@ -87,7 +122,7 @@ impl GenericArg<'tcx> {
87122
/// and skips any types that are already there.
88123
pub fn walk_shallow(
89124
self,
90-
visited: &mut FxHashSet<GenericArg<'tcx>>,
125+
visited: &mut MiniSet<GenericArg<'tcx>>,
91126
) -> impl Iterator<Item = GenericArg<'tcx>> {
92127
let mut stack = SmallVec::new();
93128
push_inner(&mut stack, self);

0 commit comments

Comments
 (0)