Auto merge of #114396 - compiler-errors:hir-typeck-nits, r=oli-obk
Miscellaneous HIR typeck nits Remove some check functions that only have one usage Also remove `Expectation::IsLast`, which was both undocumented, and was also made redundant by my cleanup/fix in #103987 😸
This commit is contained in:
commit
a922d1c0da
@ -136,15 +136,7 @@ pub fn check_match(
|
|||||||
&cause,
|
&cause,
|
||||||
Some(&arm.body),
|
Some(&arm.body),
|
||||||
arm_ty,
|
arm_ty,
|
||||||
Some(&mut |err| {
|
|err| self.suggest_removing_semicolon_for_coerce(err, expr, arm_ty, prior_arm),
|
||||||
self.suggest_removing_semicolon_for_coerce(
|
|
||||||
err,
|
|
||||||
expr,
|
|
||||||
orig_expected,
|
|
||||||
arm_ty,
|
|
||||||
prior_arm,
|
|
||||||
)
|
|
||||||
}),
|
|
||||||
false,
|
false,
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -181,7 +173,6 @@ fn suggest_removing_semicolon_for_coerce(
|
|||||||
&self,
|
&self,
|
||||||
diag: &mut Diagnostic,
|
diag: &mut Diagnostic,
|
||||||
expr: &hir::Expr<'tcx>,
|
expr: &hir::Expr<'tcx>,
|
||||||
expectation: Expectation<'tcx>,
|
|
||||||
arm_ty: Ty<'tcx>,
|
arm_ty: Ty<'tcx>,
|
||||||
prior_arm: Option<(Option<hir::HirId>, Ty<'tcx>, Span)>,
|
prior_arm: Option<(Option<hir::HirId>, Ty<'tcx>, Span)>,
|
||||||
) {
|
) {
|
||||||
@ -195,7 +186,7 @@ fn suggest_removing_semicolon_for_coerce(
|
|||||||
let hir::ExprKind::Block(block, _) = body.value.kind else {
|
let hir::ExprKind::Block(block, _) = body.value.kind else {
|
||||||
return;
|
return;
|
||||||
};
|
};
|
||||||
let Some(hir::Stmt { kind: hir::StmtKind::Semi(last_expr), .. }) =
|
let Some(hir::Stmt { kind: hir::StmtKind::Semi(last_expr), span: semi_span, .. }) =
|
||||||
block.innermost_block().stmts.last()
|
block.innermost_block().stmts.last()
|
||||||
else {
|
else {
|
||||||
return;
|
return;
|
||||||
@ -212,9 +203,6 @@ fn suggest_removing_semicolon_for_coerce(
|
|||||||
else {
|
else {
|
||||||
return;
|
return;
|
||||||
};
|
};
|
||||||
let Expectation::IsLast(stmt) = expectation else {
|
|
||||||
return;
|
|
||||||
};
|
|
||||||
|
|
||||||
let can_coerce_to_return_ty = match self.ret_coercion.as_ref() {
|
let can_coerce_to_return_ty = match self.ret_coercion.as_ref() {
|
||||||
Some(ret_coercion) => {
|
Some(ret_coercion) => {
|
||||||
@ -231,7 +219,7 @@ fn suggest_removing_semicolon_for_coerce(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
let semi_span = expr.span.shrink_to_hi().with_hi(stmt.hi());
|
let semi_span = expr.span.shrink_to_hi().with_hi(semi_span.hi());
|
||||||
let mut ret_span: MultiSpan = semi_span.into();
|
let mut ret_span: MultiSpan = semi_span.into();
|
||||||
ret_span.push_span_label(
|
ret_span.push_span_label(
|
||||||
expr.span,
|
expr.span,
|
||||||
@ -279,7 +267,7 @@ pub(super) fn if_fallback_coercion<T>(
|
|||||||
coercion.coerce_forced_unit(
|
coercion.coerce_forced_unit(
|
||||||
self,
|
self,
|
||||||
&cause,
|
&cause,
|
||||||
&mut |err| {
|
|err| {
|
||||||
if let Some((span, msg)) = &ret_reason {
|
if let Some((span, msg)) = &ret_reason {
|
||||||
err.span_label(*span, msg.clone());
|
err.span_label(*span, msg.clone());
|
||||||
} else if let ExprKind::Block(block, _) = &then_expr.kind
|
} else if let ExprKind::Block(block, _) = &then_expr.kind
|
||||||
|
@ -1418,7 +1418,7 @@ pub fn coerce<'a>(
|
|||||||
expression: &'tcx hir::Expr<'tcx>,
|
expression: &'tcx hir::Expr<'tcx>,
|
||||||
expression_ty: Ty<'tcx>,
|
expression_ty: Ty<'tcx>,
|
||||||
) {
|
) {
|
||||||
self.coerce_inner(fcx, cause, Some(expression), expression_ty, None, false)
|
self.coerce_inner(fcx, cause, Some(expression), expression_ty, |_| {}, false)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Indicates that one of the inputs is a "forced unit". This
|
/// Indicates that one of the inputs is a "forced unit". This
|
||||||
@ -1437,7 +1437,7 @@ pub fn coerce_forced_unit<'a>(
|
|||||||
&mut self,
|
&mut self,
|
||||||
fcx: &FnCtxt<'a, 'tcx>,
|
fcx: &FnCtxt<'a, 'tcx>,
|
||||||
cause: &ObligationCause<'tcx>,
|
cause: &ObligationCause<'tcx>,
|
||||||
augment_error: &mut dyn FnMut(&mut Diagnostic),
|
augment_error: impl FnOnce(&mut Diagnostic),
|
||||||
label_unit_as_expected: bool,
|
label_unit_as_expected: bool,
|
||||||
) {
|
) {
|
||||||
self.coerce_inner(
|
self.coerce_inner(
|
||||||
@ -1445,7 +1445,7 @@ pub fn coerce_forced_unit<'a>(
|
|||||||
cause,
|
cause,
|
||||||
None,
|
None,
|
||||||
Ty::new_unit(fcx.tcx),
|
Ty::new_unit(fcx.tcx),
|
||||||
Some(augment_error),
|
augment_error,
|
||||||
label_unit_as_expected,
|
label_unit_as_expected,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@ -1460,7 +1460,7 @@ pub(crate) fn coerce_inner<'a>(
|
|||||||
cause: &ObligationCause<'tcx>,
|
cause: &ObligationCause<'tcx>,
|
||||||
expression: Option<&'tcx hir::Expr<'tcx>>,
|
expression: Option<&'tcx hir::Expr<'tcx>>,
|
||||||
mut expression_ty: Ty<'tcx>,
|
mut expression_ty: Ty<'tcx>,
|
||||||
augment_error: Option<&mut dyn FnMut(&mut Diagnostic)>,
|
augment_error: impl FnOnce(&mut Diagnostic),
|
||||||
label_expression_as_expected: bool,
|
label_expression_as_expected: bool,
|
||||||
) {
|
) {
|
||||||
// Incorporate whatever type inference information we have
|
// Incorporate whatever type inference information we have
|
||||||
@ -1639,9 +1639,7 @@ pub(crate) fn coerce_inner<'a>(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Some(augment_error) = augment_error {
|
augment_error(&mut err);
|
||||||
augment_error(&mut err);
|
|
||||||
}
|
|
||||||
|
|
||||||
let is_insufficiently_polymorphic =
|
let is_insufficiently_polymorphic =
|
||||||
matches!(coercion_error, TypeError::RegionsInsufficientlyPolymorphic(..));
|
matches!(coercion_error, TypeError::RegionsInsufficientlyPolymorphic(..));
|
||||||
|
@ -21,8 +21,6 @@ pub enum Expectation<'tcx> {
|
|||||||
/// This rvalue expression will be wrapped in `&` or `Box` and coerced
|
/// This rvalue expression will be wrapped in `&` or `Box` and coerced
|
||||||
/// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
|
/// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
|
||||||
ExpectRvalueLikeUnsized(Ty<'tcx>),
|
ExpectRvalueLikeUnsized(Ty<'tcx>),
|
||||||
|
|
||||||
IsLast(Span),
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'tcx> Expectation<'tcx> {
|
impl<'a, 'tcx> Expectation<'tcx> {
|
||||||
@ -88,13 +86,12 @@ fn resolve(self, fcx: &FnCtxt<'a, 'tcx>) -> Expectation<'tcx> {
|
|||||||
ExpectCastableToType(t) => ExpectCastableToType(fcx.resolve_vars_if_possible(t)),
|
ExpectCastableToType(t) => ExpectCastableToType(fcx.resolve_vars_if_possible(t)),
|
||||||
ExpectHasType(t) => ExpectHasType(fcx.resolve_vars_if_possible(t)),
|
ExpectHasType(t) => ExpectHasType(fcx.resolve_vars_if_possible(t)),
|
||||||
ExpectRvalueLikeUnsized(t) => ExpectRvalueLikeUnsized(fcx.resolve_vars_if_possible(t)),
|
ExpectRvalueLikeUnsized(t) => ExpectRvalueLikeUnsized(fcx.resolve_vars_if_possible(t)),
|
||||||
IsLast(sp) => IsLast(sp),
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(super) fn to_option(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
|
pub(super) fn to_option(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
|
||||||
match self.resolve(fcx) {
|
match self.resolve(fcx) {
|
||||||
NoExpectation | IsLast(_) => None,
|
NoExpectation => None,
|
||||||
ExpectCastableToType(ty) | ExpectHasType(ty) | ExpectRvalueLikeUnsized(ty) => Some(ty),
|
ExpectCastableToType(ty) | ExpectHasType(ty) | ExpectRvalueLikeUnsized(ty) => Some(ty),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -106,9 +103,7 @@ pub(super) fn to_option(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
|
|||||||
pub(super) fn only_has_type(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
|
pub(super) fn only_has_type(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
|
||||||
match self {
|
match self {
|
||||||
ExpectHasType(ty) => Some(fcx.resolve_vars_if_possible(ty)),
|
ExpectHasType(ty) => Some(fcx.resolve_vars_if_possible(ty)),
|
||||||
NoExpectation | ExpectCastableToType(_) | ExpectRvalueLikeUnsized(_) | IsLast(_) => {
|
NoExpectation | ExpectCastableToType(_) | ExpectRvalueLikeUnsized(_) => None,
|
||||||
None
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -60,28 +60,13 @@
|
|||||||
use rustc_trait_selection::traits::{self, ObligationCauseCode};
|
use rustc_trait_selection::traits::{self, ObligationCauseCode};
|
||||||
|
|
||||||
impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
||||||
fn check_expr_eq_type(&self, expr: &'tcx hir::Expr<'tcx>, expected: Ty<'tcx>) {
|
|
||||||
let ty = self.check_expr_with_hint(expr, expected);
|
|
||||||
self.demand_eqtype(expr.span, expected, ty);
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn check_expr_has_type_or_error(
|
pub fn check_expr_has_type_or_error(
|
||||||
&self,
|
&self,
|
||||||
expr: &'tcx hir::Expr<'tcx>,
|
expr: &'tcx hir::Expr<'tcx>,
|
||||||
expected: Ty<'tcx>,
|
expected_ty: Ty<'tcx>,
|
||||||
extend_err: impl FnMut(&mut Diagnostic),
|
extend_err: impl FnOnce(&mut Diagnostic),
|
||||||
) -> Ty<'tcx> {
|
) -> Ty<'tcx> {
|
||||||
self.check_expr_meets_expectation_or_error(expr, ExpectHasType(expected), extend_err)
|
let mut ty = self.check_expr_with_expectation(expr, ExpectHasType(expected_ty));
|
||||||
}
|
|
||||||
|
|
||||||
fn check_expr_meets_expectation_or_error(
|
|
||||||
&self,
|
|
||||||
expr: &'tcx hir::Expr<'tcx>,
|
|
||||||
expected: Expectation<'tcx>,
|
|
||||||
mut extend_err: impl FnMut(&mut Diagnostic),
|
|
||||||
) -> Ty<'tcx> {
|
|
||||||
let expected_ty = expected.to_option(&self).unwrap_or(self.tcx.types.bool);
|
|
||||||
let mut ty = self.check_expr_with_expectation(expr, expected);
|
|
||||||
|
|
||||||
// While we don't allow *arbitrary* coercions here, we *do* allow
|
// While we don't allow *arbitrary* coercions here, we *do* allow
|
||||||
// coercions from ! to `expected`.
|
// coercions from ! to `expected`.
|
||||||
@ -341,9 +326,10 @@ fn check_expr_kind(
|
|||||||
}
|
}
|
||||||
ExprKind::Cast(e, t) => self.check_expr_cast(e, t, expr),
|
ExprKind::Cast(e, t) => self.check_expr_cast(e, t, expr),
|
||||||
ExprKind::Type(e, t) => {
|
ExprKind::Type(e, t) => {
|
||||||
let ty = self.to_ty_saving_user_provided_ty(&t);
|
let ascribed_ty = self.to_ty_saving_user_provided_ty(&t);
|
||||||
self.check_expr_eq_type(&e, ty);
|
let ty = self.check_expr_with_hint(e, ascribed_ty);
|
||||||
ty
|
self.demand_eqtype(e.span, ascribed_ty, ty);
|
||||||
|
ascribed_ty
|
||||||
}
|
}
|
||||||
ExprKind::If(cond, then_expr, opt_else_expr) => {
|
ExprKind::If(cond, then_expr, opt_else_expr) => {
|
||||||
self.check_then_else(cond, then_expr, opt_else_expr, expr.span, expected)
|
self.check_then_else(cond, then_expr, opt_else_expr, expr.span, expected)
|
||||||
@ -666,7 +652,7 @@ fn check_expr_break(
|
|||||||
coerce.coerce_forced_unit(
|
coerce.coerce_forced_unit(
|
||||||
self,
|
self,
|
||||||
&cause,
|
&cause,
|
||||||
&mut |mut err| {
|
|mut err| {
|
||||||
self.suggest_mismatched_types_on_tail(
|
self.suggest_mismatched_types_on_tail(
|
||||||
&mut err, expr, ty, e_ty, target_id,
|
&mut err, expr, ty, e_ty, target_id,
|
||||||
);
|
);
|
||||||
@ -762,7 +748,7 @@ fn check_expr_return(
|
|||||||
coercion.coerce_forced_unit(
|
coercion.coerce_forced_unit(
|
||||||
self,
|
self,
|
||||||
&cause,
|
&cause,
|
||||||
&mut |db| {
|
|db| {
|
||||||
let span = fn_decl.output.span();
|
let span = fn_decl.output.span();
|
||||||
if let Ok(snippet) = self.tcx.sess.source_map().span_to_snippet(span) {
|
if let Ok(snippet) = self.tcx.sess.source_map().span_to_snippet(span) {
|
||||||
db.span_label(
|
db.span_label(
|
||||||
@ -774,7 +760,7 @@ fn check_expr_return(
|
|||||||
true,
|
true,
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
coercion.coerce_forced_unit(self, &cause, &mut |_| (), true);
|
coercion.coerce_forced_unit(self, &cause, |_| (), true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
self.tcx.types.never
|
self.tcx.types.never
|
||||||
|
@ -1485,7 +1485,7 @@ pub fn check_decl_local(&self, local: &'tcx hir::Local<'tcx>) {
|
|||||||
self.check_decl(local.into());
|
self.check_decl(local.into());
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn check_stmt(&self, stmt: &'tcx hir::Stmt<'tcx>, is_last: bool) {
|
pub fn check_stmt(&self, stmt: &'tcx hir::Stmt<'tcx>) {
|
||||||
// Don't do all the complex logic below for `DeclItem`.
|
// Don't do all the complex logic below for `DeclItem`.
|
||||||
match stmt.kind {
|
match stmt.kind {
|
||||||
hir::StmtKind::Item(..) => return,
|
hir::StmtKind::Item(..) => return,
|
||||||
@ -1512,14 +1512,7 @@ pub fn check_stmt(&self, stmt: &'tcx hir::Stmt<'tcx>, is_last: bool) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
hir::StmtKind::Semi(ref expr) => {
|
hir::StmtKind::Semi(ref expr) => {
|
||||||
// All of this is equivalent to calling `check_expr`, but it is inlined out here
|
self.check_expr(expr);
|
||||||
// in order to capture the fact that this `match` is the last statement in its
|
|
||||||
// function. This is done for better suggestions to remove the `;`.
|
|
||||||
let expectation = match expr.kind {
|
|
||||||
hir::ExprKind::Match(..) if is_last => IsLast(stmt.span),
|
|
||||||
_ => NoExpectation,
|
|
||||||
};
|
|
||||||
self.check_expr_with_expectation(expr, expectation);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1570,8 +1563,8 @@ pub(in super::super) fn check_block_with_expected(
|
|||||||
let ctxt = BreakableCtxt { coerce: Some(coerce), may_break: false };
|
let ctxt = BreakableCtxt { coerce: Some(coerce), may_break: false };
|
||||||
|
|
||||||
let (ctxt, ()) = self.with_breakable_ctxt(blk.hir_id, ctxt, || {
|
let (ctxt, ()) = self.with_breakable_ctxt(blk.hir_id, ctxt, || {
|
||||||
for (pos, s) in blk.stmts.iter().enumerate() {
|
for s in blk.stmts {
|
||||||
self.check_stmt(s, blk.stmts.len() - 1 == pos);
|
self.check_stmt(s);
|
||||||
}
|
}
|
||||||
|
|
||||||
// check the tail expression **without** holding the
|
// check the tail expression **without** holding the
|
||||||
@ -1594,9 +1587,9 @@ pub(in super::super) fn check_block_with_expected(
|
|||||||
&cause,
|
&cause,
|
||||||
Some(tail_expr),
|
Some(tail_expr),
|
||||||
tail_expr_ty,
|
tail_expr_ty,
|
||||||
Some(&mut |diag: &mut Diagnostic| {
|
|diag| {
|
||||||
self.suggest_block_to_brackets(diag, blk, tail_expr_ty, ty_for_diagnostic);
|
self.suggest_block_to_brackets(diag, blk, tail_expr_ty, ty_for_diagnostic);
|
||||||
}),
|
},
|
||||||
false,
|
false,
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
@ -1633,7 +1626,7 @@ pub(in super::super) fn check_block_with_expected(
|
|||||||
coerce.coerce_forced_unit(
|
coerce.coerce_forced_unit(
|
||||||
self,
|
self,
|
||||||
&self.misc(sp),
|
&self.misc(sp),
|
||||||
&mut |err| {
|
|err| {
|
||||||
if let Some(expected_ty) = expected.only_has_type(self) {
|
if let Some(expected_ty) = expected.only_has_type(self) {
|
||||||
if blk.stmts.is_empty() && blk.expr.is_none() {
|
if blk.stmts.is_empty() && blk.expr.is_none() {
|
||||||
self.suggest_boxing_when_appropriate(
|
self.suggest_boxing_when_appropriate(
|
||||||
|
Loading…
Reference in New Issue
Block a user