Don't attempt to compute layout of type referencing error

This commit is contained in:
Michael Goulet 2023-07-16 23:26:02 +00:00
parent 9339f446a5
commit 37076c9b4e
8 changed files with 47 additions and 13 deletions

View File

@ -122,14 +122,9 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
} else { } else {
err.note(format!("source type: `{}` ({})", from, skeleton_string(from, sk_from))) err.note(format!("source type: `{}` ({})", from, skeleton_string(from, sk_from)))
.note(format!("target type: `{}` ({})", to, skeleton_string(to, sk_to))); .note(format!("target type: `{}` ({})", to, skeleton_string(to, sk_to)));
let mut should_delay_as_bug = false; if let Err(LayoutError::ReferencesError(_)) = sk_from {
if let Err(LayoutError::Unknown(bad_from)) = sk_from && bad_from.references_error() { err.delay_as_bug();
should_delay_as_bug = true; } else if let Err(LayoutError::ReferencesError(_)) = sk_to {
}
if let Err(LayoutError::Unknown(bad_to)) = sk_to && bad_to.references_error() {
should_delay_as_bug = true;
}
if should_delay_as_bug {
err.delay_as_bug(); err.delay_as_bug();
} }
} }

View File

@ -52,6 +52,9 @@ middle_drop_check_overflow =
overflow while adding drop-check rules for {$ty} overflow while adding drop-check rules for {$ty}
.note = overflowed on {$overflow_ty} .note = overflowed on {$overflow_ty}
middle_layout_references_error =
the type has an unknown layout
middle_limit_invalid = middle_limit_invalid =
`limit` must be a non-negative integer `limit` must be a non-negative integer
.label = {$error_str} .label = {$error_str}

View File

@ -132,6 +132,9 @@ pub enum LayoutError<'tcx> {
#[diag(middle_cycle)] #[diag(middle_cycle)]
Cycle, Cycle,
#[diag(middle_layout_references_error)]
ReferencesError,
} }
#[derive(Diagnostic)] #[derive(Diagnostic)]

View File

@ -10,7 +10,7 @@ use rustc_hir::def_id::DefId;
use rustc_index::IndexVec; use rustc_index::IndexVec;
use rustc_session::config::OptLevel; use rustc_session::config::OptLevel;
use rustc_span::symbol::{sym, Symbol}; use rustc_span::symbol::{sym, Symbol};
use rustc_span::{Span, DUMMY_SP}; use rustc_span::{ErrorGuaranteed, Span, DUMMY_SP};
use rustc_target::abi::call::FnAbi; use rustc_target::abi::call::FnAbi;
use rustc_target::abi::*; use rustc_target::abi::*;
use rustc_target::spec::{abi::Abi as SpecAbi, HasTargetSpec, PanicStrategy, Target}; use rustc_target::spec::{abi::Abi as SpecAbi, HasTargetSpec, PanicStrategy, Target};
@ -212,6 +212,7 @@ pub enum LayoutError<'tcx> {
Unknown(Ty<'tcx>), Unknown(Ty<'tcx>),
SizeOverflow(Ty<'tcx>), SizeOverflow(Ty<'tcx>),
NormalizationFailure(Ty<'tcx>, NormalizationError<'tcx>), NormalizationFailure(Ty<'tcx>, NormalizationError<'tcx>),
ReferencesError(ErrorGuaranteed),
Cycle, Cycle,
} }
@ -224,6 +225,7 @@ impl<'tcx> LayoutError<'tcx> {
SizeOverflow(_) => middle_values_too_big, SizeOverflow(_) => middle_values_too_big,
NormalizationFailure(_, _) => middle_cannot_be_normalized, NormalizationFailure(_, _) => middle_cannot_be_normalized,
Cycle => middle_cycle, Cycle => middle_cycle,
ReferencesError(_) => middle_layout_references_error,
} }
} }
@ -237,6 +239,7 @@ impl<'tcx> LayoutError<'tcx> {
E::NormalizationFailure { ty, failure_ty: e.get_type_for_failure() } E::NormalizationFailure { ty, failure_ty: e.get_type_for_failure() }
} }
Cycle => E::Cycle, Cycle => E::Cycle,
ReferencesError(_) => E::ReferencesError,
} }
} }
} }
@ -257,6 +260,7 @@ impl<'tcx> fmt::Display for LayoutError<'tcx> {
e.get_type_for_failure() e.get_type_for_failure()
), ),
LayoutError::Cycle => write!(f, "a cycle occurred during layout computation"), LayoutError::Cycle => write!(f, "a cycle occurred during layout computation"),
LayoutError::ReferencesError(_) => write!(f, "the type has an unknown layout"),
} }
} }
} }
@ -323,7 +327,8 @@ impl<'tcx> SizeSkeleton<'tcx> {
Err( Err(
e @ LayoutError::Cycle e @ LayoutError::Cycle
| e @ LayoutError::SizeOverflow(_) | e @ LayoutError::SizeOverflow(_)
| e @ LayoutError::NormalizationFailure(..), | e @ LayoutError::NormalizationFailure(..)
| e @ LayoutError::ReferencesError(_),
) => return Err(e), ) => return Err(e),
}; };

View File

@ -195,7 +195,7 @@ pub(crate) mod rustc {
impl<'tcx> From<&LayoutError<'tcx>> for Err { impl<'tcx> From<&LayoutError<'tcx>> for Err {
fn from(err: &LayoutError<'tcx>) -> Self { fn from(err: &LayoutError<'tcx>) -> Self {
match err { match err {
LayoutError::Unknown(..) => Self::UnknownLayout, LayoutError::Unknown(..) | LayoutError::ReferencesError(..) => Self::UnknownLayout,
err => unimplemented!("{:?}", err), err => unimplemented!("{:?}", err),
} }
} }

View File

@ -96,6 +96,13 @@ fn layout_of_uncached<'tcx>(
cx: &LayoutCx<'tcx, TyCtxt<'tcx>>, cx: &LayoutCx<'tcx, TyCtxt<'tcx>>,
ty: Ty<'tcx>, ty: Ty<'tcx>,
) -> Result<Layout<'tcx>, &'tcx LayoutError<'tcx>> { ) -> Result<Layout<'tcx>, &'tcx LayoutError<'tcx>> {
// Types that reference `ty::Error` pessimistically don't have a meaningful layout.
// The only side-effect of this is possibly worse diagnostics in case the layout
// was actually computable (like if the `ty::Error` showed up only in a `PhantomData`).
if let Err(guar) = ty.error_reported() {
return Err(error(cx, LayoutError::ReferencesError(guar)));
}
let tcx = cx.tcx; let tcx = cx.tcx;
let param_env = cx.param_env; let param_env = cx.param_env;
let dl = cx.data_layout(); let dl = cx.data_layout();
@ -564,11 +571,15 @@ fn layout_of_uncached<'tcx>(
return Err(error(cx, LayoutError::Unknown(ty))); return Err(error(cx, LayoutError::Unknown(ty)));
} }
ty::Bound(..) | ty::GeneratorWitness(..) | ty::GeneratorWitnessMIR(..) | ty::Infer(_) => { ty::Bound(..)
| ty::GeneratorWitness(..)
| ty::GeneratorWitnessMIR(..)
| ty::Infer(_)
| ty::Error(_) => {
bug!("Layout::compute: unexpected type `{}`", ty) bug!("Layout::compute: unexpected type `{}`", ty)
} }
ty::Placeholder(..) | ty::Param(_) | ty::Error(_) => { ty::Placeholder(..) | ty::Param(_) => {
return Err(error(cx, LayoutError::Unknown(ty))); return Err(error(cx, LayoutError::Unknown(ty)));
} }
}) })

View File

@ -0,0 +1,8 @@
// issue: 113760
union W { s: dyn Iterator<Item = Missing> }
//~^ ERROR cannot find type `Missing` in this scope
static ONCE: W = todo!();
fn main() {}

View File

@ -0,0 +1,9 @@
error[E0412]: cannot find type `Missing` in this scope
--> $DIR/malformed-unsized-type-in-union.rs:3:34
|
LL | union W { s: dyn Iterator<Item = Missing> }
| ^^^^^^^ not found in this scope
error: aborting due to previous error
For more information about this error, try `rustc --explain E0412`.