Skip to content

Commit 61d87f0

Browse files
committed
Rollup merge of #33576 - soltanmm:vtable, r=nikomatsakis
Plumb inference obligations through selection, take 2 Using a `SnapshotVec` and dumping inferred obligations into `Vtable` variants. r? @nikomatsakis
2 parents c62d65c + f52b655 commit 61d87f0

File tree

8 files changed

+235
-105
lines changed

8 files changed

+235
-105
lines changed

src/librustc/traits/mod.rs

+38-10
Original file line numberDiff line numberDiff line change
@@ -239,7 +239,7 @@ pub enum Vtable<'tcx, N> {
239239
VtableParam(Vec<N>),
240240

241241
/// Virtual calls through an object
242-
VtableObject(VtableObjectData<'tcx>),
242+
VtableObject(VtableObjectData<'tcx, N>),
243243

244244
/// Successful resolution for a builtin trait.
245245
VtableBuiltin(VtableBuiltinData<N>),
@@ -250,7 +250,7 @@ pub enum Vtable<'tcx, N> {
250250
VtableClosure(VtableClosureData<'tcx, N>),
251251

252252
/// Same as above, but for a fn pointer type with the given signature.
253-
VtableFnPointer(ty::Ty<'tcx>),
253+
VtableFnPointer(VtableFnPointerData<'tcx, N>),
254254
}
255255

256256
/// Identifies a particular impl in the source, along with a set of
@@ -293,14 +293,22 @@ pub struct VtableBuiltinData<N> {
293293
/// A vtable for some object-safe trait `Foo` automatically derived
294294
/// for the object type `Foo`.
295295
#[derive(PartialEq,Eq,Clone)]
296-
pub struct VtableObjectData<'tcx> {
296+
pub struct VtableObjectData<'tcx, N> {
297297
/// `Foo` upcast to the obligation trait. This will be some supertrait of `Foo`.
298298
pub upcast_trait_ref: ty::PolyTraitRef<'tcx>,
299299

300300
/// The vtable is formed by concatenating together the method lists of
301301
/// the base object trait and all supertraits; this is the start of
302302
/// `upcast_trait_ref`'s methods in that vtable.
303-
pub vtable_base: usize
303+
pub vtable_base: usize,
304+
305+
pub nested: Vec<N>,
306+
}
307+
308+
#[derive(Clone, PartialEq, Eq)]
309+
pub struct VtableFnPointerData<'tcx, N> {
310+
pub fn_ty: ty::Ty<'tcx>,
311+
pub nested: Vec<N>
304312
}
305313

306314
/// Creates predicate obligations from the generic bounds.
@@ -569,7 +577,20 @@ impl<'tcx, N> Vtable<'tcx, N> {
569577
VtableBuiltin(i) => i.nested,
570578
VtableDefaultImpl(d) => d.nested,
571579
VtableClosure(c) => c.nested,
572-
VtableObject(_) | VtableFnPointer(..) => vec![]
580+
VtableObject(d) => d.nested,
581+
VtableFnPointer(d) => d.nested,
582+
}
583+
}
584+
585+
fn nested_obligations_mut(&mut self) -> &mut Vec<N> {
586+
match self {
587+
&mut VtableImpl(ref mut i) => &mut i.nested,
588+
&mut VtableParam(ref mut n) => n,
589+
&mut VtableBuiltin(ref mut i) => &mut i.nested,
590+
&mut VtableDefaultImpl(ref mut d) => &mut d.nested,
591+
&mut VtableClosure(ref mut c) => &mut c.nested,
592+
&mut VtableObject(ref mut d) => &mut d.nested,
593+
&mut VtableFnPointer(ref mut d) => &mut d.nested,
573594
}
574595
}
575596

@@ -578,18 +599,25 @@ impl<'tcx, N> Vtable<'tcx, N> {
578599
VtableImpl(i) => VtableImpl(VtableImplData {
579600
impl_def_id: i.impl_def_id,
580601
substs: i.substs,
581-
nested: i.nested.into_iter().map(f).collect()
602+
nested: i.nested.into_iter().map(f).collect(),
582603
}),
583604
VtableParam(n) => VtableParam(n.into_iter().map(f).collect()),
584605
VtableBuiltin(i) => VtableBuiltin(VtableBuiltinData {
585-
nested: i.nested.into_iter().map(f).collect()
606+
nested: i.nested.into_iter().map(f).collect(),
607+
}),
608+
VtableObject(o) => VtableObject(VtableObjectData {
609+
upcast_trait_ref: o.upcast_trait_ref,
610+
vtable_base: o.vtable_base,
611+
nested: o.nested.into_iter().map(f).collect(),
586612
}),
587-
VtableObject(o) => VtableObject(o),
588613
VtableDefaultImpl(d) => VtableDefaultImpl(VtableDefaultImplData {
589614
trait_def_id: d.trait_def_id,
590-
nested: d.nested.into_iter().map(f).collect()
615+
nested: d.nested.into_iter().map(f).collect(),
616+
}),
617+
VtableFnPointer(p) => VtableFnPointer(VtableFnPointerData {
618+
fn_ty: p.fn_ty,
619+
nested: p.nested.into_iter().map(f).collect(),
591620
}),
592-
VtableFnPointer(f) => VtableFnPointer(f),
593621
VtableClosure(c) => VtableClosure(VtableClosureData {
594622
closure_def_id: c.closure_def_id,
595623
substs: c.substs,

src/librustc/traits/project.rs

+11-7
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ use super::PredicateObligation;
1919
use super::SelectionContext;
2020
use super::SelectionError;
2121
use super::VtableClosureData;
22+
use super::VtableFnPointerData;
2223
use super::VtableImplData;
2324
use super::util;
2425

@@ -158,7 +159,7 @@ enum ProjectionTyCandidate<'tcx> {
158159
Closure(VtableClosureData<'tcx, PredicateObligation<'tcx>>),
159160

160161
// fn pointer return type
161-
FnPointer(Ty<'tcx>),
162+
FnPointer(VtableFnPointerData<'tcx, PredicateObligation<'tcx>>),
162163
}
163164

164165
struct ProjectionTyCandidateSet<'tcx> {
@@ -873,9 +874,9 @@ fn assemble_candidates_from_impls<'cx, 'gcx, 'tcx>(
873874
candidate_set.vec.push(
874875
ProjectionTyCandidate::Closure(data));
875876
}
876-
super::VtableFnPointer(fn_type) => {
877+
super::VtableFnPointer(data) => {
877878
candidate_set.vec.push(
878-
ProjectionTyCandidate::FnPointer(fn_type));
879+
ProjectionTyCandidate::FnPointer(data));
879880
}
880881
super::VtableParam(..) => {
881882
// This case tell us nothing about the value of an
@@ -941,19 +942,22 @@ fn confirm_candidate<'cx, 'gcx, 'tcx>(
941942
confirm_closure_candidate(selcx, obligation, closure_vtable)
942943
}
943944

944-
ProjectionTyCandidate::FnPointer(fn_type) => {
945-
confirm_fn_pointer_candidate(selcx, obligation, fn_type)
945+
ProjectionTyCandidate::FnPointer(fn_pointer_vtable) => {
946+
confirm_fn_pointer_candidate(selcx, obligation, fn_pointer_vtable)
946947
}
947948
}
948949
}
949950

950951
fn confirm_fn_pointer_candidate<'cx, 'gcx, 'tcx>(
951952
selcx: &mut SelectionContext<'cx, 'gcx, 'tcx>,
952953
obligation: &ProjectionTyObligation<'tcx>,
953-
fn_type: Ty<'tcx>)
954+
fn_pointer_vtable: VtableFnPointerData<'tcx, PredicateObligation<'tcx>>)
954955
-> (Ty<'tcx>, Vec<PredicateObligation<'tcx>>)
955956
{
956-
let fn_type = selcx.infcx().shallow_resolve(fn_type);
957+
// FIXME(#32730) propagate obligations (fn pointer vtable nested obligations ONLY come from
958+
// unification in inference)
959+
assert!(fn_pointer_vtable.nested.is_empty());
960+
let fn_type = selcx.infcx().shallow_resolve(fn_pointer_vtable.fn_ty);
957961
let sig = fn_type.fn_sig();
958962
confirm_callable_candidate(selcx, obligation, sig, util::TupleArgumentsFlag::Yes)
959963
}

0 commit comments

Comments
 (0)