1
Fork 0

Rollup merge of #94142 - est31:let_else_typeck, r=oli-obk

rustc_typeck: adopt let else in more places

Continuation of https://github.com/rust-lang/rust/pull/89933, https://github.com/rust-lang/rust/pull/91018, https://github.com/rust-lang/rust/pull/91481, https://github.com/rust-lang/rust/pull/93046, https://github.com/rust-lang/rust/pull/93590, https://github.com/rust-lang/rust/pull/94011.

I have extended my clippy lint to also recognize tuple passing and match statements. The diff caused by fixing it is way above 1 thousand lines. Thus, I split it up into multiple pull requests to make reviewing easier. This PR handles rustc_typeck.
This commit is contained in:
Matthias Krüger 2022-02-20 00:37:33 +01:00 committed by GitHub
commit 7ca1c48bbb
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
22 changed files with 135 additions and 229 deletions

View file

@ -1808,12 +1808,9 @@ impl<'o, 'tcx> dyn AstConv<'tcx> + 'o {
(_, Res::SelfTy { trait_: Some(_), alias_to: Some((impl_def_id, _)) }) => { (_, Res::SelfTy { trait_: Some(_), alias_to: Some((impl_def_id, _)) }) => {
// `Self` in an impl of a trait -- we have a concrete self type and a // `Self` in an impl of a trait -- we have a concrete self type and a
// trait reference. // trait reference.
let trait_ref = match tcx.impl_trait_ref(impl_def_id) { let Some(trait_ref) = tcx.impl_trait_ref(impl_def_id) else {
Some(trait_ref) => trait_ref, // A cycle error occurred, most likely.
None => { return Err(ErrorReported);
// A cycle error occurred, most likely.
return Err(ErrorReported);
}
}; };
self.one_bound_for_assoc_type( self.one_bound_for_assoc_type(

View file

@ -219,10 +219,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
(self.tcx.lang_items().fn_mut_trait(), Ident::with_dummy_span(sym::call_mut), true), (self.tcx.lang_items().fn_mut_trait(), Ident::with_dummy_span(sym::call_mut), true),
(self.tcx.lang_items().fn_once_trait(), Ident::with_dummy_span(sym::call_once), false), (self.tcx.lang_items().fn_once_trait(), Ident::with_dummy_span(sym::call_once), false),
] { ] {
let trait_def_id = match opt_trait_def_id { let Some(trait_def_id) = opt_trait_def_id else { continue };
Some(def_id) => def_id,
None => continue,
};
let opt_input_types = opt_arg_exprs.map(|arg_exprs| { let opt_input_types = opt_arg_exprs.map(|arg_exprs| {
[self.tcx.mk_tup(arg_exprs.iter().map(|e| { [self.tcx.mk_tup(arg_exprs.iter().map(|e| {
@ -246,11 +243,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
if borrow { if borrow {
// Check for &self vs &mut self in the method signature. Since this is either // Check for &self vs &mut self in the method signature. Since this is either
// the Fn or FnMut trait, it should be one of those. // the Fn or FnMut trait, it should be one of those.
let (region, mutbl) = if let ty::Ref(r, _, mutbl) = let ty::Ref(region, _, mutbl) = method.sig.inputs()[0].kind() else {
method.sig.inputs()[0].kind()
{
(r, mutbl)
} else {
// The `fn`/`fn_mut` lang item is ill-formed, which should have // The `fn`/`fn_mut` lang item is ill-formed, which should have
// caused an error elsewhere. // caused an error elsewhere.
self.tcx self.tcx

View file

@ -799,10 +799,9 @@ impl<'a, 'tcx> CastCheck<'tcx> {
let expr_kind = fcx.pointer_kind(m_expr.ty, self.span)?; let expr_kind = fcx.pointer_kind(m_expr.ty, self.span)?;
let cast_kind = fcx.pointer_kind(m_cast.ty, self.span)?; let cast_kind = fcx.pointer_kind(m_cast.ty, self.span)?;
let cast_kind = match cast_kind { let Some(cast_kind) = cast_kind else {
// We can't cast if target pointer kind is unknown // We can't cast if target pointer kind is unknown
None => return Err(CastError::UnknownCastPtrKind), return Err(CastError::UnknownCastPtrKind);
Some(cast_kind) => cast_kind,
}; };
// Cast to thin pointer is OK // Cast to thin pointer is OK
@ -810,10 +809,9 @@ impl<'a, 'tcx> CastCheck<'tcx> {
return Ok(CastKind::PtrPtrCast); return Ok(CastKind::PtrPtrCast);
} }
let expr_kind = match expr_kind { let Some(expr_kind) = expr_kind else {
// We can't cast to fat pointer if source pointer kind is unknown // We can't cast to fat pointer if source pointer kind is unknown
None => return Err(CastError::UnknownExprPtrKind), return Err(CastError::UnknownExprPtrKind);
Some(expr_kind) => expr_kind,
}; };
// thin -> fat? report invalid cast (don't complain about vtable kinds) // thin -> fat? report invalid cast (don't complain about vtable kinds)

View file

@ -415,13 +415,10 @@ fn check_static_inhabited<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId, span: Spa
// have UB during initialization if they are uninhabited, but there also seems to be no good // have UB during initialization if they are uninhabited, but there also seems to be no good
// reason to allow any statics to be uninhabited. // reason to allow any statics to be uninhabited.
let ty = tcx.type_of(def_id); let ty = tcx.type_of(def_id);
let layout = match tcx.layout_of(ParamEnv::reveal_all().and(ty)) { let Ok(layout) = tcx.layout_of(ParamEnv::reveal_all().and(ty)) else {
Ok(l) => l, // Generic statics are rejected, but we still reach this case.
Err(_) => { tcx.sess.delay_span_bug(span, "generic static must be rejected");
// Generic statics are rejected, but we still reach this case. return;
tcx.sess.delay_span_bug(span, "generic static must be rejected");
return;
}
}; };
if layout.abi.is_uninhabited() { if layout.abi.is_uninhabited() {
tcx.struct_span_lint_hir( tcx.struct_span_lint_hir(
@ -852,10 +849,7 @@ pub(super) fn check_specialization_validity<'tcx>(
impl_id: DefId, impl_id: DefId,
impl_item: &hir::ImplItemRef, impl_item: &hir::ImplItemRef,
) { ) {
let ancestors = match trait_def.ancestors(tcx, impl_id) { let Ok(ancestors) = trait_def.ancestors(tcx, impl_id) else { return };
Ok(ancestors) => ancestors,
Err(_) => return,
};
let mut ancestor_impls = ancestors.skip(1).filter_map(|parent| { let mut ancestor_impls = ancestors.skip(1).filter_map(|parent| {
if parent.is_from_trait() { if parent.is_from_trait() {
None None

View file

@ -676,12 +676,9 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// We do not expect any bound regions in our predicate, so // We do not expect any bound regions in our predicate, so
// skip past the bound vars. // skip past the bound vars.
let predicate = match predicate.no_bound_vars() { let Some(predicate) = predicate.no_bound_vars() else {
Some(p) => p, debug!("deduce_future_output_from_projection: has late-bound regions");
None => { return None;
debug!("deduce_future_output_from_projection: has late-bound regions");
return None;
}
}; };
// Check that this is a projection from the `Future` trait. // Check that this is a projection from the `Future` trait.

View file

@ -429,13 +429,10 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
// (e.g., in example above, the failure from relating `Vec<T>` // (e.g., in example above, the failure from relating `Vec<T>`
// to the target type), since that should be the least // to the target type), since that should be the least
// confusing. // confusing.
let InferOk { value: ty, mut obligations } = match found { let Some(InferOk { value: ty, mut obligations }) = found else {
Some(d) => d, let err = first_error.expect("coerce_borrowed_pointer had no error");
None => { debug!("coerce_borrowed_pointer: failed with err = {:?}", err);
let err = first_error.expect("coerce_borrowed_pointer had no error"); return Err(err);
debug!("coerce_borrowed_pointer: failed with err = {:?}", err);
return Err(err);
}
}; };
if ty == a && mt_a.mutbl == hir::Mutability::Not && autoderef.step_count() == 1 { if ty == a && mt_a.mutbl == hir::Mutability::Not && autoderef.step_count() == 1 {
@ -461,9 +458,8 @@ impl<'f, 'tcx> Coerce<'f, 'tcx> {
// Now apply the autoref. We have to extract the region out of // Now apply the autoref. We have to extract the region out of
// the final ref type we got. // the final ref type we got.
let r_borrow = match ty.kind() { let ty::Ref(r_borrow, _, _) = ty.kind() else {
ty::Ref(r_borrow, _, _) => r_borrow, span_bug!(span, "expected a ref type, got {:?}", ty);
_ => span_bug!(span, "expected a ref type, got {:?}", ty),
}; };
let mutbl = match mutbl_b { let mutbl = match mutbl_b {
hir::Mutability::Not => AutoBorrowMutability::Not, hir::Mutability::Not => AutoBorrowMutability::Not,
@ -944,9 +940,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// We don't ever need two-phase here since we throw out the result of the coercion // We don't ever need two-phase here since we throw out the result of the coercion
let coerce = Coerce::new(self, cause, AllowTwoPhase::No); let coerce = Coerce::new(self, cause, AllowTwoPhase::No);
self.probe(|_| { self.probe(|_| {
let ok = match coerce.coerce(source, target) { let Ok(ok) = coerce.coerce(source, target) else {
Ok(ok) => ok, return false;
_ => return false,
}; };
let mut fcx = traits::FulfillmentContext::new_in_snapshot(); let mut fcx = traits::FulfillmentContext::new_in_snapshot();
fcx.register_predicate_obligations(self, ok.obligations); fcx.register_predicate_obligations(self, ok.obligations);

View file

@ -435,44 +435,39 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
/// opt.map(|param| { takes_ref(param) }); /// opt.map(|param| { takes_ref(param) });
/// ``` /// ```
fn can_use_as_ref(&self, expr: &hir::Expr<'_>) -> Option<(Span, &'static str, String)> { fn can_use_as_ref(&self, expr: &hir::Expr<'_>) -> Option<(Span, &'static str, String)> {
let path = match expr.kind { let hir::ExprKind::Path(hir::QPath::Resolved(_, ref path)) = expr.kind else {
hir::ExprKind::Path(hir::QPath::Resolved(_, ref path)) => path, return None;
_ => return None,
}; };
let local_id = match path.res { let hir::def::Res::Local(local_id) = path.res else {
hir::def::Res::Local(id) => id, return None;
_ => return None,
}; };
let local_parent = self.tcx.hir().get_parent_node(local_id); let local_parent = self.tcx.hir().get_parent_node(local_id);
let param_hir_id = match self.tcx.hir().find(local_parent) { let Some(Node::Param(hir::Param { hir_id: param_hir_id, .. })) = self.tcx.hir().find(local_parent) else {
Some(Node::Param(hir::Param { hir_id, .. })) => hir_id, return None;
_ => return None,
}; };
let param_parent = self.tcx.hir().get_parent_node(*param_hir_id); let param_parent = self.tcx.hir().get_parent_node(*param_hir_id);
let (expr_hir_id, closure_fn_decl) = match self.tcx.hir().find(param_parent) { let Some(Node::Expr(hir::Expr {
Some(Node::Expr(hir::Expr { hir_id: expr_hir_id,
hir_id, kind: hir::ExprKind::Closure(_, closure_fn_decl, ..),
kind: hir::ExprKind::Closure(_, decl, ..), ..
.. })) = self.tcx.hir().find(param_parent) else {
})) => (hir_id, decl), return None;
_ => return None,
}; };
let expr_parent = self.tcx.hir().get_parent_node(*expr_hir_id); let expr_parent = self.tcx.hir().get_parent_node(*expr_hir_id);
let hir = self.tcx.hir().find(expr_parent); let hir = self.tcx.hir().find(expr_parent);
let closure_params_len = closure_fn_decl.inputs.len(); let closure_params_len = closure_fn_decl.inputs.len();
let (method_path, method_expr) = match (hir, closure_params_len) { let (
( Some(Node::Expr(hir::Expr {
Some(Node::Expr(hir::Expr { kind: hir::ExprKind::MethodCall(method_path, method_expr, _),
kind: hir::ExprKind::MethodCall(segment, expr, _), ..
.. })),
})), 1,
1, ) = (hir, closure_params_len) else {
) => (segment, expr), return None;
_ => return None,
}; };
let self_ty = self.typeck_results.borrow().node_type(method_expr[0].hir_id); let self_ty = self.typeck_results.borrow().node_type(method_expr[0].hir_id);

View file

@ -622,15 +622,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// the `enclosing_loops` field and let's coerce the // the `enclosing_loops` field and let's coerce the
// type of `expr_opt` into what is expected. // type of `expr_opt` into what is expected.
let mut enclosing_breakables = self.enclosing_breakables.borrow_mut(); let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
let ctxt = match enclosing_breakables.opt_find_breakable(target_id) { let Some(ctxt) = enclosing_breakables.opt_find_breakable(target_id) else {
Some(ctxt) => ctxt, // Avoid ICE when `break` is inside a closure (#65383).
None => { return tcx.ty_error_with_message(
// Avoid ICE when `break` is inside a closure (#65383). expr.span,
return tcx.ty_error_with_message( "break was outside loop, but no error was emitted",
expr.span, );
"break was outside loop, but no error was emitted",
);
}
}; };
if let Some(ref mut coerce) = ctxt.coerce { if let Some(ref mut coerce) = ctxt.coerce {

View file

@ -745,10 +745,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
formal_args: &[Ty<'tcx>], formal_args: &[Ty<'tcx>],
) -> Vec<Ty<'tcx>> { ) -> Vec<Ty<'tcx>> {
let formal_ret = self.resolve_vars_with_obligations(formal_ret); let formal_ret = self.resolve_vars_with_obligations(formal_ret);
let ret_ty = match expected_ret.only_has_type(self) { let Some(ret_ty) = expected_ret.only_has_type(self) else { return Vec::new() };
Some(ret) => ret,
None => return Vec::new(),
};
let expect_args = self let expect_args = self
.fudge_inference_if_ok(|| { .fudge_inference_if_ok(|| {
// Attempt to apply a subtyping relationship between the formal // Attempt to apply a subtyping relationship between the formal
@ -1044,9 +1041,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// Be helpful when the user wrote `{... expr;}` and // Be helpful when the user wrote `{... expr;}` and
// taking the `;` off is enough to fix the error. // taking the `;` off is enough to fix the error.
let last_stmt = blk.stmts.last()?; let last_stmt = blk.stmts.last()?;
let last_expr = match last_stmt.kind { let hir::StmtKind::Semi(ref last_expr) = last_stmt.kind else {
hir::StmtKind::Semi(ref e) => e, return None;
_ => return None,
}; };
let last_expr_ty = self.node_ty(last_expr.hir_id); let last_expr_ty = self.node_ty(last_expr.hir_id);
let needs_box = match (last_expr_ty.kind(), expected_ty.kind()) { let needs_box = match (last_expr_ty.kind(), expected_ty.kind()) {
@ -1061,11 +1057,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
last_def_id, last_bounds, exp_def_id, exp_bounds last_def_id, last_bounds, exp_def_id, exp_bounds
); );
let (last_local_id, exp_local_id) = let last_local_id = last_def_id.as_local()?;
match (last_def_id.as_local(), exp_def_id.as_local()) { let exp_local_id = exp_def_id.as_local()?;
(Some(last_hir_id), Some(exp_hir_id)) => (last_hir_id, exp_hir_id),
(_, _) => return None,
};
match ( match (
&self.tcx.hir().expect_item(last_local_id).kind, &self.tcx.hir().expect_item(last_local_id).kind,

View file

@ -438,9 +438,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// is and we were expecting a Box, ergo Pin<Box<expected>>, we // is and we were expecting a Box, ergo Pin<Box<expected>>, we
// can suggest Box::pin. // can suggest Box::pin.
let parent = self.tcx.hir().get_parent_node(expr.hir_id); let parent = self.tcx.hir().get_parent_node(expr.hir_id);
let fn_name = match self.tcx.hir().find(parent) { let Some(Node::Expr(Expr { kind: ExprKind::Call(fn_name, _), .. })) = self.tcx.hir().find(parent) else {
Some(Node::Expr(Expr { kind: ExprKind::Call(fn_name, _), .. })) => fn_name, return false;
_ => return false,
}; };
match fn_name.kind { match fn_name.kind {
ExprKind::Path(QPath::TypeRelative( ExprKind::Path(QPath::TypeRelative(

View file

@ -149,14 +149,11 @@ impl<'a, 'tcx> ConfirmContext<'a, 'tcx> {
// time writing the results into the various typeck results. // time writing the results into the various typeck results.
let mut autoderef = let mut autoderef =
self.autoderef_overloaded_span(self.span, unadjusted_self_ty, self.call_expr.span); self.autoderef_overloaded_span(self.span, unadjusted_self_ty, self.call_expr.span);
let (ty, n) = match autoderef.nth(pick.autoderefs) { let Some((ty, n)) = autoderef.nth(pick.autoderefs) else {
Some(n) => n, return self.tcx.ty_error_with_message(
None => { rustc_span::DUMMY_SP,
return self.tcx.ty_error_with_message( &format!("failed autoderef {}", pick.autoderefs),
rustc_span::DUMMY_SP, );
&format!("failed autoderef {}", pick.autoderefs),
);
}
}; };
assert_eq!(n, pick.autoderefs); assert_eq!(n, pick.autoderefs);
@ -520,10 +517,7 @@ impl<'a, 'tcx> ConfirmContext<'a, 'tcx> {
&self, &self,
predicates: &ty::InstantiatedPredicates<'tcx>, predicates: &ty::InstantiatedPredicates<'tcx>,
) -> Option<Span> { ) -> Option<Span> {
let sized_def_id = match self.tcx.lang_items().sized_trait() { let sized_def_id = self.tcx.lang_items().sized_trait()?;
Some(def_id) => def_id,
None => return None,
};
traits::elaborate_predicates(self.tcx, predicates.predicates.iter().copied()) traits::elaborate_predicates(self.tcx, predicates.predicates.iter().copied())
// We don't care about regions here. // We don't care about regions here.

View file

@ -371,15 +371,12 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
// Trait must have a method named `m_name` and it should not have // Trait must have a method named `m_name` and it should not have
// type parameters or early-bound regions. // type parameters or early-bound regions.
let tcx = self.tcx; let tcx = self.tcx;
let method_item = match self.associated_value(trait_def_id, m_name) { let Some(method_item) = self.associated_value(trait_def_id, m_name) else {
Some(method_item) => method_item, tcx.sess.delay_span_bug(
None => { span,
tcx.sess.delay_span_bug( "operator trait does not have corresponding operator method",
span, );
"operator trait does not have corresponding operator method", return None;
);
return None;
}
}; };
let def_id = method_item.def_id; let def_id = method_item.def_id;
let generics = tcx.generics_of(def_id); let generics = tcx.generics_of(def_id);

View file

@ -1246,9 +1246,8 @@ impl<'a, 'tcx> ProbeContext<'a, 'tcx> {
return None; return None;
} }
let ty = match self_ty.kind() { let &ty::RawPtr(ty::TypeAndMut { ty, mutbl: hir::Mutability::Mut }) = self_ty.kind() else {
&ty::RawPtr(ty::TypeAndMut { ty, mutbl: hir::Mutability::Mut }) => ty, return None;
_ => return None,
}; };
let const_self_ty = ty::TypeAndMut { ty, mutbl: hir::Mutability::Not }; let const_self_ty = ty::TypeAndMut { ty, mutbl: hir::Mutability::Not };

View file

@ -37,9 +37,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
ty::Closure(..) | ty::FnDef(..) | ty::FnPtr(_) => true, ty::Closure(..) | ty::FnDef(..) | ty::FnPtr(_) => true,
// If it's not a simple function, look for things which implement `FnOnce`. // If it's not a simple function, look for things which implement `FnOnce`.
_ => { _ => {
let fn_once = match tcx.lang_items().require(LangItem::FnOnce) { let Some(fn_once) = tcx.lang_items().fn_once_trait() else {
Ok(fn_once) => fn_once, return false;
Err(..) => return false,
}; };
// This conditional prevents us from asking to call errors and unresolved types. // This conditional prevents us from asking to call errors and unresolved types.
@ -112,12 +111,11 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
CandidateSource::ImplSource(impl_did) => { CandidateSource::ImplSource(impl_did) => {
// Provide the best span we can. Use the item, if local to crate, else // Provide the best span we can. Use the item, if local to crate, else
// the impl, if local to crate (item may be defaulted), else nothing. // the impl, if local to crate (item may be defaulted), else nothing.
let item = match self.associated_value(impl_did, item_name).or_else(|| { let Some(item) = self.associated_value(impl_did, item_name).or_else(|| {
let impl_trait_ref = self.tcx.impl_trait_ref(impl_did)?; let impl_trait_ref = self.tcx.impl_trait_ref(impl_did)?;
self.associated_value(impl_trait_ref.def_id, item_name) self.associated_value(impl_trait_ref.def_id, item_name)
}) { }) else {
Some(item) => item, continue;
None => continue,
}; };
let note_span = self let note_span = self
.tcx .tcx
@ -194,10 +192,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
} }
} }
CandidateSource::TraitSource(trait_did) => { CandidateSource::TraitSource(trait_did) => {
let item = match self.associated_value(trait_did, item_name) { let Some(item) = self.associated_value(trait_did, item_name) else { continue };
Some(item) => item,
None => continue,
};
let item_span = self let item_span = self
.tcx .tcx
.sess .sess
@ -1202,10 +1197,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
let mut derives = Vec::<(String, Span, String)>::new(); let mut derives = Vec::<(String, Span, String)>::new();
let mut traits = Vec::<Span>::new(); let mut traits = Vec::<Span>::new();
for (pred, _, _) in unsatisfied_predicates { for (pred, _, _) in unsatisfied_predicates {
let trait_pred = match pred.kind().skip_binder() { let ty::PredicateKind::Trait(trait_pred) = pred.kind().skip_binder() else { continue };
ty::PredicateKind::Trait(trait_pred) => trait_pred,
_ => continue,
};
let adt = match trait_pred.self_ty().ty_adt_def() { let adt = match trait_pred.self_ty().ty_adt_def() {
Some(adt) if adt.did.is_local() => adt, Some(adt) if adt.did.is_local() => adt,
_ => continue, _ => continue,

View file

@ -981,9 +981,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
if subpats.len() == variant.fields.len() if subpats.len() == variant.fields.len()
|| subpats.len() < variant.fields.len() && ddpos.is_some() || subpats.len() < variant.fields.len() && ddpos.is_some()
{ {
let substs = match pat_ty.kind() { let ty::Adt(_, substs) = pat_ty.kind() else {
ty::Adt(_, substs) => substs, bug!("unexpected pattern type {:?}", pat_ty);
_ => bug!("unexpected pattern type {:?}", pat_ty),
}; };
for (i, subpat) in subpats.iter().enumerate_and_adjust(variant.fields.len(), ddpos) { for (i, subpat) in subpats.iter().enumerate_and_adjust(variant.fields.len(), ddpos) {
let field_ty = self.field_ty(subpat.span, &variant.fields[i], substs); let field_ty = self.field_ty(subpat.span, &variant.fields[i], substs);
@ -1221,9 +1220,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
) -> bool { ) -> bool {
let tcx = self.tcx; let tcx = self.tcx;
let (substs, adt) = match adt_ty.kind() { let ty::Adt(adt, substs) = adt_ty.kind() else {
ty::Adt(adt, substs) => (substs, adt), span_bug!(pat.span, "struct pattern is not an ADT");
_ => span_bug!(pat.span, "struct pattern is not an ADT"),
}; };
// Index the struct fields' types. // Index the struct fields' types.

View file

@ -533,19 +533,16 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
base => bug!("Expected upvar, found={:?}", base), base => bug!("Expected upvar, found={:?}", base),
}; };
let min_cap_list = match root_var_min_capture_list.get_mut(&var_hir_id) { let Some(min_cap_list) = root_var_min_capture_list.get_mut(&var_hir_id) else {
None => { let mutability = self.determine_capture_mutability(&typeck_results, &place);
let mutability = self.determine_capture_mutability(&typeck_results, &place); let min_cap_list = vec![ty::CapturedPlace {
let min_cap_list = vec![ty::CapturedPlace { place,
place, info: capture_info,
info: capture_info, mutability,
mutability, region: None,
region: None, }];
}]; root_var_min_capture_list.insert(var_hir_id, min_cap_list);
root_var_min_capture_list.insert(var_hir_id, min_cap_list); continue;
continue;
}
Some(min_cap_list) => min_cap_list,
}; };
// Go through each entry in the current list of min_captures // Go through each entry in the current list of min_captures

View file

@ -40,11 +40,8 @@ struct InherentCollect<'tcx> {
impl<'tcx> ItemLikeVisitor<'_> for InherentCollect<'tcx> { impl<'tcx> ItemLikeVisitor<'_> for InherentCollect<'tcx> {
fn visit_item(&mut self, item: &hir::Item<'_>) { fn visit_item(&mut self, item: &hir::Item<'_>) {
let (ty, assoc_items) = match item.kind { let hir::ItemKind::Impl(hir::Impl { of_trait: None, self_ty: ty, items: assoc_items, .. }) = item.kind else {
hir::ItemKind::Impl(hir::Impl { of_trait: None, ref self_ty, items, .. }) => { return;
(self_ty, items)
}
_ => return,
}; };
let self_ty = self.tcx.type_of(item.def_id); let self_ty = self.tcx.type_of(item.def_id);

View file

@ -38,9 +38,8 @@ fn orphan_check_impl(tcx: TyCtxt<'_>, def_id: LocalDefId) -> Result<(), ErrorRep
let trait_def_id = trait_ref.def_id; let trait_def_id = trait_ref.def_id;
let item = tcx.hir().item(hir::ItemId { def_id }); let item = tcx.hir().item(hir::ItemId { def_id });
let impl_ = match item.kind { let hir::ItemKind::Impl(ref impl_) = item.kind else {
hir::ItemKind::Impl(ref impl_) => impl_, bug!("{:?} is not an impl: {:?}", def_id, item);
_ => bug!("{:?} is not an impl: {:?}", def_id, item),
}; };
let sp = tcx.sess.source_map().guess_head_span(item.span); let sp = tcx.sess.source_map().guess_head_span(item.span);
let tr = impl_.of_trait.as_ref().unwrap(); let tr = impl_.of_trait.as_ref().unwrap();

View file

@ -1,4 +1,3 @@
// ignore-tidy-filelength
//! "Collection" is the process of determining the type and other external //! "Collection" is the process of determining the type and other external
//! details of each item in Rust. Collection is specifically concerned //! details of each item in Rust. Collection is specifically concerned
//! with *inter-procedural* things -- for example, for a function //! with *inter-procedural* things -- for example, for a function
@ -1018,9 +1017,8 @@ fn adt_def(tcx: TyCtxt<'_>, def_id: DefId) -> &ty::AdtDef {
let def_id = def_id.expect_local(); let def_id = def_id.expect_local();
let hir_id = tcx.hir().local_def_id_to_hir_id(def_id); let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
let item = match tcx.hir().get(hir_id) { let Node::Item(item) = tcx.hir().get(hir_id) else {
Node::Item(item) => item, bug!();
_ => bug!(),
}; };
let repr = ReprOptions::new(tcx, def_id.to_def_id()); let repr = ReprOptions::new(tcx, def_id.to_def_id());
@ -1122,9 +1120,8 @@ fn super_predicates_that_define_assoc_type(
debug!("super_predicates_that_define_assoc_type: local trait_def_id={:?}", trait_def_id); debug!("super_predicates_that_define_assoc_type: local trait_def_id={:?}", trait_def_id);
let trait_hir_id = tcx.hir().local_def_id_to_hir_id(trait_def_id.expect_local()); let trait_hir_id = tcx.hir().local_def_id_to_hir_id(trait_def_id.expect_local());
let item = match tcx.hir().get(trait_hir_id) { let Node::Item(item) = tcx.hir().get(trait_hir_id) else {
Node::Item(item) => item, bug!("trait_node_id {} is not an item", trait_hir_id);
_ => bug!("trait_node_id {} is not an item", trait_hir_id),
}; };
let (generics, bounds) = match item.kind { let (generics, bounds) = match item.kind {
@ -2637,10 +2634,7 @@ fn from_target_feature(
supported_target_features: &FxHashMap<String, Option<Symbol>>, supported_target_features: &FxHashMap<String, Option<Symbol>>,
target_features: &mut Vec<Symbol>, target_features: &mut Vec<Symbol>,
) { ) {
let list = match attr.meta_item_list() { let Some(list) = attr.meta_item_list() else { return };
Some(list) => list,
None => return,
};
let bad_item = |span| { let bad_item = |span| {
let msg = "malformed `target_feature` attribute input"; let msg = "malformed `target_feature` attribute input";
let code = "enable = \"..\"".to_owned(); let code = "enable = \"..\"".to_owned();
@ -2658,35 +2652,29 @@ fn from_target_feature(
} }
// Must be of the form `enable = "..."` (a string). // Must be of the form `enable = "..."` (a string).
let value = match item.value_str() { let Some(value) = item.value_str() else {
Some(value) => value, bad_item(item.span());
None => { continue;
bad_item(item.span());
continue;
}
}; };
// We allow comma separation to enable multiple features. // We allow comma separation to enable multiple features.
target_features.extend(value.as_str().split(',').filter_map(|feature| { target_features.extend(value.as_str().split(',').filter_map(|feature| {
let feature_gate = match supported_target_features.get(feature) { let Some(feature_gate) = supported_target_features.get(feature) else {
Some(g) => g, let msg =
None => { format!("the feature named `{}` is not valid for this target", feature);
let msg = let mut err = tcx.sess.struct_span_err(item.span(), &msg);
format!("the feature named `{}` is not valid for this target", feature); err.span_label(
let mut err = tcx.sess.struct_span_err(item.span(), &msg); item.span(),
err.span_label( format!("`{}` is not valid for this target", feature),
item.span(), );
format!("`{}` is not valid for this target", feature), if let Some(stripped) = feature.strip_prefix('+') {
); let valid = supported_target_features.contains_key(stripped);
if let Some(stripped) = feature.strip_prefix('+') { if valid {
let valid = supported_target_features.contains_key(stripped); err.help("consider removing the leading `+` in the feature name");
if valid {
err.help("consider removing the leading `+` in the feature name");
}
} }
err.emit();
return None;
} }
err.emit();
return None;
}; };
// Only allow features whose feature gates have been enabled. // Only allow features whose feature gates have been enabled.

View file

@ -164,12 +164,9 @@ fn get_impl_substs<'tcx>(
// Conservatively use an empty `ParamEnv`. // Conservatively use an empty `ParamEnv`.
let outlives_env = OutlivesEnvironment::new(ty::ParamEnv::empty()); let outlives_env = OutlivesEnvironment::new(ty::ParamEnv::empty());
infcx.resolve_regions_and_report_errors(impl1_def_id, &outlives_env, RegionckMode::default()); infcx.resolve_regions_and_report_errors(impl1_def_id, &outlives_env, RegionckMode::default());
let impl2_substs = match infcx.fully_resolve(impl2_substs) { let Ok(impl2_substs) = infcx.fully_resolve(impl2_substs) else {
Ok(s) => s, tcx.sess.struct_span_err(span, "could not resolve substs on overridden impl").emit();
Err(_) => { return None;
tcx.sess.struct_span_err(span, "could not resolve substs on overridden impl").emit();
return None;
}
}; };
Some((impl1_substs, impl2_substs)) Some((impl1_substs, impl2_substs))
} }

View file

@ -484,9 +484,8 @@ impl<'a, 'tcx> MemCategorizationContext<'a, 'tcx> {
let place_ty = self.expr_ty(expr)?; let place_ty = self.expr_ty(expr)?;
let base_ty = self.expr_ty_adjusted(base)?; let base_ty = self.expr_ty_adjusted(base)?;
let (region, mutbl) = match *base_ty.kind() { let ty::Ref(region, _, mutbl) = *base_ty.kind() else {
ty::Ref(region, _, mutbl) => (region, mutbl), span_bug!(expr.span, "cat_overloaded_place: base is not a reference");
_ => span_bug!(expr.span, "cat_overloaded_place: base is not a reference"),
}; };
let ref_ty = self.tcx().mk_ref(region, ty::TypeAndMut { ty: place_ty, mutbl }); let ref_ty = self.tcx().mk_ref(region, ty::TypeAndMut { ty: place_ty, mutbl });
@ -544,14 +543,11 @@ impl<'a, 'tcx> MemCategorizationContext<'a, 'tcx> {
) -> McResult<VariantIdx> { ) -> McResult<VariantIdx> {
let res = self.typeck_results.qpath_res(qpath, pat_hir_id); let res = self.typeck_results.qpath_res(qpath, pat_hir_id);
let ty = self.typeck_results.node_type(pat_hir_id); let ty = self.typeck_results.node_type(pat_hir_id);
let adt_def = match ty.kind() { let ty::Adt(adt_def, _) = ty.kind() else {
ty::Adt(adt_def, _) => adt_def, self.tcx()
_ => { .sess
self.tcx() .delay_span_bug(span, "struct or tuple struct pattern not applied to an ADT");
.sess return Err(());
.delay_span_bug(span, "struct or tuple struct pattern not applied to an ADT");
return Err(());
}
}; };
match res { match res {
@ -744,12 +740,9 @@ impl<'a, 'tcx> MemCategorizationContext<'a, 'tcx> {
} }
PatKind::Slice(before, ref slice, after) => { PatKind::Slice(before, ref slice, after) => {
let element_ty = match place_with_id.place.ty().builtin_index() { let Some(element_ty) = place_with_id.place.ty().builtin_index() else {
Some(ty) => ty, debug!("explicit index of non-indexable type {:?}", place_with_id);
None => { return Err(());
debug!("explicit index of non-indexable type {:?}", place_with_id);
return Err(());
}
}; };
let elt_place = self.cat_projection( let elt_place = self.cat_projection(
pat, pat,

View file

@ -71,12 +71,9 @@ impl<'cx, 'tcx> InferCtxtExt<'tcx> for InferCtxt<'cx, 'tcx> {
result, result,
); );
debug!("implied_outlives_bounds for {:?}: {:#?}", ty, result); debug!("implied_outlives_bounds for {:?}: {:#?}", ty, result);
let result = match result { let Ok(result) = result else {
Ok(v) => v, self.tcx.sess.delay_span_bug(span, "implied_outlives_bounds failed to instantiate");
Err(_) => { return vec![];
self.tcx.sess.delay_span_bug(span, "implied_outlives_bounds failed to instantiate");
return vec![];
}
}; };
// Instantiation may have produced new inference variables and constraints on those // Instantiation may have produced new inference variables and constraints on those