Skip to content

Commit

Permalink
Auto merge of #69614 - estebank:ice-age, r=davidtwco
Browse files Browse the repository at this point in the history
`delay_span_bug` when codegen cannot select obligation

Fix #69602, introduced in #60126 by letting the compiler continue past
type checking after encountering errors.
  • Loading branch information
bors committed Mar 6, 2020
2 parents 4a1b69d + 7b6f5ed commit 865b44a
Showing 6 changed files with 55 additions and 10 deletions.
2 changes: 1 addition & 1 deletion src/librustc/query/mod.rs
Original file line number Diff line number Diff line change
@@ -650,7 +650,7 @@ rustc_queries! {
Codegen {
query codegen_fulfill_obligation(
key: (ty::ParamEnv<'tcx>, ty::PolyTraitRef<'tcx>)
) -> Vtable<'tcx, ()> {
) -> Option<Vtable<'tcx, ()>> {
no_force
cache_on_disk_if { true }
desc { |tcx|
18 changes: 11 additions & 7 deletions src/librustc_infer/traits/codegen/mod.rs
Original file line number Diff line number Diff line change
@@ -19,7 +19,7 @@ use rustc::ty::{self, TyCtxt};
pub fn codegen_fulfill_obligation<'tcx>(
ty: TyCtxt<'tcx>,
(param_env, trait_ref): (ty::ParamEnv<'tcx>, ty::PolyTraitRef<'tcx>),
) -> Vtable<'tcx, ()> {
) -> Option<Vtable<'tcx, ()>> {
// Remove any references to regions; this helps improve caching.
let trait_ref = ty.erase_regions(&trait_ref);

@@ -47,11 +47,15 @@ pub fn codegen_fulfill_obligation<'tcx>(
// leading to an ambiguous result. So report this as an
// overflow bug, since I believe this is the only case
// where ambiguity can result.
bug!(
"Encountered ambiguity selecting `{:?}` during codegen, \
presuming due to overflow",
trait_ref
)
infcx.tcx.sess.delay_span_bug(
rustc_span::DUMMY_SP,
&format!(
"encountered ambiguity selecting `{:?}` during codegen, presuming due to \
overflow or prior type error",
trait_ref
),
);
return None;
}
Err(e) => {
bug!("Encountered error `{:?}` selecting `{:?}` during codegen", e, trait_ref)
@@ -71,7 +75,7 @@ pub fn codegen_fulfill_obligation<'tcx>(
let vtable = infcx.drain_fulfillment_cx_or_panic(&mut fulfill_cx, &vtable);

info!("Cache miss: {:?} => {:?}", trait_ref, vtable);
vtable
Some(vtable)
})
}

2 changes: 1 addition & 1 deletion src/librustc_mir/monomorphize/mod.rs
Original file line number Diff line number Diff line change
@@ -18,7 +18,7 @@ pub fn custom_coerce_unsize_info<'tcx>(
});

match tcx.codegen_fulfill_obligation((ty::ParamEnv::reveal_all(), trait_ref)) {
traits::VtableImpl(traits::VtableImplData { impl_def_id, .. }) => {
Some(traits::VtableImpl(traits::VtableImplData { impl_def_id, .. })) => {
tcx.coerce_unsized_info(impl_def_id).custom_kind.unwrap()
}
vtable => {
2 changes: 1 addition & 1 deletion src/librustc_ty/instance.rs
Original file line number Diff line number Diff line change
@@ -70,7 +70,7 @@ fn resolve_associated_item<'tcx>(
);

let trait_ref = ty::TraitRef::from_method(tcx, trait_id, rcvr_substs);
let vtbl = tcx.codegen_fulfill_obligation((param_env, ty::Binder::bind(trait_ref)));
let vtbl = tcx.codegen_fulfill_obligation((param_env, ty::Binder::bind(trait_ref)))?;

// Now that we know which impl is being used, we can dispatch to
// the actual function:
22 changes: 22 additions & 0 deletions src/test/ui/issues/issue-69602-type-err-during-codegen-ice.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
trait TraitA {
const VALUE: usize;
}

struct A;
impl TraitA for A {
const VALUE: usize = 0;
}

trait TraitB {
type MyA: TraitA;
const VALUE: usize = Self::MyA::VALUE;
}

struct B;
impl TraitB for B { //~ ERROR not all trait items implemented, missing: `MyA`
type M = A; //~ ERROR type `M` is not a member of trait `TraitB`
}

fn main() {
let _ = [0; B::VALUE];
}
19 changes: 19 additions & 0 deletions src/test/ui/issues/issue-69602-type-err-during-codegen-ice.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
error[E0437]: type `M` is not a member of trait `TraitB`
--> $DIR/issue-69602-type-err-during-codegen-ice.rs:17:5
|
LL | type M = A;
| ^^^^^^^^^^^^^ not a member of trait `TraitB`

error[E0046]: not all trait items implemented, missing: `MyA`
--> $DIR/issue-69602-type-err-during-codegen-ice.rs:16:1
|
LL | type MyA: TraitA;
| ----------------- `MyA` from trait
...
LL | impl TraitB for B {
| ^^^^^^^^^^^^^^^^^ missing `MyA` in implementation

error: aborting due to 2 previous errors

Some errors have detailed explanations: E0046, E0437.
For more information about an error, try `rustc --explain E0046`.

0 comments on commit 865b44a

Please sign in to comment.