1 // ignore-tidy-filelength
7 Within the check phase of type check, we check each item one at a time
8 (bodies of function expressions are checked as part of the containing
9 function). Inference is used to supply types wherever they are unknown.
11 By far the most complex case is checking the body of a function. This
12 can be broken down into several distinct phases:
14 - gather: creates type variables to represent the type of each local
15 variable and pattern binding.
17 - main: the main pass does the lion's share of the work: it
18 determines the types of all expressions, resolves
19 methods, checks for most invalid conditions, and so forth. In
20 some cases, where a type is unknown, it may create a type or region
21 variable and use that as the type of an expression.
23 In the process of checking, various constraints will be placed on
24 these type variables through the subtyping relationships requested
25 through the `demand` module. The `infer` module is in charge
26 of resolving those constraints.
28 - regionck: after main is complete, the regionck pass goes over all
29 types looking for regions and making sure that they did not escape
30 into places they are not in scope. This may also influence the
31 final assignments of the various region variables if there is some
34 - writeback: writes the final types within a function body, replacing
35 type variables with their final inferred types. These final types
36 are written into the `tcx.node_types` table, which should *never* contain
37 any reference to a type variable.
41 While type checking a function, the intermediate types for the
42 expressions, blocks, and so forth contained within the function are
43 stored in `fcx.node_types` and `fcx.node_substs`. These types
44 may contain unresolved type variables. After type checking is
45 complete, the functions in the writeback module are used to take the
46 types from this table, resolve them, and then write them into their
47 permanent home in the type context `tcx`.
49 This means that during inferencing you should use `fcx.write_ty()`
50 and `fcx.expr_ty()` / `fcx.node_ty()` to write/obtain the types of
51 nodes within the function.
53 The types of top-level items, which never contain unbound type
54 variables, are stored directly into the `tcx` typeck_results.
56 N.B., a type variable is not the same thing as a type parameter. A
57 type variable is rather an "instance" of a type parameter: that is,
58 given a generic function `fn foo<T>(t: T)`: while checking the
59 function `foo`, the type `ty_param(0)` refers to the type `T`, which
60 is treated in abstract. When `foo()` is called, however, `T` will be
61 substituted for a fresh type variable `N`. This variable will
62 eventually be resolved to some concrete type (which might itself be
77 mod generator_interior;
89 AstConv, ExplicitLateBound, GenericArgCountMismatch, GenericArgCountResult, PathSeg,
92 use rustc_ast::util::parser::ExprPrecedence;
93 use rustc_attr as attr;
94 use rustc_data_structures::captures::Captures;
95 use rustc_data_structures::fx::{FxHashMap, FxHashSet};
96 use rustc_errors::ErrorReported;
97 use rustc_errors::{pluralize, struct_span_err, Applicability, DiagnosticBuilder, DiagnosticId};
99 use rustc_hir::def::{CtorOf, DefKind, Res};
100 use rustc_hir::def_id::{CrateNum, DefId, DefIdMap, LocalDefId, LOCAL_CRATE};
101 use rustc_hir::intravisit::{self, NestedVisitorMap, Visitor};
102 use rustc_hir::itemlikevisit::ItemLikeVisitor;
103 use rustc_hir::lang_items::{
104 FutureTraitLangItem, PinTypeLangItem, SizedTraitLangItem, VaListTypeLangItem,
106 use rustc_hir::{ExprKind, GenericArg, HirIdMap, ItemKind, Node, PatKind, QPath};
107 use rustc_index::bit_set::BitSet;
108 use rustc_index::vec::Idx;
109 use rustc_infer::infer;
110 use rustc_infer::infer::canonical::{Canonical, OriginalQueryValues, QueryResponse};
111 use rustc_infer::infer::error_reporting::TypeAnnotationNeeded::E0282;
112 use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
113 use rustc_infer::infer::unify_key::{ConstVariableOrigin, ConstVariableOriginKind};
114 use rustc_infer::infer::{InferCtxt, InferOk, InferResult, RegionVariableOrigin, TyCtxtInferExt};
115 use rustc_middle::hir::map::blocks::FnLikeNode;
116 use rustc_middle::mir::interpret::ConstValue;
117 use rustc_middle::ty::adjustment::{
118 Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability,
120 use rustc_middle::ty::fold::{TypeFoldable, TypeFolder};
121 use rustc_middle::ty::query::Providers;
122 use rustc_middle::ty::subst::{self, InternalSubsts, Subst, SubstsRef};
123 use rustc_middle::ty::subst::{GenericArgKind, UserSelfTy, UserSubsts};
124 use rustc_middle::ty::util::{Discr, IntTypeExt, Representability};
125 use rustc_middle::ty::WithConstness;
126 use rustc_middle::ty::{self, AdtKind, CanonicalUserType, Const, DefIdTree, GenericParamDefKind};
127 use rustc_middle::ty::{RegionKind, ToPolyTraitRef, ToPredicate, Ty, TyCtxt, UserType};
128 use rustc_session::config::{self, EntryFnType};
129 use rustc_session::lint;
130 use rustc_session::parse::feature_err;
131 use rustc_session::Session;
132 use rustc_span::hygiene::DesugaringKind;
133 use rustc_span::source_map::{original_sp, DUMMY_SP};
134 use rustc_span::symbol::{kw, sym, Ident};
135 use rustc_span::{self, BytePos, MultiSpan, Span};
136 use rustc_target::abi::VariantIdx;
137 use rustc_target::spec::abi::Abi;
138 use rustc_trait_selection::infer::InferCtxtExt as _;
139 use rustc_trait_selection::opaque_types::{InferCtxtExt as _, OpaqueTypeDecl};
140 use rustc_trait_selection::traits::error_reporting::recursive_type_with_infinite_size_error;
141 use rustc_trait_selection::traits::error_reporting::suggestions::ReturnsVisitor;
142 use rustc_trait_selection::traits::error_reporting::InferCtxtExt as _;
143 use rustc_trait_selection::traits::query::evaluate_obligation::InferCtxtExt as _;
144 use rustc_trait_selection::traits::{
145 self, ObligationCause, ObligationCauseCode, TraitEngine, TraitEngineExt,
148 use std::cell::{Cell, Ref, RefCell, RefMut};
150 use std::collections::hash_map::Entry;
152 use std::mem::replace;
153 use std::ops::{self, Deref};
156 use crate::require_c_abi_if_c_variadic;
157 use crate::util::common::indenter;
159 use self::callee::DeferredCallResolution;
160 use self::coercion::{CoerceMany, DynamicCoerceMany};
161 use self::compare_method::{compare_const_impl, compare_impl_method, compare_ty_impl};
162 use self::method::{MethodCallee, SelfSource};
163 pub use self::Expectation::*;
164 use self::TupleArgumentsFlag::*;
167 macro_rules! type_error_struct {
168 ($session:expr, $span:expr, $typ:expr, $code:ident, $($message:tt)*) => ({
169 if $typ.references_error() {
170 $session.diagnostic().struct_dummy()
172 rustc_errors::struct_span_err!($session, $span, $code, $($message)*)
177 /// The type of a local binding, including the revealed type for anon types.
178 #[derive(Copy, Clone, Debug)]
179 pub struct LocalTy<'tcx> {
181 revealed_ty: Ty<'tcx>,
184 /// A wrapper for `InferCtxt`'s `in_progress_typeck_results` field.
185 #[derive(Copy, Clone)]
186 struct MaybeInProgressTables<'a, 'tcx> {
187 maybe_typeck_results: Option<&'a RefCell<ty::TypeckResults<'tcx>>>,
190 impl<'a, 'tcx> MaybeInProgressTables<'a, 'tcx> {
191 fn borrow(self) -> Ref<'a, ty::TypeckResults<'tcx>> {
192 match self.maybe_typeck_results {
193 Some(typeck_results) => typeck_results.borrow(),
195 "MaybeInProgressTables: inh/fcx.typeck_results.borrow() with no typeck results"
200 fn borrow_mut(self) -> RefMut<'a, ty::TypeckResults<'tcx>> {
201 match self.maybe_typeck_results {
202 Some(typeck_results) => typeck_results.borrow_mut(),
204 "MaybeInProgressTables: inh/fcx.typeck_results.borrow_mut() with no typeck results"
210 /// Closures defined within the function. For example:
213 /// bar(move|| { ... })
216 /// Here, the function `foo()` and the closure passed to
217 /// `bar()` will each have their own `FnCtxt`, but they will
218 /// share the inherited fields.
219 pub struct Inherited<'a, 'tcx> {
220 infcx: InferCtxt<'a, 'tcx>,
222 typeck_results: MaybeInProgressTables<'a, 'tcx>,
224 locals: RefCell<HirIdMap<LocalTy<'tcx>>>,
226 fulfillment_cx: RefCell<Box<dyn TraitEngine<'tcx>>>,
228 // Some additional `Sized` obligations badly affect type inference.
229 // These obligations are added in a later stage of typeck.
230 deferred_sized_obligations: RefCell<Vec<(Ty<'tcx>, Span, traits::ObligationCauseCode<'tcx>)>>,
232 // When we process a call like `c()` where `c` is a closure type,
233 // we may not have decided yet whether `c` is a `Fn`, `FnMut`, or
234 // `FnOnce` closure. In that case, we defer full resolution of the
235 // call until upvar inference can kick in and make the
236 // decision. We keep these deferred resolutions grouped by the
237 // def-id of the closure, so that once we decide, we can easily go
238 // back and process them.
239 deferred_call_resolutions: RefCell<DefIdMap<Vec<DeferredCallResolution<'tcx>>>>,
241 deferred_cast_checks: RefCell<Vec<cast::CastCheck<'tcx>>>,
243 deferred_generator_interiors: RefCell<Vec<(hir::BodyId, Ty<'tcx>, hir::GeneratorKind)>>,
245 // Opaque types found in explicit return types and their
246 // associated fresh inference variable. Writeback resolves these
247 // variables to get the concrete type, which can be used to
248 // 'de-opaque' OpaqueTypeDecl, after typeck is done with all functions.
249 opaque_types: RefCell<DefIdMap<OpaqueTypeDecl<'tcx>>>,
251 /// A map from inference variables created from opaque
252 /// type instantiations (`ty::Infer`) to the actual opaque
253 /// type (`ty::Opaque`). Used during fallback to map unconstrained
254 /// opaque type inference variables to their corresponding
256 opaque_types_vars: RefCell<FxHashMap<Ty<'tcx>, Ty<'tcx>>>,
258 body_id: Option<hir::BodyId>,
261 impl<'a, 'tcx> Deref for Inherited<'a, 'tcx> {
262 type Target = InferCtxt<'a, 'tcx>;
263 fn deref(&self) -> &Self::Target {
268 /// When type-checking an expression, we propagate downward
269 /// whatever type hint we are able in the form of an `Expectation`.
270 #[derive(Copy, Clone, Debug)]
271 pub enum Expectation<'tcx> {
272 /// We know nothing about what type this expression should have.
275 /// This expression should have the type given (or some subtype).
276 ExpectHasType(Ty<'tcx>),
278 /// This expression will be cast to the `Ty`.
279 ExpectCastableToType(Ty<'tcx>),
281 /// This rvalue expression will be wrapped in `&` or `Box` and coerced
282 /// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
283 ExpectRvalueLikeUnsized(Ty<'tcx>),
286 impl<'a, 'tcx> Expectation<'tcx> {
287 // Disregard "castable to" expectations because they
288 // can lead us astray. Consider for example `if cond
289 // {22} else {c} as u8` -- if we propagate the
290 // "castable to u8" constraint to 22, it will pick the
291 // type 22u8, which is overly constrained (c might not
292 // be a u8). In effect, the problem is that the
293 // "castable to" expectation is not the tightest thing
294 // we can say, so we want to drop it in this case.
295 // The tightest thing we can say is "must unify with
296 // else branch". Note that in the case of a "has type"
297 // constraint, this limitation does not hold.
299 // If the expected type is just a type variable, then don't use
300 // an expected type. Otherwise, we might write parts of the type
301 // when checking the 'then' block which are incompatible with the
303 fn adjust_for_branches(&self, fcx: &FnCtxt<'a, 'tcx>) -> Expectation<'tcx> {
305 ExpectHasType(ety) => {
306 let ety = fcx.shallow_resolve(ety);
307 if !ety.is_ty_var() { ExpectHasType(ety) } else { NoExpectation }
309 ExpectRvalueLikeUnsized(ety) => ExpectRvalueLikeUnsized(ety),
314 /// Provides an expectation for an rvalue expression given an *optional*
315 /// hint, which is not required for type safety (the resulting type might
316 /// be checked higher up, as is the case with `&expr` and `box expr`), but
317 /// is useful in determining the concrete type.
319 /// The primary use case is where the expected type is a fat pointer,
320 /// like `&[isize]`. For example, consider the following statement:
322 /// let x: &[isize] = &[1, 2, 3];
324 /// In this case, the expected type for the `&[1, 2, 3]` expression is
325 /// `&[isize]`. If however we were to say that `[1, 2, 3]` has the
326 /// expectation `ExpectHasType([isize])`, that would be too strong --
327 /// `[1, 2, 3]` does not have the type `[isize]` but rather `[isize; 3]`.
328 /// It is only the `&[1, 2, 3]` expression as a whole that can be coerced
329 /// to the type `&[isize]`. Therefore, we propagate this more limited hint,
330 /// which still is useful, because it informs integer literals and the like.
331 /// See the test case `test/ui/coerce-expect-unsized.rs` and #20169
332 /// for examples of where this comes up,.
333 fn rvalue_hint(fcx: &FnCtxt<'a, 'tcx>, ty: Ty<'tcx>) -> Expectation<'tcx> {
334 match fcx.tcx.struct_tail_without_normalization(ty).kind {
335 ty::Slice(_) | ty::Str | ty::Dynamic(..) => ExpectRvalueLikeUnsized(ty),
336 _ => ExpectHasType(ty),
340 // Resolves `expected` by a single level if it is a variable. If
341 // there is no expected type or resolution is not possible (e.g.,
342 // no constraints yet present), just returns `None`.
343 fn resolve(self, fcx: &FnCtxt<'a, 'tcx>) -> Expectation<'tcx> {
345 NoExpectation => NoExpectation,
346 ExpectCastableToType(t) => ExpectCastableToType(fcx.resolve_vars_if_possible(&t)),
347 ExpectHasType(t) => ExpectHasType(fcx.resolve_vars_if_possible(&t)),
348 ExpectRvalueLikeUnsized(t) => ExpectRvalueLikeUnsized(fcx.resolve_vars_if_possible(&t)),
352 fn to_option(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
353 match self.resolve(fcx) {
354 NoExpectation => None,
355 ExpectCastableToType(ty) | ExpectHasType(ty) | ExpectRvalueLikeUnsized(ty) => Some(ty),
359 /// It sometimes happens that we want to turn an expectation into
360 /// a **hard constraint** (i.e., something that must be satisfied
361 /// for the program to type-check). `only_has_type` will return
362 /// such a constraint, if it exists.
363 fn only_has_type(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
364 match self.resolve(fcx) {
365 ExpectHasType(ty) => Some(ty),
366 NoExpectation | ExpectCastableToType(_) | ExpectRvalueLikeUnsized(_) => None,
370 /// Like `only_has_type`, but instead of returning `None` if no
371 /// hard constraint exists, creates a fresh type variable.
372 fn coercion_target_type(self, fcx: &FnCtxt<'a, 'tcx>, span: Span) -> Ty<'tcx> {
373 self.only_has_type(fcx).unwrap_or_else(|| {
374 fcx.next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::MiscVariable, span })
379 #[derive(Copy, Clone, Debug, PartialEq, Eq)]
386 fn maybe_mut_place(m: hir::Mutability) -> Self {
388 hir::Mutability::Mut => Needs::MutPlace,
389 hir::Mutability::Not => Needs::None,
394 #[derive(Copy, Clone)]
395 pub struct UnsafetyState {
397 pub unsafety: hir::Unsafety,
398 pub unsafe_push_count: u32,
403 pub fn function(unsafety: hir::Unsafety, def: hir::HirId) -> UnsafetyState {
404 UnsafetyState { def, unsafety, unsafe_push_count: 0, from_fn: true }
407 pub fn recurse(&mut self, blk: &hir::Block<'_>) -> UnsafetyState {
408 use hir::BlockCheckMode;
409 match self.unsafety {
410 // If this unsafe, then if the outer function was already marked as
411 // unsafe we shouldn't attribute the unsafe'ness to the block. This
412 // way the block can be warned about instead of ignoring this
413 // extraneous block (functions are never warned about).
414 hir::Unsafety::Unsafe if self.from_fn => *self,
417 let (unsafety, def, count) = match blk.rules {
418 BlockCheckMode::PushUnsafeBlock(..) => {
419 (unsafety, blk.hir_id, self.unsafe_push_count.checked_add(1).unwrap())
421 BlockCheckMode::PopUnsafeBlock(..) => {
422 (unsafety, blk.hir_id, self.unsafe_push_count.checked_sub(1).unwrap())
424 BlockCheckMode::UnsafeBlock(..) => {
425 (hir::Unsafety::Unsafe, blk.hir_id, self.unsafe_push_count)
427 BlockCheckMode::DefaultBlock => (unsafety, self.def, self.unsafe_push_count),
429 UnsafetyState { def, unsafety, unsafe_push_count: count, from_fn: false }
435 #[derive(Debug, Copy, Clone)]
441 /// Tracks whether executing a node may exit normally (versus
442 /// return/break/panic, which "diverge", leaving dead code in their
443 /// wake). Tracked semi-automatically (through type variables marked
444 /// as diverging), with some manual adjustments for control-flow
445 /// primitives (approximating a CFG).
446 #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)]
448 /// Potentially unknown, some cases converge,
449 /// others require a CFG to determine them.
452 /// Definitely known to diverge and therefore
453 /// not reach the next sibling or its parent.
455 /// The `Span` points to the expression
456 /// that caused us to diverge
457 /// (e.g. `return`, `break`, etc).
459 /// In some cases (e.g. a `match` expression
460 /// where all arms diverge), we may be
461 /// able to provide a more informative
462 /// message to the user.
463 /// If this is `None`, a default message
464 /// will be generated, which is suitable
466 custom_note: Option<&'static str>,
469 /// Same as `Always` but with a reachability
470 /// warning already emitted.
474 // Convenience impls for combining `Diverges`.
476 impl ops::BitAnd for Diverges {
478 fn bitand(self, other: Self) -> Self {
479 cmp::min(self, other)
483 impl ops::BitOr for Diverges {
485 fn bitor(self, other: Self) -> Self {
486 cmp::max(self, other)
490 impl ops::BitAndAssign for Diverges {
491 fn bitand_assign(&mut self, other: Self) {
492 *self = *self & other;
496 impl ops::BitOrAssign for Diverges {
497 fn bitor_assign(&mut self, other: Self) {
498 *self = *self | other;
503 /// Creates a `Diverges::Always` with the provided `span` and the default note message.
504 fn always(span: Span) -> Diverges {
505 Diverges::Always { span, custom_note: None }
508 fn is_always(self) -> bool {
509 // Enum comparison ignores the
510 // contents of fields, so we just
511 // fill them in with garbage here.
512 self >= Diverges::Always { span: DUMMY_SP, custom_note: None }
516 pub struct BreakableCtxt<'tcx> {
519 // this is `null` for loops where break with a value is illegal,
520 // such as `while`, `for`, and `while let`
521 coerce: Option<DynamicCoerceMany<'tcx>>,
524 pub struct EnclosingBreakables<'tcx> {
525 stack: Vec<BreakableCtxt<'tcx>>,
526 by_id: HirIdMap<usize>,
529 impl<'tcx> EnclosingBreakables<'tcx> {
530 fn find_breakable(&mut self, target_id: hir::HirId) -> &mut BreakableCtxt<'tcx> {
531 self.opt_find_breakable(target_id).unwrap_or_else(|| {
532 bug!("could not find enclosing breakable with id {}", target_id);
536 fn opt_find_breakable(&mut self, target_id: hir::HirId) -> Option<&mut BreakableCtxt<'tcx>> {
537 match self.by_id.get(&target_id) {
538 Some(ix) => Some(&mut self.stack[*ix]),
544 pub struct FnCtxt<'a, 'tcx> {
547 /// The parameter environment used for proving trait obligations
548 /// in this function. This can change when we descend into
549 /// closures (as they bring new things into scope), hence it is
550 /// not part of `Inherited` (as of the time of this writing,
551 /// closures do not yet change the environment, but they will
553 param_env: ty::ParamEnv<'tcx>,
555 /// Number of errors that had been reported when we started
556 /// checking this function. On exit, if we find that *more* errors
557 /// have been reported, we will skip regionck and other work that
558 /// expects the types within the function to be consistent.
559 // FIXME(matthewjasper) This should not exist, and it's not correct
560 // if type checking is run in parallel.
561 err_count_on_creation: usize,
563 /// If `Some`, this stores coercion information for returned
564 /// expressions. If `None`, this is in a context where return is
565 /// inappropriate, such as a const expression.
567 /// This is a `RefCell<DynamicCoerceMany>`, which means that we
568 /// can track all the return expressions and then use them to
569 /// compute a useful coercion from the set, similar to a match
570 /// expression or other branching context. You can use methods
571 /// like `expected_ty` to access the declared return type (if
573 ret_coercion: Option<RefCell<DynamicCoerceMany<'tcx>>>,
575 /// First span of a return site that we find. Used in error messages.
576 ret_coercion_span: RefCell<Option<Span>>,
578 resume_yield_tys: Option<(Ty<'tcx>, Ty<'tcx>)>,
580 ps: RefCell<UnsafetyState>,
582 /// Whether the last checked node generates a divergence (e.g.,
583 /// `return` will set this to `Always`). In general, when entering
584 /// an expression or other node in the tree, the initial value
585 /// indicates whether prior parts of the containing expression may
586 /// have diverged. It is then typically set to `Maybe` (and the
587 /// old value remembered) for processing the subparts of the
588 /// current expression. As each subpart is processed, they may set
589 /// the flag to `Always`, etc. Finally, at the end, we take the
590 /// result and "union" it with the original value, so that when we
591 /// return the flag indicates if any subpart of the parent
592 /// expression (up to and including this part) has diverged. So,
593 /// if you read it after evaluating a subexpression `X`, the value
594 /// you get indicates whether any subexpression that was
595 /// evaluating up to and including `X` diverged.
597 /// We currently use this flag only for diagnostic purposes:
599 /// - To warn about unreachable code: if, after processing a
600 /// sub-expression but before we have applied the effects of the
601 /// current node, we see that the flag is set to `Always`, we
602 /// can issue a warning. This corresponds to something like
603 /// `foo(return)`; we warn on the `foo()` expression. (We then
604 /// update the flag to `WarnedAlways` to suppress duplicate
605 /// reports.) Similarly, if we traverse to a fresh statement (or
606 /// tail expression) from a `Always` setting, we will issue a
607 /// warning. This corresponds to something like `{return;
608 /// foo();}` or `{return; 22}`, where we would warn on the
611 /// An expression represents dead code if, after checking it,
612 /// the diverges flag is set to something other than `Maybe`.
613 diverges: Cell<Diverges>,
615 /// Whether any child nodes have any type errors.
616 has_errors: Cell<bool>,
618 enclosing_breakables: RefCell<EnclosingBreakables<'tcx>>,
620 inh: &'a Inherited<'a, 'tcx>,
623 impl<'a, 'tcx> Deref for FnCtxt<'a, 'tcx> {
624 type Target = Inherited<'a, 'tcx>;
625 fn deref(&self) -> &Self::Target {
630 /// Helper type of a temporary returned by `Inherited::build(...)`.
631 /// Necessary because we can't write the following bound:
632 /// `F: for<'b, 'tcx> where 'tcx FnOnce(Inherited<'b, 'tcx>)`.
633 pub struct InheritedBuilder<'tcx> {
634 infcx: infer::InferCtxtBuilder<'tcx>,
638 impl Inherited<'_, 'tcx> {
639 pub fn build(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> InheritedBuilder<'tcx> {
640 let hir_owner = tcx.hir().local_def_id_to_hir_id(def_id).owner;
643 infcx: tcx.infer_ctxt().with_fresh_in_progress_typeck_results(hir_owner),
649 impl<'tcx> InheritedBuilder<'tcx> {
650 pub fn enter<F, R>(&mut self, f: F) -> R
652 F: for<'a> FnOnce(Inherited<'a, 'tcx>) -> R,
654 let def_id = self.def_id;
655 self.infcx.enter(|infcx| f(Inherited::new(infcx, def_id)))
659 impl Inherited<'a, 'tcx> {
660 fn new(infcx: InferCtxt<'a, 'tcx>, def_id: LocalDefId) -> Self {
662 let item_id = tcx.hir().local_def_id_to_hir_id(def_id);
663 let body_id = tcx.hir().maybe_body_owned_by(item_id);
666 typeck_results: MaybeInProgressTables {
667 maybe_typeck_results: infcx.in_progress_typeck_results,
670 fulfillment_cx: RefCell::new(TraitEngine::new(tcx)),
671 locals: RefCell::new(Default::default()),
672 deferred_sized_obligations: RefCell::new(Vec::new()),
673 deferred_call_resolutions: RefCell::new(Default::default()),
674 deferred_cast_checks: RefCell::new(Vec::new()),
675 deferred_generator_interiors: RefCell::new(Vec::new()),
676 opaque_types: RefCell::new(Default::default()),
677 opaque_types_vars: RefCell::new(Default::default()),
682 fn register_predicate(&self, obligation: traits::PredicateObligation<'tcx>) {
683 debug!("register_predicate({:?})", obligation);
684 if obligation.has_escaping_bound_vars() {
685 span_bug!(obligation.cause.span, "escaping bound vars in predicate {:?}", obligation);
687 self.fulfillment_cx.borrow_mut().register_predicate_obligation(self, obligation);
690 fn register_predicates<I>(&self, obligations: I)
692 I: IntoIterator<Item = traits::PredicateObligation<'tcx>>,
694 for obligation in obligations {
695 self.register_predicate(obligation);
699 fn register_infer_ok_obligations<T>(&self, infer_ok: InferOk<'tcx, T>) -> T {
700 self.register_predicates(infer_ok.obligations);
704 fn normalize_associated_types_in<T>(
708 param_env: ty::ParamEnv<'tcx>,
712 T: TypeFoldable<'tcx>,
714 let ok = self.partially_normalize_associated_types_in(span, body_id, param_env, value);
715 self.register_infer_ok_obligations(ok)
719 struct CheckItemTypesVisitor<'tcx> {
723 impl ItemLikeVisitor<'tcx> for CheckItemTypesVisitor<'tcx> {
724 fn visit_item(&mut self, i: &'tcx hir::Item<'tcx>) {
725 check_item_type(self.tcx, i);
727 fn visit_trait_item(&mut self, _: &'tcx hir::TraitItem<'tcx>) {}
728 fn visit_impl_item(&mut self, _: &'tcx hir::ImplItem<'tcx>) {}
731 pub fn check_wf_new(tcx: TyCtxt<'_>) {
732 let visit = wfcheck::CheckTypeWellFormedVisitor::new(tcx);
733 tcx.hir().krate().par_visit_all_item_likes(&visit);
736 fn check_mod_item_types(tcx: TyCtxt<'_>, module_def_id: LocalDefId) {
737 tcx.hir().visit_item_likes_in_module(module_def_id, &mut CheckItemTypesVisitor { tcx });
740 fn typeck_item_bodies(tcx: TyCtxt<'_>, crate_num: CrateNum) {
741 debug_assert!(crate_num == LOCAL_CRATE);
742 tcx.par_body_owners(|body_owner_def_id| {
743 tcx.ensure().typeck(body_owner_def_id);
747 fn check_item_well_formed(tcx: TyCtxt<'_>, def_id: LocalDefId) {
748 wfcheck::check_item_well_formed(tcx, def_id);
751 fn check_trait_item_well_formed(tcx: TyCtxt<'_>, def_id: LocalDefId) {
752 wfcheck::check_trait_item(tcx, def_id);
755 fn check_impl_item_well_formed(tcx: TyCtxt<'_>, def_id: LocalDefId) {
756 wfcheck::check_impl_item(tcx, def_id);
759 pub fn provide(providers: &mut Providers) {
760 method::provide(providers);
761 *providers = Providers {
765 diagnostic_only_typeck,
769 check_item_well_formed,
770 check_trait_item_well_formed,
771 check_impl_item_well_formed,
772 check_mod_item_types,
777 fn adt_destructor(tcx: TyCtxt<'_>, def_id: DefId) -> Option<ty::Destructor> {
778 tcx.calculate_dtor(def_id, &mut dropck::check_drop_impl)
781 /// If this `DefId` is a "primary tables entry", returns
782 /// `Some((body_id, header, decl))` with information about
783 /// it's body-id, fn-header and fn-decl (if any). Otherwise,
786 /// If this function returns `Some`, then `typeck_results(def_id)` will
787 /// succeed; if it returns `None`, then `typeck_results(def_id)` may or
788 /// may not succeed. In some cases where this function returns `None`
789 /// (notably closures), `typeck_results(def_id)` would wind up
790 /// redirecting to the owning function.
794 ) -> Option<(hir::BodyId, Option<&hir::Ty<'_>>, Option<&hir::FnHeader>, Option<&hir::FnDecl<'_>>)> {
795 match tcx.hir().get(id) {
796 Node::Item(item) => match item.kind {
797 hir::ItemKind::Const(ref ty, body) | hir::ItemKind::Static(ref ty, _, body) => {
798 Some((body, Some(ty), None, None))
800 hir::ItemKind::Fn(ref sig, .., body) => {
801 Some((body, None, Some(&sig.header), Some(&sig.decl)))
805 Node::TraitItem(item) => match item.kind {
806 hir::TraitItemKind::Const(ref ty, Some(body)) => Some((body, Some(ty), None, None)),
807 hir::TraitItemKind::Fn(ref sig, hir::TraitFn::Provided(body)) => {
808 Some((body, None, Some(&sig.header), Some(&sig.decl)))
812 Node::ImplItem(item) => match item.kind {
813 hir::ImplItemKind::Const(ref ty, body) => Some((body, Some(ty), None, None)),
814 hir::ImplItemKind::Fn(ref sig, body) => {
815 Some((body, None, Some(&sig.header), Some(&sig.decl)))
819 Node::AnonConst(constant) => Some((constant.body, None, None, None)),
824 fn has_typeck_results(tcx: TyCtxt<'_>, def_id: DefId) -> bool {
825 // Closures' typeck results come from their outermost function,
826 // as they are part of the same "inference environment".
827 let outer_def_id = tcx.closure_base_def_id(def_id);
828 if outer_def_id != def_id {
829 return tcx.has_typeck_results(outer_def_id);
832 if let Some(def_id) = def_id.as_local() {
833 let id = tcx.hir().local_def_id_to_hir_id(def_id);
834 primary_body_of(tcx, id).is_some()
840 fn used_trait_imports(tcx: TyCtxt<'_>, def_id: LocalDefId) -> &FxHashSet<LocalDefId> {
841 &*tcx.typeck(def_id).used_trait_imports
844 /// Inspects the substs of opaque types, replacing any inference variables
845 /// with proper generic parameter from the identity substs.
847 /// This is run after we normalize the function signature, to fix any inference
848 /// variables introduced by the projection of associated types. This ensures that
849 /// any opaque types used in the signature continue to refer to generic parameters,
850 /// allowing them to be considered for defining uses in the function body
852 /// For example, consider this code.
857 /// fn use_it(self) -> Self::MyItem
859 /// impl<T, I> MyTrait for T where T: Iterator<Item = I> {
860 /// type MyItem = impl Iterator<Item = I>;
861 /// fn use_it(self) -> Self::MyItem {
867 /// When we normalize the signature of `use_it` from the impl block,
868 /// we will normalize `Self::MyItem` to the opaque type `impl Iterator<Item = I>`
869 /// However, this projection result may contain inference variables, due
870 /// to the way that projection works. We didn't have any inference variables
871 /// in the signature to begin with - leaving them in will cause us to incorrectly
872 /// conclude that we don't have a defining use of `MyItem`. By mapping inference
873 /// variables back to the actual generic parameters, we will correctly see that
874 /// we have a defining use of `MyItem`
875 fn fixup_opaque_types<'tcx, T>(tcx: TyCtxt<'tcx>, val: &T) -> T
877 T: TypeFoldable<'tcx>,
879 struct FixupFolder<'tcx> {
883 impl<'tcx> TypeFolder<'tcx> for FixupFolder<'tcx> {
884 fn tcx<'a>(&'a self) -> TyCtxt<'tcx> {
888 fn fold_ty(&mut self, ty: Ty<'tcx>) -> Ty<'tcx> {
890 ty::Opaque(def_id, substs) => {
891 debug!("fixup_opaque_types: found type {:?}", ty);
892 // Here, we replace any inference variables that occur within
893 // the substs of an opaque type. By definition, any type occurring
894 // in the substs has a corresponding generic parameter, which is what
895 // we replace it with.
896 // This replacement is only run on the function signature, so any
897 // inference variables that we come across must be the rust of projection
898 // (there's no other way for a user to get inference variables into
899 // a function signature).
900 if ty.needs_infer() {
901 let new_substs = InternalSubsts::for_item(self.tcx, def_id, |param, _| {
902 let old_param = substs[param.index as usize];
903 match old_param.unpack() {
904 GenericArgKind::Type(old_ty) => {
905 if let ty::Infer(_) = old_ty.kind {
906 // Replace inference type with a generic parameter
907 self.tcx.mk_param_from_def(param)
909 old_param.fold_with(self)
912 GenericArgKind::Const(old_const) => {
913 if let ty::ConstKind::Infer(_) = old_const.val {
914 // This should never happen - we currently do not support
915 // 'const projections', e.g.:
916 // `impl<T: SomeTrait> MyTrait for T where <T as SomeTrait>::MyConst == 25`
917 // which should be the only way for us to end up with a const inference
918 // variable after projection. If Rust ever gains support for this kind
919 // of projection, this should *probably* be changed to
920 // `self.tcx.mk_param_from_def(param)`
922 "Found infer const: `{:?}` in opaque type: {:?}",
927 old_param.fold_with(self)
930 GenericArgKind::Lifetime(old_region) => {
931 if let RegionKind::ReVar(_) = old_region {
932 self.tcx.mk_param_from_def(param)
934 old_param.fold_with(self)
939 let new_ty = self.tcx.mk_opaque(def_id, new_substs);
940 debug!("fixup_opaque_types: new type: {:?}", new_ty);
946 _ => ty.super_fold_with(self),
951 debug!("fixup_opaque_types({:?})", val);
952 val.fold_with(&mut FixupFolder { tcx })
955 fn typeck_const_arg<'tcx>(
957 (did, param_did): (LocalDefId, DefId),
958 ) -> &ty::TypeckResults<'tcx> {
959 let fallback = move || tcx.type_of(param_did);
960 typeck_with_fallback(tcx, did, fallback)
963 fn typeck<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> &ty::TypeckResults<'tcx> {
964 if let Some(param_did) = tcx.opt_const_param_of(def_id) {
965 tcx.typeck_const_arg((def_id, param_did))
967 let fallback = move || tcx.type_of(def_id.to_def_id());
968 typeck_with_fallback(tcx, def_id, fallback)
972 /// Used only to get `TypeckResults` for type inference during error recovery.
973 /// Currently only used for type inference of `static`s and `const`s to avoid type cycle errors.
974 fn diagnostic_only_typeck<'tcx>(tcx: TyCtxt<'tcx>, def_id: LocalDefId) -> &ty::TypeckResults<'tcx> {
975 let fallback = move || {
976 let span = tcx.hir().span(tcx.hir().local_def_id_to_hir_id(def_id));
977 tcx.ty_error_with_message(span, "diagnostic only typeck table used")
979 typeck_with_fallback(tcx, def_id, fallback)
982 fn typeck_with_fallback<'tcx>(
985 fallback: impl Fn() -> Ty<'tcx> + 'tcx,
986 ) -> &'tcx ty::TypeckResults<'tcx> {
987 // Closures' typeck results come from their outermost function,
988 // as they are part of the same "inference environment".
989 let outer_def_id = tcx.closure_base_def_id(def_id.to_def_id()).expect_local();
990 if outer_def_id != def_id {
991 return tcx.typeck(outer_def_id);
994 let id = tcx.hir().local_def_id_to_hir_id(def_id);
995 let span = tcx.hir().span(id);
997 // Figure out what primary body this item has.
998 let (body_id, body_ty, fn_header, fn_decl) = primary_body_of(tcx, id).unwrap_or_else(|| {
999 span_bug!(span, "can't type-check body of {:?}", def_id);
1001 let body = tcx.hir().body(body_id);
1003 let typeck_results = Inherited::build(tcx, def_id).enter(|inh| {
1004 let param_env = tcx.param_env(def_id);
1005 let fcx = if let (Some(header), Some(decl)) = (fn_header, fn_decl) {
1006 let fn_sig = if crate::collect::get_infer_ret_ty(&decl.output).is_some() {
1007 let fcx = FnCtxt::new(&inh, param_env, body.value.hir_id);
1013 &hir::Generics::empty(),
1020 check_abi(tcx, span, fn_sig.abi());
1022 // Compute the fty from point of view of inside the fn.
1023 let fn_sig = tcx.liberate_late_bound_regions(def_id.to_def_id(), &fn_sig);
1024 let fn_sig = inh.normalize_associated_types_in(
1031 let fn_sig = fixup_opaque_types(tcx, &fn_sig);
1033 let fcx = check_fn(&inh, param_env, fn_sig, decl, id, body, None).0;
1036 let fcx = FnCtxt::new(&inh, param_env, body.value.hir_id);
1037 let expected_type = body_ty
1038 .and_then(|ty| match ty.kind {
1039 hir::TyKind::Infer => Some(AstConv::ast_ty_to_ty(&fcx, ty)),
1042 .unwrap_or_else(fallback);
1043 let expected_type = fcx.normalize_associated_types_in(body.value.span, &expected_type);
1044 fcx.require_type_is_sized(expected_type, body.value.span, traits::ConstSized);
1046 let revealed_ty = if tcx.features().impl_trait_in_bindings {
1047 fcx.instantiate_opaque_types_from_value(id, &expected_type, body.value.span)
1052 // Gather locals in statics (because of block expressions).
1053 GatherLocalsVisitor { fcx: &fcx, parent_id: id }.visit_body(body);
1055 fcx.check_expr_coercable_to_type(&body.value, revealed_ty, None);
1057 fcx.write_ty(id, revealed_ty);
1062 // All type checking constraints were added, try to fallback unsolved variables.
1063 fcx.select_obligations_where_possible(false, |_| {});
1064 let mut fallback_has_occurred = false;
1066 // We do fallback in two passes, to try to generate
1067 // better error messages.
1068 // The first time, we do *not* replace opaque types.
1069 for ty in &fcx.unsolved_variables() {
1070 fallback_has_occurred |= fcx.fallback_if_possible(ty, FallbackMode::NoOpaque);
1072 // We now see if we can make progress. This might
1073 // cause us to unify inference variables for opaque types,
1074 // since we may have unified some other type variables
1075 // during the first phase of fallback.
1076 // This means that we only replace inference variables with their underlying
1077 // opaque types as a last resort.
1079 // In code like this:
1082 // type MyType = impl Copy;
1083 // fn produce() -> MyType { true }
1084 // fn bad_produce() -> MyType { panic!() }
1087 // we want to unify the opaque inference variable in `bad_produce`
1088 // with the diverging fallback for `panic!` (e.g. `()` or `!`).
1089 // This will produce a nice error message about conflicting concrete
1090 // types for `MyType`.
1092 // If we had tried to fallback the opaque inference variable to `MyType`,
1093 // we will generate a confusing type-check error that does not explicitly
1094 // refer to opaque types.
1095 fcx.select_obligations_where_possible(fallback_has_occurred, |_| {});
1097 // We now run fallback again, but this time we allow it to replace
1098 // unconstrained opaque type variables, in addition to performing
1099 // other kinds of fallback.
1100 for ty in &fcx.unsolved_variables() {
1101 fallback_has_occurred |= fcx.fallback_if_possible(ty, FallbackMode::All);
1104 // See if we can make any more progress.
1105 fcx.select_obligations_where_possible(fallback_has_occurred, |_| {});
1107 // Even though coercion casts provide type hints, we check casts after fallback for
1108 // backwards compatibility. This makes fallback a stronger type hint than a cast coercion.
1111 // Closure and generator analysis may run after fallback
1112 // because they don't constrain other type variables.
1113 fcx.closure_analyze(body);
1114 assert!(fcx.deferred_call_resolutions.borrow().is_empty());
1115 fcx.resolve_generator_interiors(def_id.to_def_id());
1117 for (ty, span, code) in fcx.deferred_sized_obligations.borrow_mut().drain(..) {
1118 let ty = fcx.normalize_ty(span, ty);
1119 fcx.require_type_is_sized(ty, span, code);
1122 fcx.select_all_obligations_or_error();
1124 if fn_decl.is_some() {
1125 fcx.regionck_fn(id, body);
1127 fcx.regionck_expr(body);
1130 fcx.resolve_type_vars_in_body(body)
1133 // Consistency check our TypeckResults instance can hold all ItemLocalIds
1134 // it will need to hold.
1135 assert_eq!(typeck_results.hir_owner, id.owner);
1140 fn check_abi(tcx: TyCtxt<'_>, span: Span, abi: Abi) {
1141 if !tcx.sess.target.target.is_abi_supported(abi) {
1146 "The ABI `{}` is not supported for the current target",
1153 struct GatherLocalsVisitor<'a, 'tcx> {
1154 fcx: &'a FnCtxt<'a, 'tcx>,
1155 parent_id: hir::HirId,
1158 impl<'a, 'tcx> GatherLocalsVisitor<'a, 'tcx> {
1159 fn assign(&mut self, span: Span, nid: hir::HirId, ty_opt: Option<LocalTy<'tcx>>) -> Ty<'tcx> {
1162 // Infer the variable's type.
1163 let var_ty = self.fcx.next_ty_var(TypeVariableOrigin {
1164 kind: TypeVariableOriginKind::TypeInference,
1170 .insert(nid, LocalTy { decl_ty: var_ty, revealed_ty: var_ty });
1174 // Take type that the user specified.
1175 self.fcx.locals.borrow_mut().insert(nid, typ);
1182 impl<'a, 'tcx> Visitor<'tcx> for GatherLocalsVisitor<'a, 'tcx> {
1183 type Map = intravisit::ErasedMap<'tcx>;
1185 fn nested_visit_map(&mut self) -> NestedVisitorMap<Self::Map> {
1186 NestedVisitorMap::None
1189 // Add explicitly-declared locals.
1190 fn visit_local(&mut self, local: &'tcx hir::Local<'tcx>) {
1191 let local_ty = match local.ty {
1193 let o_ty = self.fcx.to_ty(&ty);
1195 let revealed_ty = if self.fcx.tcx.features().impl_trait_in_bindings {
1196 self.fcx.instantiate_opaque_types_from_value(self.parent_id, &o_ty, ty.span)
1205 .canonicalize_user_type_annotation(&UserType::Ty(revealed_ty));
1207 "visit_local: ty.hir_id={:?} o_ty={:?} revealed_ty={:?} c_ty={:?}",
1208 ty.hir_id, o_ty, revealed_ty, c_ty
1213 .user_provided_types_mut()
1214 .insert(ty.hir_id, c_ty);
1216 Some(LocalTy { decl_ty: o_ty, revealed_ty })
1220 self.assign(local.span, local.hir_id, local_ty);
1223 "local variable {:?} is assigned type {}",
1225 self.fcx.ty_to_string(&*self.fcx.locals.borrow().get(&local.hir_id).unwrap().decl_ty)
1227 intravisit::walk_local(self, local);
1230 // Add pattern bindings.
1231 fn visit_pat(&mut self, p: &'tcx hir::Pat<'tcx>) {
1232 if let PatKind::Binding(_, _, ident, _) = p.kind {
1233 let var_ty = self.assign(p.span, p.hir_id, None);
1235 if !self.fcx.tcx.features().unsized_locals {
1236 self.fcx.require_type_is_sized(var_ty, p.span, traits::VariableType(p.hir_id));
1240 "pattern binding {} is assigned to {} with type {:?}",
1242 self.fcx.ty_to_string(&*self.fcx.locals.borrow().get(&p.hir_id).unwrap().decl_ty),
1246 intravisit::walk_pat(self, p);
1249 // Don't descend into the bodies of nested closures.
1252 _: intravisit::FnKind<'tcx>,
1253 _: &'tcx hir::FnDecl<'tcx>,
1261 /// When `check_fn` is invoked on a generator (i.e., a body that
1262 /// includes yield), it returns back some information about the yield
1264 struct GeneratorTypes<'tcx> {
1265 /// Type of generator argument / values returned by `yield`.
1266 resume_ty: Ty<'tcx>,
1268 /// Type of value that is yielded.
1271 /// Types that are captured (see `GeneratorInterior` for more).
1274 /// Indicates if the generator is movable or static (immovable).
1275 movability: hir::Movability,
1278 /// Helper used for fns and closures. Does the grungy work of checking a function
1279 /// body and returns the function context used for that purpose, since in the case of a fn item
1280 /// there is still a bit more to do.
1283 /// * inherited: other fields inherited from the enclosing fn (if any)
1284 fn check_fn<'a, 'tcx>(
1285 inherited: &'a Inherited<'a, 'tcx>,
1286 param_env: ty::ParamEnv<'tcx>,
1287 fn_sig: ty::FnSig<'tcx>,
1288 decl: &'tcx hir::FnDecl<'tcx>,
1290 body: &'tcx hir::Body<'tcx>,
1291 can_be_generator: Option<hir::Movability>,
1292 ) -> (FnCtxt<'a, 'tcx>, Option<GeneratorTypes<'tcx>>) {
1293 let mut fn_sig = fn_sig;
1295 debug!("check_fn(sig={:?}, fn_id={}, param_env={:?})", fn_sig, fn_id, param_env);
1297 // Create the function context. This is either derived from scratch or,
1298 // in the case of closures, based on the outer context.
1299 let mut fcx = FnCtxt::new(inherited, param_env, body.value.hir_id);
1300 *fcx.ps.borrow_mut() = UnsafetyState::function(fn_sig.unsafety, fn_id);
1303 let sess = tcx.sess;
1304 let hir = tcx.hir();
1306 let declared_ret_ty = fn_sig.output();
1307 let revealed_ret_ty =
1308 fcx.instantiate_opaque_types_from_value(fn_id, &declared_ret_ty, decl.output.span());
1309 debug!("check_fn: declared_ret_ty: {}, revealed_ret_ty: {}", declared_ret_ty, revealed_ret_ty);
1310 fcx.ret_coercion = Some(RefCell::new(CoerceMany::new(revealed_ret_ty)));
1311 fn_sig = tcx.mk_fn_sig(
1312 fn_sig.inputs().iter().cloned(),
1319 let span = body.value.span;
1321 fn_maybe_err(tcx, span, fn_sig.abi);
1323 if body.generator_kind.is_some() && can_be_generator.is_some() {
1325 .next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::TypeInference, span });
1326 fcx.require_type_is_sized(yield_ty, span, traits::SizedYieldType);
1328 // Resume type defaults to `()` if the generator has no argument.
1329 let resume_ty = fn_sig.inputs().get(0).copied().unwrap_or_else(|| tcx.mk_unit());
1331 fcx.resume_yield_tys = Some((resume_ty, yield_ty));
1334 let outer_def_id = tcx.closure_base_def_id(hir.local_def_id(fn_id).to_def_id()).expect_local();
1335 let outer_hir_id = hir.local_def_id_to_hir_id(outer_def_id);
1336 GatherLocalsVisitor { fcx: &fcx, parent_id: outer_hir_id }.visit_body(body);
1338 // C-variadic fns also have a `VaList` input that's not listed in `fn_sig`
1339 // (as it's created inside the body itself, not passed in from outside).
1340 let maybe_va_list = if fn_sig.c_variadic {
1341 let span = body.params.last().unwrap().span;
1342 let va_list_did = tcx.require_lang_item(VaListTypeLangItem, Some(span));
1343 let region = fcx.next_region_var(RegionVariableOrigin::MiscVariable(span));
1345 Some(tcx.type_of(va_list_did).subst(tcx, &[region.into()]))
1350 // Add formal parameters.
1351 let inputs_hir = hir.fn_decl_by_hir_id(fn_id).map(|decl| &decl.inputs);
1352 let inputs_fn = fn_sig.inputs().iter().copied();
1353 for (idx, (param_ty, param)) in inputs_fn.chain(maybe_va_list).zip(body.params).enumerate() {
1354 // Check the pattern.
1355 let ty_span = try { inputs_hir?.get(idx)?.span };
1356 fcx.check_pat_top(¶m.pat, param_ty, ty_span, false);
1358 // Check that argument is Sized.
1359 // The check for a non-trivial pattern is a hack to avoid duplicate warnings
1360 // for simple cases like `fn foo(x: Trait)`,
1361 // where we would error once on the parameter as a whole, and once on the binding `x`.
1362 if param.pat.simple_ident().is_none() && !tcx.features().unsized_locals {
1363 fcx.require_type_is_sized(param_ty, param.pat.span, traits::SizedArgumentType(ty_span));
1366 fcx.write_ty(param.hir_id, param_ty);
1369 inherited.typeck_results.borrow_mut().liberated_fn_sigs_mut().insert(fn_id, fn_sig);
1371 if let ty::Dynamic(..) = declared_ret_ty.kind {
1372 // FIXME: We need to verify that the return type is `Sized` after the return expression has
1373 // been evaluated so that we have types available for all the nodes being returned, but that
1374 // requires the coerced evaluated type to be stored. Moving `check_return_expr` before this
1375 // causes unsized errors caused by the `declared_ret_ty` to point at the return expression,
1376 // while keeping the current ordering we will ignore the tail expression's type because we
1377 // don't know it yet. We can't do `check_expr_kind` while keeping `check_return_expr`
1378 // because we will trigger "unreachable expression" lints unconditionally.
1379 // Because of all of this, we perform a crude check to know whether the simplest `!Sized`
1380 // case that a newcomer might make, returning a bare trait, and in that case we populate
1381 // the tail expression's type so that the suggestion will be correct, but ignore all other
1383 fcx.check_expr(&body.value);
1384 fcx.require_type_is_sized(declared_ret_ty, decl.output.span(), traits::SizedReturnType);
1385 tcx.sess.delay_span_bug(decl.output.span(), "`!Sized` return type");
1387 fcx.require_type_is_sized(declared_ret_ty, decl.output.span(), traits::SizedReturnType);
1388 fcx.check_return_expr(&body.value);
1391 // We insert the deferred_generator_interiors entry after visiting the body.
1392 // This ensures that all nested generators appear before the entry of this generator.
1393 // resolve_generator_interiors relies on this property.
1394 let gen_ty = if let (Some(_), Some(gen_kind)) = (can_be_generator, body.generator_kind) {
1396 .next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::MiscVariable, span });
1397 fcx.deferred_generator_interiors.borrow_mut().push((body.id(), interior, gen_kind));
1399 let (resume_ty, yield_ty) = fcx.resume_yield_tys.unwrap();
1400 Some(GeneratorTypes {
1404 movability: can_be_generator.unwrap(),
1410 // Finalize the return check by taking the LUB of the return types
1411 // we saw and assigning it to the expected return type. This isn't
1412 // really expected to fail, since the coercions would have failed
1413 // earlier when trying to find a LUB.
1415 // However, the behavior around `!` is sort of complex. In the
1416 // event that the `actual_return_ty` comes back as `!`, that
1417 // indicates that the fn either does not return or "returns" only
1418 // values of type `!`. In this case, if there is an expected
1419 // return type that is *not* `!`, that should be ok. But if the
1420 // return type is being inferred, we want to "fallback" to `!`:
1422 // let x = move || panic!();
1424 // To allow for that, I am creating a type variable with diverging
1425 // fallback. This was deemed ever so slightly better than unifying
1426 // the return value with `!` because it allows for the caller to
1427 // make more assumptions about the return type (e.g., they could do
1429 // let y: Option<u32> = Some(x());
1431 // which would then cause this return type to become `u32`, not
1433 let coercion = fcx.ret_coercion.take().unwrap().into_inner();
1434 let mut actual_return_ty = coercion.complete(&fcx);
1435 if actual_return_ty.is_never() {
1436 actual_return_ty = fcx.next_diverging_ty_var(TypeVariableOrigin {
1437 kind: TypeVariableOriginKind::DivergingFn,
1441 fcx.demand_suptype(span, revealed_ret_ty, actual_return_ty);
1443 // Check that the main return type implements the termination trait.
1444 if let Some(term_id) = tcx.lang_items().termination() {
1445 if let Some((def_id, EntryFnType::Main)) = tcx.entry_fn(LOCAL_CRATE) {
1446 let main_id = hir.local_def_id_to_hir_id(def_id);
1447 if main_id == fn_id {
1448 let substs = tcx.mk_substs_trait(declared_ret_ty, &[]);
1449 let trait_ref = ty::TraitRef::new(term_id, substs);
1450 let return_ty_span = decl.output.span();
1451 let cause = traits::ObligationCause::new(
1454 ObligationCauseCode::MainFunctionType,
1457 inherited.register_predicate(traits::Obligation::new(
1460 trait_ref.without_const().to_predicate(tcx),
1466 // Check that a function marked as `#[panic_handler]` has signature `fn(&PanicInfo) -> !`
1467 if let Some(panic_impl_did) = tcx.lang_items().panic_impl() {
1468 if panic_impl_did == hir.local_def_id(fn_id).to_def_id() {
1469 if let Some(panic_info_did) = tcx.lang_items().panic_info() {
1470 if declared_ret_ty.kind != ty::Never {
1471 sess.span_err(decl.output.span(), "return type should be `!`");
1474 let inputs = fn_sig.inputs();
1475 let span = hir.span(fn_id);
1476 if inputs.len() == 1 {
1477 let arg_is_panic_info = match inputs[0].kind {
1478 ty::Ref(region, ty, mutbl) => match ty.kind {
1479 ty::Adt(ref adt, _) => {
1480 adt.did == panic_info_did
1481 && mutbl == hir::Mutability::Not
1482 && *region != RegionKind::ReStatic
1489 if !arg_is_panic_info {
1490 sess.span_err(decl.inputs[0].span, "argument should be `&PanicInfo`");
1493 if let Node::Item(item) = hir.get(fn_id) {
1494 if let ItemKind::Fn(_, ref generics, _) = item.kind {
1495 if !generics.params.is_empty() {
1496 sess.span_err(span, "should have no type parameters");
1501 let span = sess.source_map().guess_head_span(span);
1502 sess.span_err(span, "function should have one argument");
1505 sess.err("language item required, but not found: `panic_info`");
1510 // Check that a function marked as `#[alloc_error_handler]` has signature `fn(Layout) -> !`
1511 if let Some(alloc_error_handler_did) = tcx.lang_items().oom() {
1512 if alloc_error_handler_did == hir.local_def_id(fn_id).to_def_id() {
1513 if let Some(alloc_layout_did) = tcx.lang_items().alloc_layout() {
1514 if declared_ret_ty.kind != ty::Never {
1515 sess.span_err(decl.output.span(), "return type should be `!`");
1518 let inputs = fn_sig.inputs();
1519 let span = hir.span(fn_id);
1520 if inputs.len() == 1 {
1521 let arg_is_alloc_layout = match inputs[0].kind {
1522 ty::Adt(ref adt, _) => adt.did == alloc_layout_did,
1526 if !arg_is_alloc_layout {
1527 sess.span_err(decl.inputs[0].span, "argument should be `Layout`");
1530 if let Node::Item(item) = hir.get(fn_id) {
1531 if let ItemKind::Fn(_, ref generics, _) = item.kind {
1532 if !generics.params.is_empty() {
1535 "`#[alloc_error_handler]` function should have no type \
1542 let span = sess.source_map().guess_head_span(span);
1543 sess.span_err(span, "function should have one argument");
1546 sess.err("language item required, but not found: `alloc_layout`");
1554 fn check_struct(tcx: TyCtxt<'_>, id: hir::HirId, span: Span) {
1555 let def_id = tcx.hir().local_def_id(id);
1556 let def = tcx.adt_def(def_id);
1557 def.destructor(tcx); // force the destructor to be evaluated
1558 check_representable(tcx, span, def_id);
1560 if def.repr.simd() {
1561 check_simd(tcx, span, def_id);
1564 check_transparent(tcx, span, def);
1565 check_packed(tcx, span, def);
1568 fn check_union(tcx: TyCtxt<'_>, id: hir::HirId, span: Span) {
1569 let def_id = tcx.hir().local_def_id(id);
1570 let def = tcx.adt_def(def_id);
1571 def.destructor(tcx); // force the destructor to be evaluated
1572 check_representable(tcx, span, def_id);
1573 check_transparent(tcx, span, def);
1574 check_union_fields(tcx, span, def_id);
1575 check_packed(tcx, span, def);
1578 /// When the `#![feature(untagged_unions)]` gate is active,
1579 /// check that the fields of the `union` does not contain fields that need dropping.
1580 fn check_union_fields(tcx: TyCtxt<'_>, span: Span, item_def_id: LocalDefId) -> bool {
1581 let item_type = tcx.type_of(item_def_id);
1582 if let ty::Adt(def, substs) = item_type.kind {
1583 assert!(def.is_union());
1584 let fields = &def.non_enum_variant().fields;
1585 let param_env = tcx.param_env(item_def_id);
1586 for field in fields {
1587 let field_ty = field.ty(tcx, substs);
1588 // We are currently checking the type this field came from, so it must be local.
1589 let field_span = tcx.hir().span_if_local(field.did).unwrap();
1590 if field_ty.needs_drop(tcx, param_env) {
1595 "unions may not contain fields that need dropping"
1597 .span_note(field_span, "`std::mem::ManuallyDrop` can be used to wrap the type")
1603 span_bug!(span, "unions must be ty::Adt, but got {:?}", item_type.kind);
1608 /// Checks that an opaque type does not contain cycles and does not use `Self` or `T::Foo`
1609 /// projections that would result in "inheriting lifetimes".
1610 fn check_opaque<'tcx>(
1613 substs: SubstsRef<'tcx>,
1615 origin: &hir::OpaqueTyOrigin,
1617 check_opaque_for_inheriting_lifetimes(tcx, def_id, span);
1618 check_opaque_for_cycles(tcx, def_id, substs, span, origin);
1621 /// Checks that an opaque type does not use `Self` or `T::Foo` projections that would result
1622 /// in "inheriting lifetimes".
1623 fn check_opaque_for_inheriting_lifetimes(tcx: TyCtxt<'tcx>, def_id: LocalDefId, span: Span) {
1624 let item = tcx.hir().expect_item(tcx.hir().local_def_id_to_hir_id(def_id));
1626 "check_opaque_for_inheriting_lifetimes: def_id={:?} span={:?} item={:?}",
1631 struct ProhibitOpaqueVisitor<'tcx> {
1632 opaque_identity_ty: Ty<'tcx>,
1633 generics: &'tcx ty::Generics,
1634 ty: Option<Ty<'tcx>>,
1637 impl<'tcx> ty::fold::TypeVisitor<'tcx> for ProhibitOpaqueVisitor<'tcx> {
1638 fn visit_ty(&mut self, t: Ty<'tcx>) -> bool {
1639 debug!("check_opaque_for_inheriting_lifetimes: (visit_ty) t={:?}", t);
1640 if t != self.opaque_identity_ty && t.super_visit_with(self) {
1647 fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool {
1648 debug!("check_opaque_for_inheriting_lifetimes: (visit_region) r={:?}", r);
1649 if let RegionKind::ReEarlyBound(ty::EarlyBoundRegion { index, .. }) = r {
1650 return *index < self.generics.parent_count as u32;
1653 r.super_visit_with(self)
1656 fn visit_const(&mut self, c: &'tcx ty::Const<'tcx>) -> bool {
1657 if let ty::ConstKind::Unevaluated(..) = c.val {
1658 // FIXME(#72219) We currenctly don't detect lifetimes within substs
1659 // which would violate this check. Even though the particular substitution is not used
1660 // within the const, this should still be fixed.
1663 c.super_visit_with(self)
1667 if let ItemKind::OpaqueTy(hir::OpaqueTy {
1668 origin: hir::OpaqueTyOrigin::AsyncFn | hir::OpaqueTyOrigin::FnReturn,
1672 let mut visitor = ProhibitOpaqueVisitor {
1673 opaque_identity_ty: tcx.mk_opaque(
1675 InternalSubsts::identity_for_item(tcx, def_id.to_def_id()),
1677 generics: tcx.generics_of(def_id),
1680 let prohibit_opaque = tcx
1681 .predicates_of(def_id)
1684 .any(|(predicate, _)| predicate.visit_with(&mut visitor));
1686 "check_opaque_for_inheriting_lifetimes: prohibit_opaque={:?}, visitor={:?}",
1687 prohibit_opaque, visitor
1690 if prohibit_opaque {
1691 let is_async = match item.kind {
1692 ItemKind::OpaqueTy(hir::OpaqueTy { origin, .. }) => match origin {
1693 hir::OpaqueTyOrigin::AsyncFn => true,
1696 _ => unreachable!(),
1699 let mut err = struct_span_err!(
1703 "`{}` return type cannot contain a projection or `Self` that references lifetimes from \
1705 if is_async { "async fn" } else { "impl Trait" },
1708 if let Ok(snippet) = tcx.sess.source_map().span_to_snippet(span) {
1709 if snippet == "Self" {
1710 if let Some(ty) = visitor.ty {
1711 err.span_suggestion(
1713 "consider spelling out the type instead",
1714 format!("{:?}", ty),
1715 Applicability::MaybeIncorrect,
1725 /// Given a `DefId` for an opaque type in return position, find its parent item's return
1727 fn get_owner_return_paths(
1730 ) -> Option<(hir::HirId, ReturnsVisitor<'tcx>)> {
1731 let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
1732 let id = tcx.hir().get_parent_item(hir_id);
1736 .and_then(|(hir_id, node)| node.body_id().map(|b| (hir_id, b)))
1737 .map(|(hir_id, body_id)| {
1738 let body = tcx.hir().body(body_id);
1739 let mut visitor = ReturnsVisitor::default();
1740 visitor.visit_body(body);
1745 /// Emit an error for recursive opaque types.
1747 /// If this is a return `impl Trait`, find the item's return expressions and point at them. For
1748 /// direct recursion this is enough, but for indirect recursion also point at the last intermediary
1751 /// If all the return expressions evaluate to `!`, then we explain that the error will go away
1752 /// after changing it. This can happen when a user uses `panic!()` or similar as a placeholder.
1753 fn opaque_type_cycle_error(tcx: TyCtxt<'tcx>, def_id: LocalDefId, span: Span) {
1754 let mut err = struct_span_err!(tcx.sess, span, E0720, "cannot resolve opaque type");
1756 let mut label = false;
1757 if let Some((hir_id, visitor)) = get_owner_return_paths(tcx, def_id) {
1758 let typeck_results = tcx.typeck(tcx.hir().local_def_id(hir_id));
1762 .filter_map(|expr| typeck_results.node_type_opt(expr.hir_id))
1763 .all(|ty| matches!(ty.kind, ty::Never))
1768 .filter(|expr| typeck_results.node_type_opt(expr.hir_id).is_some())
1769 .map(|expr| expr.span)
1770 .collect::<Vec<Span>>();
1771 let span_len = spans.len();
1773 err.span_label(spans[0], "this returned value is of `!` type");
1775 let mut multispan: MultiSpan = spans.clone().into();
1778 .push_span_label(span, "this returned value is of `!` type".to_string());
1780 err.span_note(multispan, "these returned values have a concrete \"never\" type");
1782 err.help("this error will resolve once the item's body returns a concrete type");
1784 let mut seen = FxHashSet::default();
1786 err.span_label(span, "recursive opaque type");
1788 for (sp, ty) in visitor
1791 .filter_map(|e| typeck_results.node_type_opt(e.hir_id).map(|t| (e.span, t)))
1792 .filter(|(_, ty)| !matches!(ty.kind, ty::Never))
1794 struct VisitTypes(Vec<DefId>);
1795 impl<'tcx> ty::fold::TypeVisitor<'tcx> for VisitTypes {
1796 fn visit_ty(&mut self, t: Ty<'tcx>) -> bool {
1798 ty::Opaque(def, _) => {
1802 _ => t.super_visit_with(self),
1806 let mut visitor = VisitTypes(vec![]);
1807 ty.visit_with(&mut visitor);
1808 for def_id in visitor.0 {
1809 let ty_span = tcx.def_span(def_id);
1810 if !seen.contains(&ty_span) {
1811 err.span_label(ty_span, &format!("returning this opaque type `{}`", ty));
1812 seen.insert(ty_span);
1814 err.span_label(sp, &format!("returning here with type `{}`", ty));
1820 err.span_label(span, "cannot resolve opaque type");
1825 /// Emit an error for recursive opaque types in a `let` binding.
1826 fn binding_opaque_type_cycle_error(
1830 partially_expanded_type: Ty<'tcx>,
1832 let mut err = struct_span_err!(tcx.sess, span, E0720, "cannot resolve opaque type");
1833 err.span_label(span, "cannot resolve opaque type");
1834 // Find the the owner that declared this `impl Trait` type.
1835 let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
1836 let mut prev_hir_id = hir_id;
1837 let mut hir_id = tcx.hir().get_parent_node(hir_id);
1838 while let Some(node) = tcx.hir().find(hir_id) {
1840 hir::Node::Local(hir::Local {
1844 source: hir::LocalSource::Normal,
1847 err.span_label(pat.span, "this binding might not have a concrete type");
1848 err.span_suggestion_verbose(
1849 ty.span.shrink_to_hi(),
1850 "set the binding to a value for a concrete type to be resolved",
1851 " = /* value */".to_string(),
1852 Applicability::HasPlaceholders,
1855 hir::Node::Local(hir::Local {
1857 source: hir::LocalSource::Normal,
1860 let hir_id = tcx.hir().local_def_id_to_hir_id(def_id);
1861 let typeck_results =
1862 tcx.typeck(tcx.hir().local_def_id(tcx.hir().get_parent_item(hir_id)));
1863 if let Some(ty) = typeck_results.node_type_opt(expr.hir_id) {
1867 "this is of type `{}`, which doesn't constrain \
1868 `{}` enough to arrive to a concrete type",
1869 ty, partially_expanded_type
1876 if prev_hir_id == hir_id {
1879 prev_hir_id = hir_id;
1880 hir_id = tcx.hir().get_parent_node(hir_id);
1885 fn async_opaque_type_cycle_error(tcx: TyCtxt<'tcx>, span: Span) {
1886 struct_span_err!(tcx.sess, span, E0733, "recursion in an `async fn` requires boxing")
1887 .span_label(span, "recursive `async fn`")
1888 .note("a recursive `async fn` must be rewritten to return a boxed `dyn Future`")
1892 /// Checks that an opaque type does not contain cycles.
1893 fn check_opaque_for_cycles<'tcx>(
1896 substs: SubstsRef<'tcx>,
1898 origin: &hir::OpaqueTyOrigin,
1900 if let Err(partially_expanded_type) = tcx.try_expand_impl_trait_type(def_id.to_def_id(), substs)
1903 hir::OpaqueTyOrigin::AsyncFn => async_opaque_type_cycle_error(tcx, span),
1904 hir::OpaqueTyOrigin::Binding => {
1905 binding_opaque_type_cycle_error(tcx, def_id, span, partially_expanded_type)
1907 _ => opaque_type_cycle_error(tcx, def_id, span),
1912 // Forbid defining intrinsics in Rust code,
1913 // as they must always be defined by the compiler.
1914 fn fn_maybe_err(tcx: TyCtxt<'_>, sp: Span, abi: Abi) {
1915 if let Abi::RustIntrinsic | Abi::PlatformIntrinsic = abi {
1916 tcx.sess.span_err(sp, "intrinsic must be in `extern \"rust-intrinsic\" { ... }` block");
1920 pub fn check_item_type<'tcx>(tcx: TyCtxt<'tcx>, it: &'tcx hir::Item<'tcx>) {
1922 "check_item_type(it.hir_id={}, it.name={})",
1924 tcx.def_path_str(tcx.hir().local_def_id(it.hir_id).to_def_id())
1926 let _indenter = indenter();
1928 // Consts can play a role in type-checking, so they are included here.
1929 hir::ItemKind::Static(..) => {
1930 let def_id = tcx.hir().local_def_id(it.hir_id);
1931 tcx.ensure().typeck(def_id);
1932 maybe_check_static_with_link_section(tcx, def_id, it.span);
1934 hir::ItemKind::Const(..) => {
1935 tcx.ensure().typeck(tcx.hir().local_def_id(it.hir_id));
1937 hir::ItemKind::Enum(ref enum_definition, _) => {
1938 check_enum(tcx, it.span, &enum_definition.variants, it.hir_id);
1940 hir::ItemKind::Fn(..) => {} // entirely within check_item_body
1941 hir::ItemKind::Impl { ref items, .. } => {
1942 debug!("ItemKind::Impl {} with id {}", it.ident, it.hir_id);
1943 let impl_def_id = tcx.hir().local_def_id(it.hir_id);
1944 if let Some(impl_trait_ref) = tcx.impl_trait_ref(impl_def_id) {
1945 check_impl_items_against_trait(tcx, it.span, impl_def_id, impl_trait_ref, items);
1946 let trait_def_id = impl_trait_ref.def_id;
1947 check_on_unimplemented(tcx, trait_def_id, it);
1950 hir::ItemKind::Trait(_, _, _, _, ref items) => {
1951 let def_id = tcx.hir().local_def_id(it.hir_id);
1952 check_on_unimplemented(tcx, def_id.to_def_id(), it);
1954 for item in items.iter() {
1955 let item = tcx.hir().trait_item(item.id);
1956 if let hir::TraitItemKind::Fn(sig, _) = &item.kind {
1957 let abi = sig.header.abi;
1958 fn_maybe_err(tcx, item.ident.span, abi);
1962 hir::ItemKind::Struct(..) => {
1963 check_struct(tcx, it.hir_id, it.span);
1965 hir::ItemKind::Union(..) => {
1966 check_union(tcx, it.hir_id, it.span);
1968 hir::ItemKind::OpaqueTy(hir::OpaqueTy { origin, .. }) => {
1969 // HACK(jynelson): trying to infer the type of `impl trait` breaks documenting
1970 // `async-std` (and `pub async fn` in general).
1971 // Since rustdoc doesn't care about the concrete type behind `impl Trait`, just don't look at it!
1972 // See https://github.com/rust-lang/rust/issues/75100
1973 if !tcx.sess.opts.actually_rustdoc {
1974 let def_id = tcx.hir().local_def_id(it.hir_id);
1976 let substs = InternalSubsts::identity_for_item(tcx, def_id.to_def_id());
1977 check_opaque(tcx, def_id, substs, it.span, &origin);
1980 hir::ItemKind::TyAlias(..) => {
1981 let def_id = tcx.hir().local_def_id(it.hir_id);
1982 let pty_ty = tcx.type_of(def_id);
1983 let generics = tcx.generics_of(def_id);
1984 check_type_params_are_used(tcx, &generics, pty_ty);
1986 hir::ItemKind::ForeignMod(ref m) => {
1987 check_abi(tcx, it.span, m.abi);
1989 if m.abi == Abi::RustIntrinsic {
1990 for item in m.items {
1991 intrinsic::check_intrinsic_type(tcx, item);
1993 } else if m.abi == Abi::PlatformIntrinsic {
1994 for item in m.items {
1995 intrinsic::check_platform_intrinsic_type(tcx, item);
1998 for item in m.items {
1999 let generics = tcx.generics_of(tcx.hir().local_def_id(item.hir_id));
2000 let own_counts = generics.own_counts();
2001 if generics.params.len() - own_counts.lifetimes != 0 {
2002 let (kinds, kinds_pl, egs) = match (own_counts.types, own_counts.consts) {
2003 (_, 0) => ("type", "types", Some("u32")),
2004 // We don't specify an example value, because we can't generate
2005 // a valid value for any type.
2006 (0, _) => ("const", "consts", None),
2007 _ => ("type or const", "types or consts", None),
2013 "foreign items may not have {} parameters",
2016 .span_label(item.span, &format!("can't have {} parameters", kinds))
2018 // FIXME: once we start storing spans for type arguments, turn this
2019 // into a suggestion.
2021 "replace the {} parameters with concrete {}{}",
2024 egs.map(|egs| format!(" like `{}`", egs)).unwrap_or_default(),
2030 if let hir::ForeignItemKind::Fn(ref fn_decl, _, _) = item.kind {
2031 require_c_abi_if_c_variadic(tcx, fn_decl, m.abi, item.span);
2036 _ => { /* nothing to do */ }
2040 fn maybe_check_static_with_link_section(tcx: TyCtxt<'_>, id: LocalDefId, span: Span) {
2041 // Only restricted on wasm32 target for now
2042 if !tcx.sess.opts.target_triple.triple().starts_with("wasm32") {
2046 // If `#[link_section]` is missing, then nothing to verify
2047 let attrs = tcx.codegen_fn_attrs(id);
2048 if attrs.link_section.is_none() {
2052 // For the wasm32 target statics with `#[link_section]` are placed into custom
2053 // sections of the final output file, but this isn't link custom sections of
2054 // other executable formats. Namely we can only embed a list of bytes,
2055 // nothing with pointers to anything else or relocations. If any relocation
2056 // show up, reject them here.
2057 // `#[link_section]` may contain arbitrary, or even undefined bytes, but it is
2058 // the consumer's responsibility to ensure all bytes that have been read
2059 // have defined values.
2060 match tcx.const_eval_poly(id.to_def_id()) {
2061 Ok(ConstValue::ByRef { alloc, .. }) => {
2062 if alloc.relocations().len() != 0 {
2063 let msg = "statics with a custom `#[link_section]` must be a \
2064 simple list of bytes on the wasm target with no \
2065 extra levels of indirection such as references";
2066 tcx.sess.span_err(span, msg);
2069 Ok(_) => bug!("Matching on non-ByRef static"),
2074 fn check_on_unimplemented(tcx: TyCtxt<'_>, trait_def_id: DefId, item: &hir::Item<'_>) {
2075 let item_def_id = tcx.hir().local_def_id(item.hir_id);
2076 // an error would be reported if this fails.
2077 let _ = traits::OnUnimplementedDirective::of_item(tcx, trait_def_id, item_def_id.to_def_id());
2080 fn report_forbidden_specialization(
2082 impl_item: &hir::ImplItem<'_>,
2085 let mut err = struct_span_err!(
2089 "`{}` specializes an item from a parent `impl`, but \
2090 that item is not marked `default`",
2093 err.span_label(impl_item.span, format!("cannot specialize default item `{}`", impl_item.ident));
2095 match tcx.span_of_impl(parent_impl) {
2097 err.span_label(span, "parent `impl` is here");
2099 "to specialize, `{}` in the parent `impl` must be marked `default`",
2104 err.note(&format!("parent implementation is in crate `{}`", cname));
2111 fn check_specialization_validity<'tcx>(
2113 trait_def: &ty::TraitDef,
2114 trait_item: &ty::AssocItem,
2116 impl_item: &hir::ImplItem<'_>,
2118 let kind = match impl_item.kind {
2119 hir::ImplItemKind::Const(..) => ty::AssocKind::Const,
2120 hir::ImplItemKind::Fn(..) => ty::AssocKind::Fn,
2121 hir::ImplItemKind::TyAlias(_) => ty::AssocKind::Type,
2124 let ancestors = match trait_def.ancestors(tcx, impl_id) {
2125 Ok(ancestors) => ancestors,
2128 let mut ancestor_impls = ancestors
2130 .filter_map(|parent| {
2131 if parent.is_from_trait() {
2134 Some((parent, parent.item(tcx, trait_item.ident, kind, trait_def.def_id)))
2139 if ancestor_impls.peek().is_none() {
2140 // No parent, nothing to specialize.
2144 let opt_result = ancestor_impls.find_map(|(parent_impl, parent_item)| {
2146 // Parent impl exists, and contains the parent item we're trying to specialize, but
2147 // doesn't mark it `default`.
2148 Some(parent_item) if traits::impl_item_is_final(tcx, &parent_item) => {
2149 Some(Err(parent_impl.def_id()))
2152 // Parent impl contains item and makes it specializable.
2153 Some(_) => Some(Ok(())),
2155 // Parent impl doesn't mention the item. This means it's inherited from the
2156 // grandparent. In that case, if parent is a `default impl`, inherited items use the
2157 // "defaultness" from the grandparent, else they are final.
2159 if tcx.impl_defaultness(parent_impl.def_id()).is_default() {
2162 Some(Err(parent_impl.def_id()))
2168 // If `opt_result` is `None`, we have only encountered `default impl`s that don't contain the
2169 // item. This is allowed, the item isn't actually getting specialized here.
2170 let result = opt_result.unwrap_or(Ok(()));
2172 if let Err(parent_impl) = result {
2173 report_forbidden_specialization(tcx, impl_item, parent_impl);
2177 fn check_impl_items_against_trait<'tcx>(
2179 full_impl_span: Span,
2180 impl_id: LocalDefId,
2181 impl_trait_ref: ty::TraitRef<'tcx>,
2182 impl_item_refs: &[hir::ImplItemRef<'_>],
2184 let impl_span = tcx.sess.source_map().guess_head_span(full_impl_span);
2186 // If the trait reference itself is erroneous (so the compilation is going
2187 // to fail), skip checking the items here -- the `impl_item` table in `tcx`
2188 // isn't populated for such impls.
2189 if impl_trait_ref.references_error() {
2193 // Negative impls are not expected to have any items
2194 match tcx.impl_polarity(impl_id) {
2195 ty::ImplPolarity::Reservation | ty::ImplPolarity::Positive => {}
2196 ty::ImplPolarity::Negative => {
2197 if let [first_item_ref, ..] = impl_item_refs {
2198 let first_item_span = tcx.hir().impl_item(first_item_ref.id).span;
2203 "negative impls cannot have any items"
2211 // Locate trait definition and items
2212 let trait_def = tcx.trait_def(impl_trait_ref.def_id);
2214 let impl_items = || impl_item_refs.iter().map(|iiref| tcx.hir().impl_item(iiref.id));
2216 // Check existing impl methods to see if they are both present in trait
2217 // and compatible with trait signature
2218 for impl_item in impl_items() {
2219 let namespace = impl_item.kind.namespace();
2220 let ty_impl_item = tcx.associated_item(tcx.hir().local_def_id(impl_item.hir_id));
2221 let ty_trait_item = tcx
2222 .associated_items(impl_trait_ref.def_id)
2223 .find_by_name_and_namespace(tcx, ty_impl_item.ident, namespace, impl_trait_ref.def_id)
2225 // Not compatible, but needed for the error message
2226 tcx.associated_items(impl_trait_ref.def_id)
2227 .filter_by_name(tcx, ty_impl_item.ident, impl_trait_ref.def_id)
2231 // Check that impl definition matches trait definition
2232 if let Some(ty_trait_item) = ty_trait_item {
2233 match impl_item.kind {
2234 hir::ImplItemKind::Const(..) => {
2235 // Find associated const definition.
2236 if ty_trait_item.kind == ty::AssocKind::Const {
2245 let mut err = struct_span_err!(
2249 "item `{}` is an associated const, \
2250 which doesn't match its trait `{}`",
2252 impl_trait_ref.print_only_trait_path()
2254 err.span_label(impl_item.span, "does not match trait");
2255 // We can only get the spans from local trait definition
2256 // Same for E0324 and E0325
2257 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
2258 err.span_label(trait_span, "item in trait");
2263 hir::ImplItemKind::Fn(..) => {
2264 let opt_trait_span = tcx.hir().span_if_local(ty_trait_item.def_id);
2265 if ty_trait_item.kind == ty::AssocKind::Fn {
2266 compare_impl_method(
2275 let mut err = struct_span_err!(
2279 "item `{}` is an associated method, \
2280 which doesn't match its trait `{}`",
2282 impl_trait_ref.print_only_trait_path()
2284 err.span_label(impl_item.span, "does not match trait");
2285 if let Some(trait_span) = opt_trait_span {
2286 err.span_label(trait_span, "item in trait");
2291 hir::ImplItemKind::TyAlias(_) => {
2292 let opt_trait_span = tcx.hir().span_if_local(ty_trait_item.def_id);
2293 if ty_trait_item.kind == ty::AssocKind::Type {
2303 let mut err = struct_span_err!(
2307 "item `{}` is an associated type, \
2308 which doesn't match its trait `{}`",
2310 impl_trait_ref.print_only_trait_path()
2312 err.span_label(impl_item.span, "does not match trait");
2313 if let Some(trait_span) = opt_trait_span {
2314 err.span_label(trait_span, "item in trait");
2321 check_specialization_validity(
2325 impl_id.to_def_id(),
2331 // Check for missing items from trait
2332 let mut missing_items = Vec::new();
2333 if let Ok(ancestors) = trait_def.ancestors(tcx, impl_id.to_def_id()) {
2334 for trait_item in tcx.associated_items(impl_trait_ref.def_id).in_definition_order() {
2335 let is_implemented = ancestors
2336 .leaf_def(tcx, trait_item.ident, trait_item.kind)
2337 .map(|node_item| !node_item.defining_node.is_from_trait())
2340 if !is_implemented && tcx.impl_defaultness(impl_id).is_final() {
2341 if !trait_item.defaultness.has_value() {
2342 missing_items.push(*trait_item);
2348 if !missing_items.is_empty() {
2349 missing_items_err(tcx, impl_span, &missing_items, full_impl_span);
2353 fn missing_items_err(
2356 missing_items: &[ty::AssocItem],
2357 full_impl_span: Span,
2359 let missing_items_msg = missing_items
2361 .map(|trait_item| trait_item.ident.to_string())
2362 .collect::<Vec<_>>()
2365 let mut err = struct_span_err!(
2369 "not all trait items implemented, missing: `{}`",
2372 err.span_label(impl_span, format!("missing `{}` in implementation", missing_items_msg));
2374 // `Span` before impl block closing brace.
2375 let hi = full_impl_span.hi() - BytePos(1);
2376 // Point at the place right before the closing brace of the relevant `impl` to suggest
2377 // adding the associated item at the end of its body.
2378 let sugg_sp = full_impl_span.with_lo(hi).with_hi(hi);
2379 // Obtain the level of indentation ending in `sugg_sp`.
2380 let indentation = tcx.sess.source_map().span_to_margin(sugg_sp).unwrap_or(0);
2381 // Make the whitespace that will make the suggestion have the right indentation.
2382 let padding: String = (0..indentation).map(|_| " ").collect();
2384 for trait_item in missing_items {
2385 let snippet = suggestion_signature(&trait_item, tcx);
2386 let code = format!("{}{}\n{}", padding, snippet, padding);
2387 let msg = format!("implement the missing item: `{}`", snippet);
2388 let appl = Applicability::HasPlaceholders;
2389 if let Some(span) = tcx.hir().span_if_local(trait_item.def_id) {
2390 err.span_label(span, format!("`{}` from trait", trait_item.ident));
2391 err.tool_only_span_suggestion(sugg_sp, &msg, code, appl);
2393 err.span_suggestion_hidden(sugg_sp, &msg, code, appl);
2399 /// Resugar `ty::GenericPredicates` in a way suitable to be used in structured suggestions.
2400 fn bounds_from_generic_predicates<'tcx>(
2402 predicates: ty::GenericPredicates<'tcx>,
2403 ) -> (String, String) {
2404 let mut types: FxHashMap<Ty<'tcx>, Vec<DefId>> = FxHashMap::default();
2405 let mut projections = vec![];
2406 for (predicate, _) in predicates.predicates {
2407 debug!("predicate {:?}", predicate);
2408 match predicate.skip_binders() {
2409 ty::PredicateAtom::Trait(trait_predicate, _) => {
2410 let entry = types.entry(trait_predicate.self_ty()).or_default();
2411 let def_id = trait_predicate.def_id();
2412 if Some(def_id) != tcx.lang_items().sized_trait() {
2413 // Type params are `Sized` by default, do not add that restriction to the list
2414 // if it is a positive requirement.
2415 entry.push(trait_predicate.def_id());
2418 ty::PredicateAtom::Projection(projection_pred) => {
2419 projections.push(ty::Binder::bind(projection_pred));
2424 let generics = if types.is_empty() {
2431 .filter_map(|t| match t.kind {
2432 ty::Param(_) => Some(t.to_string()),
2433 // Avoid suggesting the following:
2434 // fn foo<T, <T as Trait>::Bar>(_: T) where T: Trait, <T as Trait>::Bar: Other {}
2437 .collect::<Vec<_>>()
2441 let mut where_clauses = vec![];
2442 for (ty, bounds) in types {
2443 for bound in &bounds {
2444 where_clauses.push(format!("{}: {}", ty, tcx.def_path_str(*bound)));
2447 for projection in &projections {
2448 let p = projection.skip_binder();
2449 // FIXME: this is not currently supported syntax, we should be looking at the `types` and
2450 // insert the associated types where they correspond, but for now let's be "lazy" and
2451 // propose this instead of the following valid resugaring:
2452 // `T: Trait, Trait::Assoc = K` → `T: Trait<Assoc = K>`
2453 where_clauses.push(format!("{} = {}", tcx.def_path_str(p.projection_ty.item_def_id), p.ty));
2455 let where_clauses = if where_clauses.is_empty() {
2458 format!(" where {}", where_clauses.join(", "))
2460 (generics, where_clauses)
2463 /// Return placeholder code for the given function.
2464 fn fn_sig_suggestion<'tcx>(
2466 sig: ty::FnSig<'tcx>,
2468 predicates: ty::GenericPredicates<'tcx>,
2469 assoc: &ty::AssocItem,
2476 Some(match ty.kind {
2477 ty::Param(_) if assoc.fn_has_self_parameter && i == 0 => "self".to_string(),
2478 ty::Ref(reg, ref_ty, mutability) if i == 0 => {
2479 let reg = match &format!("{}", reg)[..] {
2480 "'_" | "" => String::new(),
2481 reg => format!("{} ", reg),
2483 if assoc.fn_has_self_parameter {
2485 ty::Param(param) if param.name == kw::SelfUpper => {
2486 format!("&{}{}self", reg, mutability.prefix_str())
2489 _ => format!("self: {}", ty),
2492 format!("_: {:?}", ty)
2496 if assoc.fn_has_self_parameter && i == 0 {
2497 format!("self: {:?}", ty)
2499 format!("_: {:?}", ty)
2504 .chain(std::iter::once(if sig.c_variadic { Some("...".to_string()) } else { None }))
2505 .filter_map(|arg| arg)
2506 .collect::<Vec<String>>()
2508 let output = sig.output();
2509 let output = if !output.is_unit() { format!(" -> {:?}", output) } else { String::new() };
2511 let unsafety = sig.unsafety.prefix_str();
2512 let (generics, where_clauses) = bounds_from_generic_predicates(tcx, predicates);
2514 // FIXME: this is not entirely correct, as the lifetimes from borrowed params will
2515 // not be present in the `fn` definition, not will we account for renamed
2516 // lifetimes between the `impl` and the `trait`, but this should be good enough to
2517 // fill in a significant portion of the missing code, and other subsequent
2518 // suggestions can help the user fix the code.
2520 "{}fn {}{}({}){}{} {{ todo!() }}",
2521 unsafety, ident, generics, args, output, where_clauses
2525 /// Return placeholder code for the given associated item.
2526 /// Similar to `ty::AssocItem::suggestion`, but appropriate for use as the code snippet of a
2527 /// structured suggestion.
2528 fn suggestion_signature(assoc: &ty::AssocItem, tcx: TyCtxt<'_>) -> String {
2530 ty::AssocKind::Fn => {
2531 // We skip the binder here because the binder would deanonymize all
2532 // late-bound regions, and we don't want method signatures to show up
2533 // `as for<'r> fn(&'r MyType)`. Pretty-printing handles late-bound
2534 // regions just fine, showing `fn(&MyType)`.
2537 tcx.fn_sig(assoc.def_id).skip_binder(),
2539 tcx.predicates_of(assoc.def_id),
2543 ty::AssocKind::Type => format!("type {} = Type;", assoc.ident),
2544 ty::AssocKind::Const => {
2545 let ty = tcx.type_of(assoc.def_id);
2546 let val = expr::ty_kind_suggestion(ty).unwrap_or("value");
2547 format!("const {}: {:?} = {};", assoc.ident, ty, val)
2552 /// Checks whether a type can be represented in memory. In particular, it
2553 /// identifies types that contain themselves without indirection through a
2554 /// pointer, which would mean their size is unbounded.
2555 fn check_representable(tcx: TyCtxt<'_>, sp: Span, item_def_id: LocalDefId) -> bool {
2556 let rty = tcx.type_of(item_def_id);
2558 // Check that it is possible to represent this type. This call identifies
2559 // (1) types that contain themselves and (2) types that contain a different
2560 // recursive type. It is only necessary to throw an error on those that
2561 // contain themselves. For case 2, there must be an inner type that will be
2562 // caught by case 1.
2563 match rty.is_representable(tcx, sp) {
2564 Representability::SelfRecursive(spans) => {
2565 recursive_type_with_infinite_size_error(tcx, item_def_id.to_def_id(), spans);
2568 Representability::Representable | Representability::ContainsRecursive => (),
2573 pub fn check_simd(tcx: TyCtxt<'_>, sp: Span, def_id: LocalDefId) {
2574 let t = tcx.type_of(def_id);
2575 if let ty::Adt(def, substs) = t.kind {
2576 if def.is_struct() {
2577 let fields = &def.non_enum_variant().fields;
2578 if fields.is_empty() {
2579 struct_span_err!(tcx.sess, sp, E0075, "SIMD vector cannot be empty").emit();
2582 let e = fields[0].ty(tcx, substs);
2583 if !fields.iter().all(|f| f.ty(tcx, substs) == e) {
2584 struct_span_err!(tcx.sess, sp, E0076, "SIMD vector should be homogeneous")
2585 .span_label(sp, "SIMD elements must have the same type")
2590 ty::Param(_) => { /* struct<T>(T, T, T, T) is ok */ }
2591 _ if e.is_machine() => { /* struct(u8, u8, u8, u8) is ok */ }
2597 "SIMD vector element type should be machine type"
2607 fn check_packed(tcx: TyCtxt<'_>, sp: Span, def: &ty::AdtDef) {
2608 let repr = def.repr;
2610 for attr in tcx.get_attrs(def.did).iter() {
2611 for r in attr::find_repr_attrs(&tcx.sess, attr) {
2612 if let attr::ReprPacked(pack) = r {
2613 if let Some(repr_pack) = repr.pack {
2614 if pack as u64 != repr_pack.bytes() {
2619 "type has conflicting packed representation hints"
2627 if repr.align.is_some() {
2632 "type has conflicting packed and align representation hints"
2636 if let Some(def_spans) = check_packed_inner(tcx, def.did, &mut vec![]) {
2637 let mut err = struct_span_err!(
2641 "packed type cannot transitively contain a `#[repr(align)]` type"
2645 tcx.def_span(def_spans[0].0),
2647 "`{}` has a `#[repr(align)]` attribute",
2648 tcx.item_name(def_spans[0].0)
2652 if def_spans.len() > 2 {
2653 let mut first = true;
2654 for (adt_def, span) in def_spans.iter().skip(1).rev() {
2655 let ident = tcx.item_name(*adt_def);
2660 "`{}` contains a field of type `{}`",
2661 tcx.type_of(def.did),
2665 format!("...which contains a field of type `{}`", ident)
2678 fn check_packed_inner(
2681 stack: &mut Vec<DefId>,
2682 ) -> Option<Vec<(DefId, Span)>> {
2683 if let ty::Adt(def, substs) = tcx.type_of(def_id).kind {
2684 if def.is_struct() || def.is_union() {
2685 if def.repr.align.is_some() {
2686 return Some(vec![(def.did, DUMMY_SP)]);
2690 for field in &def.non_enum_variant().fields {
2691 if let ty::Adt(def, _) = field.ty(tcx, substs).kind {
2692 if !stack.contains(&def.did) {
2693 if let Some(mut defs) = check_packed_inner(tcx, def.did, stack) {
2694 defs.push((def.did, field.ident.span));
2707 /// Emit an error when encountering more or less than one variant in a transparent enum.
2708 fn bad_variant_count<'tcx>(tcx: TyCtxt<'tcx>, adt: &'tcx ty::AdtDef, sp: Span, did: DefId) {
2709 let variant_spans: Vec<_> = adt
2712 .map(|variant| tcx.hir().span_if_local(variant.def_id).unwrap())
2714 let msg = format!("needs exactly one variant, but has {}", adt.variants.len(),);
2715 let mut err = struct_span_err!(tcx.sess, sp, E0731, "transparent enum {}", msg);
2716 err.span_label(sp, &msg);
2717 if let [start @ .., end] = &*variant_spans {
2718 for variant_span in start {
2719 err.span_label(*variant_span, "");
2721 err.span_label(*end, &format!("too many variants in `{}`", tcx.def_path_str(did)));
2726 /// Emit an error when encountering more or less than one non-zero-sized field in a transparent
2728 fn bad_non_zero_sized_fields<'tcx>(
2730 adt: &'tcx ty::AdtDef,
2732 field_spans: impl Iterator<Item = Span>,
2735 let msg = format!("needs exactly one non-zero-sized field, but has {}", field_count);
2736 let mut err = struct_span_err!(
2740 "{}transparent {} {}",
2741 if adt.is_enum() { "the variant of a " } else { "" },
2745 err.span_label(sp, &msg);
2746 for sp in field_spans {
2747 err.span_label(sp, "this field is non-zero-sized");
2752 fn check_transparent<'tcx>(tcx: TyCtxt<'tcx>, sp: Span, adt: &'tcx ty::AdtDef) {
2753 if !adt.repr.transparent() {
2756 let sp = tcx.sess.source_map().guess_head_span(sp);
2758 if adt.is_union() && !tcx.features().transparent_unions {
2760 &tcx.sess.parse_sess,
2761 sym::transparent_unions,
2763 "transparent unions are unstable",
2768 if adt.variants.len() != 1 {
2769 bad_variant_count(tcx, adt, sp, adt.did);
2770 if adt.variants.is_empty() {
2771 // Don't bother checking the fields. No variants (and thus no fields) exist.
2776 // For each field, figure out if it's known to be a ZST and align(1)
2777 let field_infos = adt.all_fields().map(|field| {
2778 let ty = field.ty(tcx, InternalSubsts::identity_for_item(tcx, field.did));
2779 let param_env = tcx.param_env(field.did);
2780 let layout = tcx.layout_of(param_env.and(ty));
2781 // We are currently checking the type this field came from, so it must be local
2782 let span = tcx.hir().span_if_local(field.did).unwrap();
2783 let zst = layout.map(|layout| layout.is_zst()).unwrap_or(false);
2784 let align1 = layout.map(|layout| layout.align.abi.bytes() == 1).unwrap_or(false);
2788 let non_zst_fields =
2789 field_infos.clone().filter_map(|(span, zst, _align1)| if !zst { Some(span) } else { None });
2790 let non_zst_count = non_zst_fields.clone().count();
2791 if non_zst_count != 1 {
2792 bad_non_zero_sized_fields(tcx, adt, non_zst_count, non_zst_fields, sp);
2794 for (span, zst, align1) in field_infos {
2800 "zero-sized field in transparent {} has alignment larger than 1",
2803 .span_label(span, "has alignment larger than 1")
2809 #[allow(trivial_numeric_casts)]
2810 pub fn check_enum<'tcx>(
2813 vs: &'tcx [hir::Variant<'tcx>],
2816 let def_id = tcx.hir().local_def_id(id);
2817 let def = tcx.adt_def(def_id);
2818 def.destructor(tcx); // force the destructor to be evaluated
2821 let attributes = tcx.get_attrs(def_id.to_def_id());
2822 if let Some(attr) = tcx.sess.find_by_name(&attributes, sym::repr) {
2827 "unsupported representation for zero-variant enum"
2829 .span_label(sp, "zero-variant enum")
2834 let repr_type_ty = def.repr.discr_type().to_ty(tcx);
2835 if repr_type_ty == tcx.types.i128 || repr_type_ty == tcx.types.u128 {
2836 if !tcx.features().repr128 {
2838 &tcx.sess.parse_sess,
2841 "repr with 128-bit type is unstable",
2848 if let Some(ref e) = v.disr_expr {
2849 tcx.ensure().typeck(tcx.hir().local_def_id(e.hir_id));
2853 if tcx.adt_def(def_id).repr.int.is_none() && tcx.features().arbitrary_enum_discriminant {
2854 let is_unit = |var: &hir::Variant<'_>| match var.data {
2855 hir::VariantData::Unit(..) => true,
2859 let has_disr = |var: &hir::Variant<'_>| var.disr_expr.is_some();
2860 let has_non_units = vs.iter().any(|var| !is_unit(var));
2861 let disr_units = vs.iter().any(|var| is_unit(&var) && has_disr(&var));
2862 let disr_non_unit = vs.iter().any(|var| !is_unit(&var) && has_disr(&var));
2864 if disr_non_unit || (disr_units && has_non_units) {
2866 struct_span_err!(tcx.sess, sp, E0732, "`#[repr(inttype)]` must be specified");
2871 let mut disr_vals: Vec<Discr<'tcx>> = Vec::with_capacity(vs.len());
2872 for ((_, discr), v) in def.discriminants(tcx).zip(vs) {
2873 // Check for duplicate discriminant values
2874 if let Some(i) = disr_vals.iter().position(|&x| x.val == discr.val) {
2875 let variant_did = def.variants[VariantIdx::new(i)].def_id;
2876 let variant_i_hir_id = tcx.hir().local_def_id_to_hir_id(variant_did.expect_local());
2877 let variant_i = tcx.hir().expect_variant(variant_i_hir_id);
2878 let i_span = match variant_i.disr_expr {
2879 Some(ref expr) => tcx.hir().span(expr.hir_id),
2880 None => tcx.hir().span(variant_i_hir_id),
2882 let span = match v.disr_expr {
2883 Some(ref expr) => tcx.hir().span(expr.hir_id),
2890 "discriminant value `{}` already exists",
2893 .span_label(i_span, format!("first use of `{}`", disr_vals[i]))
2894 .span_label(span, format!("enum already has `{}`", disr_vals[i]))
2897 disr_vals.push(discr);
2900 check_representable(tcx, sp, def_id);
2901 check_transparent(tcx, sp, def);
2904 fn report_unexpected_variant_res(tcx: TyCtxt<'_>, res: Res, span: Span) {
2909 "expected unit struct, unit variant or constant, found {}{}",
2911 tcx.sess.source_map().span_to_snippet(span).map_or(String::new(), |s| format!(" `{}`", s)),
2916 impl<'a, 'tcx> AstConv<'tcx> for FnCtxt<'a, 'tcx> {
2917 fn tcx<'b>(&'b self) -> TyCtxt<'tcx> {
2921 fn item_def_id(&self) -> Option<DefId> {
2925 fn default_constness_for_trait_bounds(&self) -> hir::Constness {
2926 // FIXME: refactor this into a method
2927 let node = self.tcx.hir().get(self.body_id);
2928 if let Some(fn_like) = FnLikeNode::from_node(node) {
2931 hir::Constness::NotConst
2935 fn get_type_parameter_bounds(&self, _: Span, def_id: DefId) -> ty::GenericPredicates<'tcx> {
2937 let hir_id = tcx.hir().local_def_id_to_hir_id(def_id.expect_local());
2938 let item_id = tcx.hir().ty_param_owner(hir_id);
2939 let item_def_id = tcx.hir().local_def_id(item_id);
2940 let generics = tcx.generics_of(item_def_id);
2941 let index = generics.param_def_id_to_index[&def_id];
2942 ty::GenericPredicates {
2944 predicates: tcx.arena.alloc_from_iter(
2945 self.param_env.caller_bounds().iter().filter_map(|predicate| {
2946 match predicate.skip_binders() {
2947 ty::PredicateAtom::Trait(data, _) if data.self_ty().is_param(index) => {
2948 // HACK(eddyb) should get the original `Span`.
2949 let span = tcx.def_span(def_id);
2950 Some((predicate, span))
2959 fn re_infer(&self, def: Option<&ty::GenericParamDef>, span: Span) -> Option<ty::Region<'tcx>> {
2961 Some(def) => infer::EarlyBoundRegion(span, def.name),
2962 None => infer::MiscVariable(span),
2964 Some(self.next_region_var(v))
2967 fn allow_ty_infer(&self) -> bool {
2971 fn ty_infer(&self, param: Option<&ty::GenericParamDef>, span: Span) -> Ty<'tcx> {
2972 if let Some(param) = param {
2973 if let GenericArgKind::Type(ty) = self.var_for_def(span, param).unpack() {
2978 self.next_ty_var(TypeVariableOrigin {
2979 kind: TypeVariableOriginKind::TypeInference,
2988 param: Option<&ty::GenericParamDef>,
2990 ) -> &'tcx Const<'tcx> {
2991 if let Some(param) = param {
2992 if let GenericArgKind::Const(ct) = self.var_for_def(span, param).unpack() {
2997 self.next_const_var(
2999 ConstVariableOrigin { kind: ConstVariableOriginKind::ConstInference, span },
3004 fn projected_ty_from_poly_trait_ref(
3008 item_segment: &hir::PathSegment<'_>,
3009 poly_trait_ref: ty::PolyTraitRef<'tcx>,
3011 let (trait_ref, _) = self.replace_bound_vars_with_fresh_vars(
3013 infer::LateBoundRegionConversionTime::AssocTypeProjection(item_def_id),
3017 let item_substs = <dyn AstConv<'tcx>>::create_substs_for_associated_item(
3026 self.tcx().mk_projection(item_def_id, item_substs)
3029 fn normalize_ty(&self, span: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
3030 if ty.has_escaping_bound_vars() {
3031 ty // FIXME: normalization and escaping regions
3033 self.normalize_associated_types_in(span, &ty)
3037 fn set_tainted_by_errors(&self) {
3038 self.infcx.set_tainted_by_errors()
3041 fn record_ty(&self, hir_id: hir::HirId, ty: Ty<'tcx>, _span: Span) {
3042 self.write_ty(hir_id, ty)
3046 /// Controls whether the arguments are tupled. This is used for the call
3049 /// Tupling means that all call-side arguments are packed into a tuple and
3050 /// passed as a single parameter. For example, if tupling is enabled, this
3053 /// fn f(x: (isize, isize))
3055 /// Can be called as:
3062 #[derive(Clone, Eq, PartialEq)]
3063 enum TupleArgumentsFlag {
3068 /// Controls how we perform fallback for unconstrained
3071 /// Do not fallback type variables to opaque types.
3073 /// Perform all possible kinds of fallback, including
3074 /// turning type variables to opaque types.
3078 impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
3080 inh: &'a Inherited<'a, 'tcx>,
3081 param_env: ty::ParamEnv<'tcx>,
3082 body_id: hir::HirId,
3083 ) -> FnCtxt<'a, 'tcx> {
3087 err_count_on_creation: inh.tcx.sess.err_count(),
3089 ret_coercion_span: RefCell::new(None),
3090 resume_yield_tys: None,
3091 ps: RefCell::new(UnsafetyState::function(hir::Unsafety::Normal, hir::CRATE_HIR_ID)),
3092 diverges: Cell::new(Diverges::Maybe),
3093 has_errors: Cell::new(false),
3094 enclosing_breakables: RefCell::new(EnclosingBreakables {
3096 by_id: Default::default(),
3102 pub fn sess(&self) -> &Session {
3106 pub fn errors_reported_since_creation(&self) -> bool {
3107 self.tcx.sess.err_count() > self.err_count_on_creation
3110 /// Produces warning on the given node, if the current point in the
3111 /// function is unreachable, and there hasn't been another warning.
3112 fn warn_if_unreachable(&self, id: hir::HirId, span: Span, kind: &str) {
3113 // FIXME: Combine these two 'if' expressions into one once
3114 // let chains are implemented
3115 if let Diverges::Always { span: orig_span, custom_note } = self.diverges.get() {
3116 // If span arose from a desugaring of `if` or `while`, then it is the condition itself,
3117 // which diverges, that we are about to lint on. This gives suboptimal diagnostics.
3118 // Instead, stop here so that the `if`- or `while`-expression's block is linted instead.
3119 if !span.is_desugaring(DesugaringKind::CondTemporary)
3120 && !span.is_desugaring(DesugaringKind::Async)
3121 && !orig_span.is_desugaring(DesugaringKind::Await)
3123 self.diverges.set(Diverges::WarnedAlways);
3125 debug!("warn_if_unreachable: id={:?} span={:?} kind={}", id, span, kind);
3127 self.tcx().struct_span_lint_hir(lint::builtin::UNREACHABLE_CODE, id, span, |lint| {
3128 let msg = format!("unreachable {}", kind);
3130 .span_label(span, &msg)
3134 .unwrap_or("any code following this expression is unreachable"),
3142 pub fn cause(&self, span: Span, code: ObligationCauseCode<'tcx>) -> ObligationCause<'tcx> {
3143 ObligationCause::new(span, self.body_id, code)
3146 pub fn misc(&self, span: Span) -> ObligationCause<'tcx> {
3147 self.cause(span, ObligationCauseCode::MiscObligation)
3150 /// Resolves type and const variables in `ty` if possible. Unlike the infcx
3151 /// version (resolve_vars_if_possible), this version will
3152 /// also select obligations if it seems useful, in an effort
3153 /// to get more type information.
3154 fn resolve_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
3155 debug!("resolve_vars_with_obligations(ty={:?})", ty);
3157 // No Infer()? Nothing needs doing.
3158 if !ty.has_infer_types_or_consts() {
3159 debug!("resolve_vars_with_obligations: ty={:?}", ty);
3163 // If `ty` is a type variable, see whether we already know what it is.
3164 ty = self.resolve_vars_if_possible(&ty);
3165 if !ty.has_infer_types_or_consts() {
3166 debug!("resolve_vars_with_obligations: ty={:?}", ty);
3170 // If not, try resolving pending obligations as much as
3171 // possible. This can help substantially when there are
3172 // indirect dependencies that don't seem worth tracking
3174 self.select_obligations_where_possible(false, |_| {});
3175 ty = self.resolve_vars_if_possible(&ty);
3177 debug!("resolve_vars_with_obligations: ty={:?}", ty);
3181 fn record_deferred_call_resolution(
3183 closure_def_id: DefId,
3184 r: DeferredCallResolution<'tcx>,
3186 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
3187 deferred_call_resolutions.entry(closure_def_id).or_default().push(r);
3190 fn remove_deferred_call_resolutions(
3192 closure_def_id: DefId,
3193 ) -> Vec<DeferredCallResolution<'tcx>> {
3194 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
3195 deferred_call_resolutions.remove(&closure_def_id).unwrap_or(vec![])
3198 pub fn tag(&self) -> String {
3199 format!("{:p}", self)
3202 pub fn local_ty(&self, span: Span, nid: hir::HirId) -> LocalTy<'tcx> {
3203 self.locals.borrow().get(&nid).cloned().unwrap_or_else(|| {
3204 span_bug!(span, "no type for local variable {}", self.tcx.hir().node_to_string(nid))
3209 pub fn write_ty(&self, id: hir::HirId, ty: Ty<'tcx>) {
3211 "write_ty({:?}, {:?}) in fcx {}",
3213 self.resolve_vars_if_possible(&ty),
3216 self.typeck_results.borrow_mut().node_types_mut().insert(id, ty);
3218 if ty.references_error() {
3219 self.has_errors.set(true);
3220 self.set_tainted_by_errors();
3224 pub fn write_field_index(&self, hir_id: hir::HirId, index: usize) {
3225 self.typeck_results.borrow_mut().field_indices_mut().insert(hir_id, index);
3228 fn write_resolution(&self, hir_id: hir::HirId, r: Result<(DefKind, DefId), ErrorReported>) {
3229 self.typeck_results.borrow_mut().type_dependent_defs_mut().insert(hir_id, r);
3232 pub fn write_method_call(&self, hir_id: hir::HirId, method: MethodCallee<'tcx>) {
3233 debug!("write_method_call(hir_id={:?}, method={:?})", hir_id, method);
3234 self.write_resolution(hir_id, Ok((DefKind::AssocFn, method.def_id)));
3235 self.write_substs(hir_id, method.substs);
3237 // When the method is confirmed, the `method.substs` includes
3238 // parameters from not just the method, but also the impl of
3239 // the method -- in particular, the `Self` type will be fully
3240 // resolved. However, those are not something that the "user
3241 // specified" -- i.e., those types come from the inferred type
3242 // of the receiver, not something the user wrote. So when we
3243 // create the user-substs, we want to replace those earlier
3244 // types with just the types that the user actually wrote --
3245 // that is, those that appear on the *method itself*.
3247 // As an example, if the user wrote something like
3248 // `foo.bar::<u32>(...)` -- the `Self` type here will be the
3249 // type of `foo` (possibly adjusted), but we don't want to
3250 // include that. We want just the `[_, u32]` part.
3251 if !method.substs.is_noop() {
3252 let method_generics = self.tcx.generics_of(method.def_id);
3253 if !method_generics.params.is_empty() {
3254 let user_type_annotation = self.infcx.probe(|_| {
3255 let user_substs = UserSubsts {
3256 substs: InternalSubsts::for_item(self.tcx, method.def_id, |param, _| {
3257 let i = param.index as usize;
3258 if i < method_generics.parent_count {
3259 self.infcx.var_for_def(DUMMY_SP, param)
3264 user_self_ty: None, // not relevant here
3267 self.infcx.canonicalize_user_type_annotation(&UserType::TypeOf(
3273 debug!("write_method_call: user_type_annotation={:?}", user_type_annotation);
3274 self.write_user_type_annotation(hir_id, user_type_annotation);
3279 pub fn write_substs(&self, node_id: hir::HirId, substs: SubstsRef<'tcx>) {
3280 if !substs.is_noop() {
3281 debug!("write_substs({:?}, {:?}) in fcx {}", node_id, substs, self.tag());
3283 self.typeck_results.borrow_mut().node_substs_mut().insert(node_id, substs);
3287 /// Given the substs that we just converted from the HIR, try to
3288 /// canonicalize them and store them as user-given substitutions
3289 /// (i.e., substitutions that must be respected by the NLL check).
3291 /// This should be invoked **before any unifications have
3292 /// occurred**, so that annotations like `Vec<_>` are preserved
3294 pub fn write_user_type_annotation_from_substs(
3298 substs: SubstsRef<'tcx>,
3299 user_self_ty: Option<UserSelfTy<'tcx>>,
3302 "write_user_type_annotation_from_substs: hir_id={:?} def_id={:?} substs={:?} \
3303 user_self_ty={:?} in fcx {}",
3311 if Self::can_contain_user_lifetime_bounds((substs, user_self_ty)) {
3312 let canonicalized = self.infcx.canonicalize_user_type_annotation(&UserType::TypeOf(
3314 UserSubsts { substs, user_self_ty },
3316 debug!("write_user_type_annotation_from_substs: canonicalized={:?}", canonicalized);
3317 self.write_user_type_annotation(hir_id, canonicalized);
3321 pub fn write_user_type_annotation(
3324 canonical_user_type_annotation: CanonicalUserType<'tcx>,
3327 "write_user_type_annotation: hir_id={:?} canonical_user_type_annotation={:?} tag={}",
3329 canonical_user_type_annotation,
3333 if !canonical_user_type_annotation.is_identity() {
3336 .user_provided_types_mut()
3337 .insert(hir_id, canonical_user_type_annotation);
3339 debug!("write_user_type_annotation: skipping identity substs");
3343 pub fn apply_adjustments(&self, expr: &hir::Expr<'_>, adj: Vec<Adjustment<'tcx>>) {
3344 debug!("apply_adjustments(expr={:?}, adj={:?})", expr, adj);
3350 let autoborrow_mut = adj.iter().any(|adj| {
3351 matches!(adj, &Adjustment {
3352 kind: Adjust::Borrow(AutoBorrow::Ref(_, AutoBorrowMutability::Mut { .. })),
3357 match self.typeck_results.borrow_mut().adjustments_mut().entry(expr.hir_id) {
3358 Entry::Vacant(entry) => {
3361 Entry::Occupied(mut entry) => {
3362 debug!(" - composing on top of {:?}", entry.get());
3363 match (&entry.get()[..], &adj[..]) {
3364 // Applying any adjustment on top of a NeverToAny
3365 // is a valid NeverToAny adjustment, because it can't
3367 (&[Adjustment { kind: Adjust::NeverToAny, .. }], _) => return,
3369 Adjustment { kind: Adjust::Deref(_), .. },
3370 Adjustment { kind: Adjust::Borrow(AutoBorrow::Ref(..)), .. },
3372 Adjustment { kind: Adjust::Deref(_), .. },
3373 .. // Any following adjustments are allowed.
3375 // A reborrow has no effect before a dereference.
3377 // FIXME: currently we never try to compose autoderefs
3378 // and ReifyFnPointer/UnsafeFnPointer, but we could.
3380 bug!("while adjusting {:?}, can't compose {:?} and {:?}",
3381 expr, entry.get(), adj)
3383 *entry.get_mut() = adj;
3387 // If there is an mutable auto-borrow, it is equivalent to `&mut <expr>`.
3388 // In this case implicit use of `Deref` and `Index` within `<expr>` should
3389 // instead be `DerefMut` and `IndexMut`, so fix those up.
3391 self.convert_place_derefs_to_mutable(expr);
3395 /// Basically whenever we are converting from a type scheme into
3396 /// the fn body space, we always want to normalize associated
3397 /// types as well. This function combines the two.
3398 fn instantiate_type_scheme<T>(&self, span: Span, substs: SubstsRef<'tcx>, value: &T) -> T
3400 T: TypeFoldable<'tcx>,
3402 let value = value.subst(self.tcx, substs);
3403 let result = self.normalize_associated_types_in(span, &value);
3404 debug!("instantiate_type_scheme(value={:?}, substs={:?}) = {:?}", value, substs, result);
3408 /// As `instantiate_type_scheme`, but for the bounds found in a
3409 /// generic type scheme.
3410 fn instantiate_bounds(
3414 substs: SubstsRef<'tcx>,
3415 ) -> (ty::InstantiatedPredicates<'tcx>, Vec<Span>) {
3416 let bounds = self.tcx.predicates_of(def_id);
3417 let spans: Vec<Span> = bounds.predicates.iter().map(|(_, span)| *span).collect();
3418 let result = bounds.instantiate(self.tcx, substs);
3419 let result = self.normalize_associated_types_in(span, &result);
3421 "instantiate_bounds(bounds={:?}, substs={:?}) = {:?}, {:?}",
3422 bounds, substs, result, spans,
3427 /// Replaces the opaque types from the given value with type variables,
3428 /// and records the `OpaqueTypeMap` for later use during writeback. See
3429 /// `InferCtxt::instantiate_opaque_types` for more details.
3430 fn instantiate_opaque_types_from_value<T: TypeFoldable<'tcx>>(
3432 parent_id: hir::HirId,
3436 let parent_def_id = self.tcx.hir().local_def_id(parent_id);
3438 "instantiate_opaque_types_from_value(parent_def_id={:?}, value={:?})",
3439 parent_def_id, value
3442 let (value, opaque_type_map) =
3443 self.register_infer_ok_obligations(self.instantiate_opaque_types(
3451 let mut opaque_types = self.opaque_types.borrow_mut();
3452 let mut opaque_types_vars = self.opaque_types_vars.borrow_mut();
3453 for (ty, decl) in opaque_type_map {
3454 let _ = opaque_types.insert(ty, decl);
3455 let _ = opaque_types_vars.insert(decl.concrete_ty, decl.opaque_type);
3461 fn normalize_associated_types_in<T>(&self, span: Span, value: &T) -> T
3463 T: TypeFoldable<'tcx>,
3465 self.inh.normalize_associated_types_in(span, self.body_id, self.param_env, value)
3468 fn normalize_associated_types_in_as_infer_ok<T>(
3472 ) -> InferOk<'tcx, T>
3474 T: TypeFoldable<'tcx>,
3476 self.inh.partially_normalize_associated_types_in(span, self.body_id, self.param_env, value)
3479 pub fn require_type_meets(
3483 code: traits::ObligationCauseCode<'tcx>,
3486 self.register_bound(ty, def_id, traits::ObligationCause::new(span, self.body_id, code));
3489 pub fn require_type_is_sized(
3493 code: traits::ObligationCauseCode<'tcx>,
3495 if !ty.references_error() {
3496 let lang_item = self.tcx.require_lang_item(SizedTraitLangItem, None);
3497 self.require_type_meets(ty, span, code, lang_item);
3501 pub fn require_type_is_sized_deferred(
3505 code: traits::ObligationCauseCode<'tcx>,
3507 if !ty.references_error() {
3508 self.deferred_sized_obligations.borrow_mut().push((ty, span, code));
3512 pub fn register_bound(
3516 cause: traits::ObligationCause<'tcx>,
3518 if !ty.references_error() {
3519 self.fulfillment_cx.borrow_mut().register_bound(
3529 pub fn to_ty(&self, ast_t: &hir::Ty<'_>) -> Ty<'tcx> {
3530 let t = AstConv::ast_ty_to_ty(self, ast_t);
3531 self.register_wf_obligation(t.into(), ast_t.span, traits::MiscObligation);
3535 pub fn to_ty_saving_user_provided_ty(&self, ast_ty: &hir::Ty<'_>) -> Ty<'tcx> {
3536 let ty = self.to_ty(ast_ty);
3537 debug!("to_ty_saving_user_provided_ty: ty={:?}", ty);
3539 if Self::can_contain_user_lifetime_bounds(ty) {
3540 let c_ty = self.infcx.canonicalize_response(&UserType::Ty(ty));
3541 debug!("to_ty_saving_user_provided_ty: c_ty={:?}", c_ty);
3542 self.typeck_results.borrow_mut().user_provided_types_mut().insert(ast_ty.hir_id, c_ty);
3548 pub fn to_const(&self, ast_c: &hir::AnonConst) -> &'tcx ty::Const<'tcx> {
3549 let const_def_id = self.tcx.hir().local_def_id(ast_c.hir_id);
3550 let c = ty::Const::from_anon_const(self.tcx, const_def_id);
3551 self.register_wf_obligation(
3553 self.tcx.hir().span(ast_c.hir_id),
3554 ObligationCauseCode::MiscObligation,
3559 pub fn const_arg_to_const(
3561 ast_c: &hir::AnonConst,
3562 param_def_id: DefId,
3563 ) -> &'tcx ty::Const<'tcx> {
3564 let const_def = ty::WithOptConstParam {
3565 did: self.tcx.hir().local_def_id(ast_c.hir_id),
3566 const_param_did: Some(param_def_id),
3568 let c = ty::Const::from_opt_const_arg_anon_const(self.tcx, const_def);
3569 self.register_wf_obligation(
3571 self.tcx.hir().span(ast_c.hir_id),
3572 ObligationCauseCode::MiscObligation,
3577 // If the type given by the user has free regions, save it for later, since
3578 // NLL would like to enforce those. Also pass in types that involve
3579 // projections, since those can resolve to `'static` bounds (modulo #54940,
3580 // which hopefully will be fixed by the time you see this comment, dear
3581 // reader, although I have my doubts). Also pass in types with inference
3582 // types, because they may be repeated. Other sorts of things are already
3583 // sufficiently enforced with erased regions. =)
3584 fn can_contain_user_lifetime_bounds<T>(t: T) -> bool
3586 T: TypeFoldable<'tcx>,
3588 t.has_free_regions() || t.has_projections() || t.has_infer_types()
3591 pub fn node_ty(&self, id: hir::HirId) -> Ty<'tcx> {
3592 match self.typeck_results.borrow().node_types().get(id) {
3594 None if self.is_tainted_by_errors() => self.tcx.ty_error(),
3597 "no type for node {}: {} in fcx {}",
3599 self.tcx.hir().node_to_string(id),
3606 /// Registers an obligation for checking later, during regionck, that `arg` is well-formed.
3607 pub fn register_wf_obligation(
3609 arg: subst::GenericArg<'tcx>,
3611 code: traits::ObligationCauseCode<'tcx>,
3613 // WF obligations never themselves fail, so no real need to give a detailed cause:
3614 let cause = traits::ObligationCause::new(span, self.body_id, code);
3615 self.register_predicate(traits::Obligation::new(
3618 ty::PredicateAtom::WellFormed(arg).to_predicate(self.tcx),
3622 /// Registers obligations that all `substs` are well-formed.
3623 pub fn add_wf_bounds(&self, substs: SubstsRef<'tcx>, expr: &hir::Expr<'_>) {
3624 for arg in substs.iter().filter(|arg| {
3625 matches!(arg.unpack(), GenericArgKind::Type(..) | GenericArgKind::Const(..))
3627 self.register_wf_obligation(arg, expr.span, traits::MiscObligation);
3631 /// Given a fully substituted set of bounds (`generic_bounds`), and the values with which each
3632 /// type/region parameter was instantiated (`substs`), creates and registers suitable
3633 /// trait/region obligations.
3635 /// For example, if there is a function:
3638 /// fn foo<'a,T:'a>(...)
3641 /// and a reference:
3647 /// Then we will create a fresh region variable `'$0` and a fresh type variable `$1` for `'a`
3648 /// and `T`. This routine will add a region obligation `$1:'$0` and register it locally.
3649 pub fn add_obligations_for_parameters(
3651 cause: traits::ObligationCause<'tcx>,
3652 predicates: ty::InstantiatedPredicates<'tcx>,
3654 assert!(!predicates.has_escaping_bound_vars());
3656 debug!("add_obligations_for_parameters(predicates={:?})", predicates);
3658 for obligation in traits::predicates_for_generics(cause, self.param_env, predicates) {
3659 self.register_predicate(obligation);
3663 // FIXME(arielb1): use this instead of field.ty everywhere
3664 // Only for fields! Returns <none> for methods>
3665 // Indifferent to privacy flags
3669 field: &'tcx ty::FieldDef,
3670 substs: SubstsRef<'tcx>,
3672 self.normalize_associated_types_in(span, &field.ty(self.tcx, substs))
3675 fn check_casts(&self) {
3676 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
3677 for cast in deferred_cast_checks.drain(..) {
3682 fn resolve_generator_interiors(&self, def_id: DefId) {
3683 let mut generators = self.deferred_generator_interiors.borrow_mut();
3684 for (body_id, interior, kind) in generators.drain(..) {
3685 self.select_obligations_where_possible(false, |_| {});
3686 generator_interior::resolve_interior(self, def_id, body_id, interior, kind);
3690 // Tries to apply a fallback to `ty` if it is an unsolved variable.
3692 // - Unconstrained ints are replaced with `i32`.
3694 // - Unconstrained floats are replaced with with `f64`.
3696 // - Non-numerics get replaced with `!` when `#![feature(never_type_fallback)]`
3697 // is enabled. Otherwise, they are replaced with `()`.
3699 // Fallback becomes very dubious if we have encountered type-checking errors.
3700 // In that case, fallback to Error.
3701 // The return value indicates whether fallback has occurred.
3702 fn fallback_if_possible(&self, ty: Ty<'tcx>, mode: FallbackMode) -> bool {
3703 use rustc_middle::ty::error::UnconstrainedNumeric::Neither;
3704 use rustc_middle::ty::error::UnconstrainedNumeric::{UnconstrainedFloat, UnconstrainedInt};
3706 assert!(ty.is_ty_infer());
3707 let fallback = match self.type_is_unconstrained_numeric(ty) {
3708 _ if self.is_tainted_by_errors() => self.tcx().ty_error(),
3709 UnconstrainedInt => self.tcx.types.i32,
3710 UnconstrainedFloat => self.tcx.types.f64,
3711 Neither if self.type_var_diverges(ty) => self.tcx.mk_diverging_default(),
3713 // This type variable was created from the instantiation of an opaque
3714 // type. The fact that we're attempting to perform fallback for it
3715 // means that the function neither constrained it to a concrete
3716 // type, nor to the opaque type itself.
3718 // For example, in this code:
3721 // type MyType = impl Copy;
3722 // fn defining_use() -> MyType { true }
3723 // fn other_use() -> MyType { defining_use() }
3726 // `defining_use` will constrain the instantiated inference
3727 // variable to `bool`, while `other_use` will constrain
3728 // the instantiated inference variable to `MyType`.
3730 // When we process opaque types during writeback, we
3731 // will handle cases like `other_use`, and not count
3732 // them as defining usages
3734 // However, we also need to handle cases like this:
3737 // pub type Foo = impl Copy;
3738 // fn produce() -> Option<Foo> {
3743 // In the above snippet, the inference variable created by
3744 // instantiating `Option<Foo>` will be completely unconstrained.
3745 // We treat this as a non-defining use by making the inference
3746 // variable fall back to the opaque type itself.
3747 if let FallbackMode::All = mode {
3748 if let Some(opaque_ty) = self.opaque_types_vars.borrow().get(ty) {
3750 "fallback_if_possible: falling back opaque type var {:?} to {:?}",
3762 debug!("fallback_if_possible: defaulting `{:?}` to `{:?}`", ty, fallback);
3763 self.demand_eqtype(rustc_span::DUMMY_SP, ty, fallback);
3767 fn select_all_obligations_or_error(&self) {
3768 debug!("select_all_obligations_or_error");
3769 if let Err(errors) = self.fulfillment_cx.borrow_mut().select_all_or_error(&self) {
3770 self.report_fulfillment_errors(&errors, self.inh.body_id, false);
3774 /// Select as many obligations as we can at present.
3775 fn select_obligations_where_possible(
3777 fallback_has_occurred: bool,
3778 mutate_fullfillment_errors: impl Fn(&mut Vec<traits::FulfillmentError<'tcx>>),
3780 let result = self.fulfillment_cx.borrow_mut().select_where_possible(self);
3781 if let Err(mut errors) = result {
3782 mutate_fullfillment_errors(&mut errors);
3783 self.report_fulfillment_errors(&errors, self.inh.body_id, fallback_has_occurred);
3787 /// For the overloaded place expressions (`*x`, `x[3]`), the trait
3788 /// returns a type of `&T`, but the actual type we assign to the
3789 /// *expression* is `T`. So this function just peels off the return
3790 /// type by one layer to yield `T`.
3791 fn make_overloaded_place_return_type(
3793 method: MethodCallee<'tcx>,
3794 ) -> ty::TypeAndMut<'tcx> {
3795 // extract method return type, which will be &T;
3796 let ret_ty = method.sig.output();
3798 // method returns &T, but the type as visible to user is T, so deref
3799 ret_ty.builtin_deref(true).unwrap()
3802 fn check_method_argument_types(
3805 expr: &'tcx hir::Expr<'tcx>,
3806 method: Result<MethodCallee<'tcx>, ()>,
3807 args_no_rcvr: &'tcx [hir::Expr<'tcx>],
3808 tuple_arguments: TupleArgumentsFlag,
3809 expected: Expectation<'tcx>,
3811 let has_error = match method {
3812 Ok(method) => method.substs.references_error() || method.sig.references_error(),
3816 let err_inputs = self.err_args(args_no_rcvr.len());
3818 let err_inputs = match tuple_arguments {
3819 DontTupleArguments => err_inputs,
3820 TupleArguments => vec![self.tcx.intern_tup(&err_inputs[..])],
3823 self.check_argument_types(
3833 return self.tcx.ty_error();
3836 let method = method.unwrap();
3837 // HACK(eddyb) ignore self in the definition (see above).
3838 let expected_arg_tys = self.expected_inputs_for_expected_output(
3841 method.sig.output(),
3842 &method.sig.inputs()[1..],
3844 self.check_argument_types(
3847 &method.sig.inputs()[1..],
3848 &expected_arg_tys[..],
3850 method.sig.c_variadic,
3852 self.tcx.hir().span_if_local(method.def_id),
3857 fn self_type_matches_expected_vid(
3859 trait_ref: ty::PolyTraitRef<'tcx>,
3860 expected_vid: ty::TyVid,
3862 let self_ty = self.shallow_resolve(trait_ref.skip_binder().self_ty());
3864 "self_type_matches_expected_vid(trait_ref={:?}, self_ty={:?}, expected_vid={:?})",
3865 trait_ref, self_ty, expected_vid
3867 match self_ty.kind {
3868 ty::Infer(ty::TyVar(found_vid)) => {
3869 // FIXME: consider using `sub_root_var` here so we
3870 // can see through subtyping.
3871 let found_vid = self.root_var(found_vid);
3872 debug!("self_type_matches_expected_vid - found_vid={:?}", found_vid);
3873 expected_vid == found_vid
3879 fn obligations_for_self_ty<'b>(
3882 ) -> impl Iterator<Item = (ty::PolyTraitRef<'tcx>, traits::PredicateObligation<'tcx>)>
3885 // FIXME: consider using `sub_root_var` here so we
3886 // can see through subtyping.
3887 let ty_var_root = self.root_var(self_ty);
3889 "obligations_for_self_ty: self_ty={:?} ty_var_root={:?} pending_obligations={:?}",
3892 self.fulfillment_cx.borrow().pending_obligations()
3897 .pending_obligations()
3899 .filter_map(move |obligation| {
3900 match obligation.predicate.skip_binders() {
3901 ty::PredicateAtom::Projection(data) => {
3902 Some((ty::Binder::bind(data).to_poly_trait_ref(self.tcx), obligation))
3904 ty::PredicateAtom::Trait(data, _) => {
3905 Some((ty::Binder::bind(data).to_poly_trait_ref(), obligation))
3907 ty::PredicateAtom::Subtype(..) => None,
3908 ty::PredicateAtom::RegionOutlives(..) => None,
3909 ty::PredicateAtom::TypeOutlives(..) => None,
3910 ty::PredicateAtom::WellFormed(..) => None,
3911 ty::PredicateAtom::ObjectSafe(..) => None,
3912 ty::PredicateAtom::ConstEvaluatable(..) => None,
3913 ty::PredicateAtom::ConstEquate(..) => None,
3914 // N.B., this predicate is created by breaking down a
3915 // `ClosureType: FnFoo()` predicate, where
3916 // `ClosureType` represents some `Closure`. It can't
3917 // possibly be referring to the current closure,
3918 // because we haven't produced the `Closure` for
3919 // this closure yet; this is exactly why the other
3920 // code is looking for a self type of a unresolved
3921 // inference variable.
3922 ty::PredicateAtom::ClosureKind(..) => None,
3925 .filter(move |(tr, _)| self.self_type_matches_expected_vid(*tr, ty_var_root))
3928 fn type_var_is_sized(&self, self_ty: ty::TyVid) -> bool {
3929 self.obligations_for_self_ty(self_ty)
3930 .any(|(tr, _)| Some(tr.def_id()) == self.tcx.lang_items().sized_trait())
3933 /// Generic function that factors out common logic from function calls,
3934 /// method calls and overloaded operators.
3935 fn check_argument_types(
3938 expr: &'tcx hir::Expr<'tcx>,
3939 fn_inputs: &[Ty<'tcx>],
3940 expected_arg_tys: &[Ty<'tcx>],
3941 args: &'tcx [hir::Expr<'tcx>],
3943 tuple_arguments: TupleArgumentsFlag,
3944 def_span: Option<Span>,
3947 // Grab the argument types, supplying fresh type variables
3948 // if the wrong number of arguments were supplied
3949 let supplied_arg_count = if tuple_arguments == DontTupleArguments { args.len() } else { 1 };
3951 // All the input types from the fn signature must outlive the call
3952 // so as to validate implied bounds.
3953 for (&fn_input_ty, arg_expr) in fn_inputs.iter().zip(args.iter()) {
3954 self.register_wf_obligation(fn_input_ty.into(), arg_expr.span, traits::MiscObligation);
3957 let expected_arg_count = fn_inputs.len();
3959 let param_count_error = |expected_count: usize,
3964 let (span, start_span, args) = match &expr.kind {
3965 hir::ExprKind::Call(hir::Expr { span, .. }, args) => (*span, *span, &args[..]),
3966 hir::ExprKind::MethodCall(path_segment, span, args, _) => (
3968 // `sp` doesn't point at the whole `foo.bar()`, only at `bar`.
3971 .and_then(|args| args.args.iter().last())
3972 // Account for `foo.bar::<T>()`.
3974 // Skip the closing `>`.
3977 .next_point(tcx.sess.source_map().next_point(arg.span()))
3980 &args[1..], // Skip the receiver.
3982 k => span_bug!(sp, "checking argument types on a non-call: `{:?}`", k),
3984 let arg_spans = if args.is_empty() {
3986 // ^^^-- supplied 0 arguments
3988 // expected 2 arguments
3989 vec![tcx.sess.source_map().next_point(start_span).with_hi(sp.hi())]
3992 // ^^^ - - - supplied 3 arguments
3994 // expected 2 arguments
3995 args.iter().map(|arg| arg.span).collect::<Vec<Span>>()
3998 let mut err = tcx.sess.struct_span_err_with_code(
4001 "this function takes {}{} but {} {} supplied",
4002 if c_variadic { "at least " } else { "" },
4003 potentially_plural_count(expected_count, "argument"),
4004 potentially_plural_count(arg_count, "argument"),
4005 if arg_count == 1 { "was" } else { "were" }
4007 DiagnosticId::Error(error_code.to_owned()),
4009 let label = format!("supplied {}", potentially_plural_count(arg_count, "argument"));
4010 for (i, span) in arg_spans.into_iter().enumerate() {
4013 if arg_count == 0 || i + 1 == arg_count { &label } else { "" },
4017 if let Some(def_s) = def_span.map(|sp| tcx.sess.source_map().guess_head_span(sp)) {
4018 err.span_label(def_s, "defined here");
4021 let sugg_span = tcx.sess.source_map().end_point(expr.span);
4022 // remove closing `)` from the span
4023 let sugg_span = sugg_span.shrink_to_lo();
4024 err.span_suggestion(
4026 "expected the unit value `()`; create it with empty parentheses",
4028 Applicability::MachineApplicable,
4035 if c_variadic { "at least " } else { "" },
4036 potentially_plural_count(expected_count, "argument")
4043 let mut expected_arg_tys = expected_arg_tys.to_vec();
4045 let formal_tys = if tuple_arguments == TupleArguments {
4046 let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
4047 match tuple_type.kind {
4048 ty::Tuple(arg_types) if arg_types.len() != args.len() => {
4049 param_count_error(arg_types.len(), args.len(), "E0057", false, false);
4050 expected_arg_tys = vec![];
4051 self.err_args(args.len())
4053 ty::Tuple(arg_types) => {
4054 expected_arg_tys = match expected_arg_tys.get(0) {
4055 Some(&ty) => match ty.kind {
4056 ty::Tuple(ref tys) => tys.iter().map(|k| k.expect_ty()).collect(),
4061 arg_types.iter().map(|k| k.expect_ty()).collect()
4068 "cannot use call notation; the first type parameter \
4069 for the function trait is neither a tuple nor unit"
4072 expected_arg_tys = vec![];
4073 self.err_args(args.len())
4076 } else if expected_arg_count == supplied_arg_count {
4078 } else if c_variadic {
4079 if supplied_arg_count >= expected_arg_count {
4082 param_count_error(expected_arg_count, supplied_arg_count, "E0060", true, false);
4083 expected_arg_tys = vec![];
4084 self.err_args(supplied_arg_count)
4087 // is the missing argument of type `()`?
4088 let sugg_unit = if expected_arg_tys.len() == 1 && supplied_arg_count == 0 {
4089 self.resolve_vars_if_possible(&expected_arg_tys[0]).is_unit()
4090 } else if fn_inputs.len() == 1 && supplied_arg_count == 0 {
4091 self.resolve_vars_if_possible(&fn_inputs[0]).is_unit()
4095 param_count_error(expected_arg_count, supplied_arg_count, "E0061", false, sugg_unit);
4097 expected_arg_tys = vec![];
4098 self.err_args(supplied_arg_count)
4102 "check_argument_types: formal_tys={:?}",
4103 formal_tys.iter().map(|t| self.ty_to_string(*t)).collect::<Vec<String>>()
4106 // If there is no expectation, expect formal_tys.
4107 let expected_arg_tys =
4108 if !expected_arg_tys.is_empty() { expected_arg_tys } else { formal_tys.clone() };
4110 let mut final_arg_types: Vec<(usize, Ty<'_>, Ty<'_>)> = vec![];
4112 // Check the arguments.
4113 // We do this in a pretty awful way: first we type-check any arguments
4114 // that are not closures, then we type-check the closures. This is so
4115 // that we have more information about the types of arguments when we
4116 // type-check the functions. This isn't really the right way to do this.
4117 for &check_closures in &[false, true] {
4118 debug!("check_closures={}", check_closures);
4120 // More awful hacks: before we check argument types, try to do
4121 // an "opportunistic" trait resolution of any trait bounds on
4122 // the call. This helps coercions.
4124 self.select_obligations_where_possible(false, |errors| {
4125 self.point_at_type_arg_instead_of_call_if_possible(errors, expr);
4126 self.point_at_arg_instead_of_call_if_possible(
4128 &final_arg_types[..],
4135 // For C-variadic functions, we don't have a declared type for all of
4136 // the arguments hence we only do our usual type checking with
4137 // the arguments who's types we do know.
4138 let t = if c_variadic {
4140 } else if tuple_arguments == TupleArguments {
4145 for (i, arg) in args.iter().take(t).enumerate() {
4146 // Warn only for the first loop (the "no closures" one).
4147 // Closure arguments themselves can't be diverging, but
4148 // a previous argument can, e.g., `foo(panic!(), || {})`.
4149 if !check_closures {
4150 self.warn_if_unreachable(arg.hir_id, arg.span, "expression");
4153 let is_closure = match arg.kind {
4154 ExprKind::Closure(..) => true,
4158 if is_closure != check_closures {
4162 debug!("checking the argument");
4163 let formal_ty = formal_tys[i];
4165 // The special-cased logic below has three functions:
4166 // 1. Provide as good of an expected type as possible.
4167 let expected = Expectation::rvalue_hint(self, expected_arg_tys[i]);
4169 let checked_ty = self.check_expr_with_expectation(&arg, expected);
4171 // 2. Coerce to the most detailed type that could be coerced
4172 // to, which is `expected_ty` if `rvalue_hint` returns an
4173 // `ExpectHasType(expected_ty)`, or the `formal_ty` otherwise.
4174 let coerce_ty = expected.only_has_type(self).unwrap_or(formal_ty);
4175 // We're processing function arguments so we definitely want to use
4176 // two-phase borrows.
4177 self.demand_coerce(&arg, checked_ty, coerce_ty, None, AllowTwoPhase::Yes);
4178 final_arg_types.push((i, checked_ty, coerce_ty));
4180 // 3. Relate the expected type and the formal one,
4181 // if the expected type was used for the coercion.
4182 self.demand_suptype(arg.span, formal_ty, coerce_ty);
4186 // We also need to make sure we at least write the ty of the other
4187 // arguments which we skipped above.
4189 fn variadic_error<'tcx>(s: &Session, span: Span, t: Ty<'tcx>, cast_ty: &str) {
4190 use crate::structured_errors::{StructuredDiagnostic, VariadicError};
4191 VariadicError::new(s, span, t, cast_ty).diagnostic().emit();
4194 for arg in args.iter().skip(expected_arg_count) {
4195 let arg_ty = self.check_expr(&arg);
4197 // There are a few types which get autopromoted when passed via varargs
4198 // in C but we just error out instead and require explicit casts.
4199 let arg_ty = self.structurally_resolved_type(arg.span, arg_ty);
4201 ty::Float(ast::FloatTy::F32) => {
4202 variadic_error(tcx.sess, arg.span, arg_ty, "c_double");
4204 ty::Int(ast::IntTy::I8 | ast::IntTy::I16) | ty::Bool => {
4205 variadic_error(tcx.sess, arg.span, arg_ty, "c_int");
4207 ty::Uint(ast::UintTy::U8 | ast::UintTy::U16) => {
4208 variadic_error(tcx.sess, arg.span, arg_ty, "c_uint");
4211 let ptr_ty = self.tcx.mk_fn_ptr(arg_ty.fn_sig(self.tcx));
4212 let ptr_ty = self.resolve_vars_if_possible(&ptr_ty);
4213 variadic_error(tcx.sess, arg.span, arg_ty, &ptr_ty.to_string());
4221 fn err_args(&self, len: usize) -> Vec<Ty<'tcx>> {
4222 vec![self.tcx.ty_error(); len]
4225 /// Given a vec of evaluated `FulfillmentError`s and an `fn` call argument expressions, we walk
4226 /// the checked and coerced types for each argument to see if any of the `FulfillmentError`s
4227 /// reference a type argument. The reason to walk also the checked type is that the coerced type
4228 /// can be not easily comparable with predicate type (because of coercion). If the types match
4229 /// for either checked or coerced type, and there's only *one* argument that does, we point at
4230 /// the corresponding argument's expression span instead of the `fn` call path span.
4231 fn point_at_arg_instead_of_call_if_possible(
4233 errors: &mut Vec<traits::FulfillmentError<'tcx>>,
4234 final_arg_types: &[(usize, Ty<'tcx>, Ty<'tcx>)],
4236 args: &'tcx [hir::Expr<'tcx>],
4238 // We *do not* do this for desugared call spans to keep good diagnostics when involving
4239 // the `?` operator.
4240 if call_sp.desugaring_kind().is_some() {
4244 for error in errors {
4245 // Only if the cause is somewhere inside the expression we want try to point at arg.
4246 // Otherwise, it means that the cause is somewhere else and we should not change
4247 // anything because we can break the correct span.
4248 if !call_sp.contains(error.obligation.cause.span) {
4252 if let ty::PredicateAtom::Trait(predicate, _) =
4253 error.obligation.predicate.skip_binders()
4255 // Collect the argument position for all arguments that could have caused this
4256 // `FulfillmentError`.
4257 let mut referenced_in = final_arg_types
4259 .map(|&(i, checked_ty, _)| (i, checked_ty))
4260 .chain(final_arg_types.iter().map(|&(i, _, coerced_ty)| (i, coerced_ty)))
4261 .flat_map(|(i, ty)| {
4262 let ty = self.resolve_vars_if_possible(&ty);
4263 // We walk the argument type because the argument's type could have
4264 // been `Option<T>`, but the `FulfillmentError` references `T`.
4265 if ty.walk().any(|arg| arg == predicate.self_ty().into()) {
4271 .collect::<Vec<_>>();
4273 // Both checked and coerced types could have matched, thus we need to remove
4275 referenced_in.sort();
4276 referenced_in.dedup();
4278 if let (Some(ref_in), None) = (referenced_in.pop(), referenced_in.pop()) {
4279 // We make sure that only *one* argument matches the obligation failure
4280 // and we assign the obligation's span to its expression's.
4281 error.obligation.cause.make_mut().span = args[ref_in].span;
4282 error.points_at_arg_span = true;
4288 /// Given a vec of evaluated `FulfillmentError`s and an `fn` call expression, we walk the
4289 /// `PathSegment`s and resolve their type parameters to see if any of the `FulfillmentError`s
4290 /// were caused by them. If they were, we point at the corresponding type argument's span
4291 /// instead of the `fn` call path span.
4292 fn point_at_type_arg_instead_of_call_if_possible(
4294 errors: &mut Vec<traits::FulfillmentError<'tcx>>,
4295 call_expr: &'tcx hir::Expr<'tcx>,
4297 if let hir::ExprKind::Call(path, _) = &call_expr.kind {
4298 if let hir::ExprKind::Path(qpath) = &path.kind {
4299 if let hir::QPath::Resolved(_, path) = &qpath {
4300 for error in errors {
4301 if let ty::PredicateAtom::Trait(predicate, _) =
4302 error.obligation.predicate.skip_binders()
4304 // If any of the type arguments in this path segment caused the
4305 // `FullfillmentError`, point at its span (#61860).
4309 .filter_map(|seg| seg.args.as_ref())
4310 .flat_map(|a| a.args.iter())
4312 if let hir::GenericArg::Type(hir_ty) = &arg {
4313 if let hir::TyKind::Path(hir::QPath::TypeRelative(..)) =
4316 // Avoid ICE with associated types. As this is best
4317 // effort only, it's ok to ignore the case. It
4318 // would trigger in `is_send::<T::AssocType>();`
4319 // from `typeck-default-trait-impl-assoc-type.rs`.
4321 let ty = AstConv::ast_ty_to_ty(self, hir_ty);
4322 let ty = self.resolve_vars_if_possible(&ty);
4323 if ty == predicate.self_ty() {
4324 error.obligation.cause.make_mut().span = hir_ty.span;
4336 // AST fragment checking
4337 fn check_lit(&self, lit: &hir::Lit, expected: Expectation<'tcx>) -> Ty<'tcx> {
4341 ast::LitKind::Str(..) => tcx.mk_static_str(),
4342 ast::LitKind::ByteStr(ref v) => {
4343 tcx.mk_imm_ref(tcx.lifetimes.re_static, tcx.mk_array(tcx.types.u8, v.len() as u64))
4345 ast::LitKind::Byte(_) => tcx.types.u8,
4346 ast::LitKind::Char(_) => tcx.types.char,
4347 ast::LitKind::Int(_, ast::LitIntType::Signed(t)) => tcx.mk_mach_int(t),
4348 ast::LitKind::Int(_, ast::LitIntType::Unsigned(t)) => tcx.mk_mach_uint(t),
4349 ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
4350 let opt_ty = expected.to_option(self).and_then(|ty| match ty.kind {
4351 ty::Int(_) | ty::Uint(_) => Some(ty),
4352 ty::Char => Some(tcx.types.u8),
4353 ty::RawPtr(..) => Some(tcx.types.usize),
4354 ty::FnDef(..) | ty::FnPtr(_) => Some(tcx.types.usize),
4357 opt_ty.unwrap_or_else(|| self.next_int_var())
4359 ast::LitKind::Float(_, ast::LitFloatType::Suffixed(t)) => tcx.mk_mach_float(t),
4360 ast::LitKind::Float(_, ast::LitFloatType::Unsuffixed) => {
4361 let opt_ty = expected.to_option(self).and_then(|ty| match ty.kind {
4362 ty::Float(_) => Some(ty),
4365 opt_ty.unwrap_or_else(|| self.next_float_var())
4367 ast::LitKind::Bool(_) => tcx.types.bool,
4368 ast::LitKind::Err(_) => tcx.ty_error(),
4372 /// Unifies the output type with the expected type early, for more coercions
4373 /// and forward type information on the input expressions.
4374 fn expected_inputs_for_expected_output(
4377 expected_ret: Expectation<'tcx>,
4378 formal_ret: Ty<'tcx>,
4379 formal_args: &[Ty<'tcx>],
4380 ) -> Vec<Ty<'tcx>> {
4381 let formal_ret = self.resolve_vars_with_obligations(formal_ret);
4382 let ret_ty = match expected_ret.only_has_type(self) {
4384 None => return Vec::new(),
4386 let expect_args = self
4387 .fudge_inference_if_ok(|| {
4388 // Attempt to apply a subtyping relationship between the formal
4389 // return type (likely containing type variables if the function
4390 // is polymorphic) and the expected return type.
4391 // No argument expectations are produced if unification fails.
4392 let origin = self.misc(call_span);
4393 let ures = self.at(&origin, self.param_env).sup(ret_ty, &formal_ret);
4395 // FIXME(#27336) can't use ? here, Try::from_error doesn't default
4396 // to identity so the resulting type is not constrained.
4399 // Process any obligations locally as much as
4400 // we can. We don't care if some things turn
4401 // out unconstrained or ambiguous, as we're
4402 // just trying to get hints here.
4403 self.save_and_restore_in_snapshot_flag(|_| {
4404 let mut fulfill = TraitEngine::new(self.tcx);
4405 for obligation in ok.obligations {
4406 fulfill.register_predicate_obligation(self, obligation);
4408 fulfill.select_where_possible(self)
4412 Err(_) => return Err(()),
4415 // Record all the argument types, with the substitutions
4416 // produced from the above subtyping unification.
4417 Ok(formal_args.iter().map(|ty| self.resolve_vars_if_possible(ty)).collect())
4419 .unwrap_or_default();
4421 "expected_inputs_for_expected_output(formal={:?} -> {:?}, expected={:?} -> {:?})",
4422 formal_args, formal_ret, expect_args, expected_ret
4427 pub fn check_struct_path(
4431 ) -> Option<(&'tcx ty::VariantDef, Ty<'tcx>)> {
4432 let path_span = qpath.qself_span();
4433 let (def, ty) = self.finish_resolving_struct_path(qpath, path_span, hir_id);
4434 let variant = match def {
4436 self.set_tainted_by_errors();
4439 Res::Def(DefKind::Variant, _) => match ty.kind {
4440 ty::Adt(adt, substs) => Some((adt.variant_of_res(def), adt.did, substs)),
4441 _ => bug!("unexpected type: {:?}", ty),
4443 Res::Def(DefKind::Struct | DefKind::Union | DefKind::TyAlias | DefKind::AssocTy, _)
4444 | Res::SelfTy(..) => match ty.kind {
4445 ty::Adt(adt, substs) if !adt.is_enum() => {
4446 Some((adt.non_enum_variant(), adt.did, substs))
4450 _ => bug!("unexpected definition: {:?}", def),
4453 if let Some((variant, did, substs)) = variant {
4454 debug!("check_struct_path: did={:?} substs={:?}", did, substs);
4455 self.write_user_type_annotation_from_substs(hir_id, did, substs, None);
4457 // Check bounds on type arguments used in the path.
4458 let (bounds, _) = self.instantiate_bounds(path_span, did, substs);
4460 traits::ObligationCause::new(path_span, self.body_id, traits::ItemObligation(did));
4461 self.add_obligations_for_parameters(cause, bounds);
4469 "expected struct, variant or union type, found {}",
4470 ty.sort_string(self.tcx)
4472 .span_label(path_span, "not a struct")
4478 // Finish resolving a path in a struct expression or pattern `S::A { .. }` if necessary.
4479 // The newly resolved definition is written into `type_dependent_defs`.
4480 fn finish_resolving_struct_path(
4485 ) -> (Res, Ty<'tcx>) {
4487 QPath::Resolved(ref maybe_qself, ref path) => {
4488 let self_ty = maybe_qself.as_ref().map(|qself| self.to_ty(qself));
4489 let ty = AstConv::res_to_ty(self, self_ty, path, true);
4492 QPath::TypeRelative(ref qself, ref segment) => {
4493 let ty = self.to_ty(qself);
4495 let res = if let hir::TyKind::Path(QPath::Resolved(_, ref path)) = qself.kind {
4501 AstConv::associated_path_to_ty(self, hir_id, path_span, ty, res, segment, true);
4502 let ty = result.map(|(ty, _, _)| ty).unwrap_or_else(|_| self.tcx().ty_error());
4503 let result = result.map(|(_, kind, def_id)| (kind, def_id));
4505 // Write back the new resolution.
4506 self.write_resolution(hir_id, result);
4508 (result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err), ty)
4510 QPath::LangItem(lang_item, span) => {
4511 self.resolve_lang_item_path(lang_item, span, hir_id)
4516 fn resolve_lang_item_path(
4518 lang_item: hir::LangItem,
4521 ) -> (Res, Ty<'tcx>) {
4522 let def_id = self.tcx.require_lang_item(lang_item, Some(span));
4523 let def_kind = self.tcx.def_kind(def_id);
4525 let item_ty = if let DefKind::Variant = def_kind {
4526 self.tcx.type_of(self.tcx.parent(def_id).expect("variant w/out parent"))
4528 self.tcx.type_of(def_id)
4530 let substs = self.infcx.fresh_substs_for_item(span, def_id);
4531 let ty = item_ty.subst(self.tcx, substs);
4533 self.write_resolution(hir_id, Ok((def_kind, def_id)));
4534 self.add_required_obligations(span, def_id, &substs);
4535 (Res::Def(def_kind, def_id), ty)
4538 /// Resolves an associated value path into a base type and associated constant, or method
4539 /// resolution. The newly resolved definition is written into `type_dependent_defs`.
4540 pub fn resolve_ty_and_res_ufcs<'b>(
4542 qpath: &'b QPath<'b>,
4545 ) -> (Res, Option<Ty<'tcx>>, &'b [hir::PathSegment<'b>]) {
4546 debug!("resolve_ty_and_res_ufcs: qpath={:?} hir_id={:?} span={:?}", qpath, hir_id, span);
4547 let (ty, qself, item_segment) = match *qpath {
4548 QPath::Resolved(ref opt_qself, ref path) => {
4551 opt_qself.as_ref().map(|qself| self.to_ty(qself)),
4555 QPath::TypeRelative(ref qself, ref segment) => (self.to_ty(qself), qself, segment),
4556 QPath::LangItem(..) => bug!("`resolve_ty_and_res_ufcs` called on `LangItem`"),
4558 if let Some(&cached_result) = self.typeck_results.borrow().type_dependent_defs().get(hir_id)
4560 // Return directly on cache hit. This is useful to avoid doubly reporting
4561 // errors with default match binding modes. See #44614.
4563 cached_result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err);
4564 return (def, Some(ty), slice::from_ref(&**item_segment));
4566 let item_name = item_segment.ident;
4567 let result = self.resolve_ufcs(span, item_name, ty, hir_id).or_else(|error| {
4568 let result = match error {
4569 method::MethodError::PrivateMatch(kind, def_id, _) => Ok((kind, def_id)),
4570 _ => Err(ErrorReported),
4572 if item_name.name != kw::Invalid {
4573 if let Some(mut e) = self.report_method_error(
4577 SelfSource::QPath(qself),
4587 // Write back the new resolution.
4588 self.write_resolution(hir_id, result);
4590 result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err),
4592 slice::from_ref(&**item_segment),
4596 pub fn check_decl_initializer(
4598 local: &'tcx hir::Local<'tcx>,
4599 init: &'tcx hir::Expr<'tcx>,
4601 // FIXME(tschottdorf): `contains_explicit_ref_binding()` must be removed
4602 // for #42640 (default match binding modes).
4605 let ref_bindings = local.pat.contains_explicit_ref_binding();
4607 let local_ty = self.local_ty(init.span, local.hir_id).revealed_ty;
4608 if let Some(m) = ref_bindings {
4609 // Somewhat subtle: if we have a `ref` binding in the pattern,
4610 // we want to avoid introducing coercions for the RHS. This is
4611 // both because it helps preserve sanity and, in the case of
4612 // ref mut, for soundness (issue #23116). In particular, in
4613 // the latter case, we need to be clear that the type of the
4614 // referent for the reference that results is *equal to* the
4615 // type of the place it is referencing, and not some
4616 // supertype thereof.
4617 let init_ty = self.check_expr_with_needs(init, Needs::maybe_mut_place(m));
4618 self.demand_eqtype(init.span, local_ty, init_ty);
4621 self.check_expr_coercable_to_type(init, local_ty, None)
4625 /// Type check a `let` statement.
4626 pub fn check_decl_local(&self, local: &'tcx hir::Local<'tcx>) {
4627 // Determine and write the type which we'll check the pattern against.
4628 let ty = self.local_ty(local.span, local.hir_id).decl_ty;
4629 self.write_ty(local.hir_id, ty);
4631 // Type check the initializer.
4632 if let Some(ref init) = local.init {
4633 let init_ty = self.check_decl_initializer(local, &init);
4634 self.overwrite_local_ty_if_err(local, ty, init_ty);
4637 // Does the expected pattern type originate from an expression and what is the span?
4638 let (origin_expr, ty_span) = match (local.ty, local.init) {
4639 (Some(ty), _) => (false, Some(ty.span)), // Bias towards the explicit user type.
4640 (_, Some(init)) => (true, Some(init.span)), // No explicit type; so use the scrutinee.
4641 _ => (false, None), // We have `let $pat;`, so the expected type is unconstrained.
4644 // Type check the pattern. Override if necessary to avoid knock-on errors.
4645 self.check_pat_top(&local.pat, ty, ty_span, origin_expr);
4646 let pat_ty = self.node_ty(local.pat.hir_id);
4647 self.overwrite_local_ty_if_err(local, ty, pat_ty);
4650 fn overwrite_local_ty_if_err(
4652 local: &'tcx hir::Local<'tcx>,
4656 if ty.references_error() {
4657 // Override the types everywhere with `err()` to avoid knock on errors.
4658 self.write_ty(local.hir_id, ty);
4659 self.write_ty(local.pat.hir_id, ty);
4660 let local_ty = LocalTy { decl_ty, revealed_ty: ty };
4661 self.locals.borrow_mut().insert(local.hir_id, local_ty);
4662 self.locals.borrow_mut().insert(local.pat.hir_id, local_ty);
4666 fn suggest_semicolon_at_end(&self, span: Span, err: &mut DiagnosticBuilder<'_>) {
4667 err.span_suggestion_short(
4668 span.shrink_to_hi(),
4669 "consider using a semicolon here",
4671 Applicability::MachineApplicable,
4675 pub fn check_stmt(&self, stmt: &'tcx hir::Stmt<'tcx>) {
4676 // Don't do all the complex logic below for `DeclItem`.
4678 hir::StmtKind::Item(..) => return,
4679 hir::StmtKind::Local(..) | hir::StmtKind::Expr(..) | hir::StmtKind::Semi(..) => {}
4682 self.warn_if_unreachable(stmt.hir_id, stmt.span, "statement");
4684 // Hide the outer diverging and `has_errors` flags.
4685 let old_diverges = self.diverges.replace(Diverges::Maybe);
4686 let old_has_errors = self.has_errors.replace(false);
4689 hir::StmtKind::Local(ref l) => {
4690 self.check_decl_local(&l);
4693 hir::StmtKind::Item(_) => {}
4694 hir::StmtKind::Expr(ref expr) => {
4695 // Check with expected type of `()`.
4696 self.check_expr_has_type_or_error(&expr, self.tcx.mk_unit(), |err| {
4697 self.suggest_semicolon_at_end(expr.span, err);
4700 hir::StmtKind::Semi(ref expr) => {
4701 self.check_expr(&expr);
4705 // Combine the diverging and `has_error` flags.
4706 self.diverges.set(self.diverges.get() | old_diverges);
4707 self.has_errors.set(self.has_errors.get() | old_has_errors);
4710 pub fn check_block_no_value(&self, blk: &'tcx hir::Block<'tcx>) {
4711 let unit = self.tcx.mk_unit();
4712 let ty = self.check_block_with_expected(blk, ExpectHasType(unit));
4714 // if the block produces a `!` value, that can always be
4715 // (effectively) coerced to unit.
4717 self.demand_suptype(blk.span, unit, ty);
4721 /// If `expr` is a `match` expression that has only one non-`!` arm, use that arm's tail
4722 /// expression's `Span`, otherwise return `expr.span`. This is done to give better errors
4723 /// when given code like the following:
4725 /// if false { return 0i32; } else { 1u32 }
4726 /// // ^^^^ point at this instead of the whole `if` expression
4728 fn get_expr_coercion_span(&self, expr: &hir::Expr<'_>) -> rustc_span::Span {
4729 if let hir::ExprKind::Match(_, arms, _) = &expr.kind {
4730 let arm_spans: Vec<Span> = arms
4733 self.in_progress_typeck_results
4734 .and_then(|typeck_results| {
4735 typeck_results.borrow().node_type_opt(arm.body.hir_id)
4737 .and_then(|arm_ty| {
4738 if arm_ty.is_never() {
4741 Some(match &arm.body.kind {
4742 // Point at the tail expression when possible.
4743 hir::ExprKind::Block(block, _) => {
4744 block.expr.as_ref().map(|e| e.span).unwrap_or(block.span)
4752 if arm_spans.len() == 1 {
4753 return arm_spans[0];
4759 fn check_block_with_expected(
4761 blk: &'tcx hir::Block<'tcx>,
4762 expected: Expectation<'tcx>,
4765 let mut fcx_ps = self.ps.borrow_mut();
4766 let unsafety_state = fcx_ps.recurse(blk);
4767 replace(&mut *fcx_ps, unsafety_state)
4770 // In some cases, blocks have just one exit, but other blocks
4771 // can be targeted by multiple breaks. This can happen both
4772 // with labeled blocks as well as when we desugar
4773 // a `try { ... }` expression.
4777 // 'a: { if true { break 'a Err(()); } Ok(()) }
4779 // Here we would wind up with two coercions, one from
4780 // `Err(())` and the other from the tail expression
4781 // `Ok(())`. If the tail expression is omitted, that's a
4782 // "forced unit" -- unless the block diverges, in which
4783 // case we can ignore the tail expression (e.g., `'a: {
4784 // break 'a 22; }` would not force the type of the block
4786 let tail_expr = blk.expr.as_ref();
4787 let coerce_to_ty = expected.coercion_target_type(self, blk.span);
4788 let coerce = if blk.targeted_by_break {
4789 CoerceMany::new(coerce_to_ty)
4791 let tail_expr: &[&hir::Expr<'_>] = match tail_expr {
4792 Some(e) => slice::from_ref(e),
4795 CoerceMany::with_coercion_sites(coerce_to_ty, tail_expr)
4798 let prev_diverges = self.diverges.get();
4799 let ctxt = BreakableCtxt { coerce: Some(coerce), may_break: false };
4801 let (ctxt, ()) = self.with_breakable_ctxt(blk.hir_id, ctxt, || {
4802 for s in blk.stmts {
4806 // check the tail expression **without** holding the
4807 // `enclosing_breakables` lock below.
4808 let tail_expr_ty = tail_expr.map(|t| self.check_expr_with_expectation(t, expected));
4810 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4811 let ctxt = enclosing_breakables.find_breakable(blk.hir_id);
4812 let coerce = ctxt.coerce.as_mut().unwrap();
4813 if let Some(tail_expr_ty) = tail_expr_ty {
4814 let tail_expr = tail_expr.unwrap();
4815 let span = self.get_expr_coercion_span(tail_expr);
4816 let cause = self.cause(span, ObligationCauseCode::BlockTailExpression(blk.hir_id));
4817 coerce.coerce(self, &cause, tail_expr, tail_expr_ty);
4819 // Subtle: if there is no explicit tail expression,
4820 // that is typically equivalent to a tail expression
4821 // of `()` -- except if the block diverges. In that
4822 // case, there is no value supplied from the tail
4823 // expression (assuming there are no other breaks,
4824 // this implies that the type of the block will be
4827 // #41425 -- label the implicit `()` as being the
4828 // "found type" here, rather than the "expected type".
4829 if !self.diverges.get().is_always() {
4830 // #50009 -- Do not point at the entire fn block span, point at the return type
4831 // span, as it is the cause of the requirement, and
4832 // `consider_hint_about_removing_semicolon` will point at the last expression
4833 // if it were a relevant part of the error. This improves usability in editors
4834 // that highlight errors inline.
4835 let mut sp = blk.span;
4836 let mut fn_span = None;
4837 if let Some((decl, ident)) = self.get_parent_fn_decl(blk.hir_id) {
4838 let ret_sp = decl.output.span();
4839 if let Some(block_sp) = self.parent_item_span(blk.hir_id) {
4840 // HACK: on some cases (`ui/liveness/liveness-issue-2163.rs`) the
4841 // output would otherwise be incorrect and even misleading. Make sure
4842 // the span we're aiming at correspond to a `fn` body.
4843 if block_sp == blk.span {
4845 fn_span = Some(ident.span);
4849 coerce.coerce_forced_unit(
4853 if let Some(expected_ty) = expected.only_has_type(self) {
4854 self.consider_hint_about_removing_semicolon(blk, expected_ty, err);
4856 if let Some(fn_span) = fn_span {
4859 "implicitly returns `()` as its body has no tail or `return` \
4871 // If we can break from the block, then the block's exit is always reachable
4872 // (... as long as the entry is reachable) - regardless of the tail of the block.
4873 self.diverges.set(prev_diverges);
4876 let mut ty = ctxt.coerce.unwrap().complete(self);
4878 if self.has_errors.get() || ty.references_error() {
4879 ty = self.tcx.ty_error()
4882 self.write_ty(blk.hir_id, ty);
4884 *self.ps.borrow_mut() = prev;
4888 fn parent_item_span(&self, id: hir::HirId) -> Option<Span> {
4889 let node = self.tcx.hir().get(self.tcx.hir().get_parent_item(id));
4891 Node::Item(&hir::Item { kind: hir::ItemKind::Fn(_, _, body_id), .. })
4892 | Node::ImplItem(&hir::ImplItem { kind: hir::ImplItemKind::Fn(_, body_id), .. }) => {
4893 let body = self.tcx.hir().body(body_id);
4894 if let ExprKind::Block(block, _) = &body.value.kind {
4895 return Some(block.span);
4903 /// Given a function block's `HirId`, returns its `FnDecl` if it exists, or `None` otherwise.
4904 fn get_parent_fn_decl(&self, blk_id: hir::HirId) -> Option<(&'tcx hir::FnDecl<'tcx>, Ident)> {
4905 let parent = self.tcx.hir().get(self.tcx.hir().get_parent_item(blk_id));
4906 self.get_node_fn_decl(parent).map(|(fn_decl, ident, _)| (fn_decl, ident))
4909 /// Given a function `Node`, return its `FnDecl` if it exists, or `None` otherwise.
4910 fn get_node_fn_decl(&self, node: Node<'tcx>) -> Option<(&'tcx hir::FnDecl<'tcx>, Ident, bool)> {
4912 Node::Item(&hir::Item { ident, kind: hir::ItemKind::Fn(ref sig, ..), .. }) => {
4913 // This is less than ideal, it will not suggest a return type span on any
4914 // method called `main`, regardless of whether it is actually the entry point,
4915 // but it will still present it as the reason for the expected type.
4916 Some((&sig.decl, ident, ident.name != sym::main))
4918 Node::TraitItem(&hir::TraitItem {
4920 kind: hir::TraitItemKind::Fn(ref sig, ..),
4922 }) => Some((&sig.decl, ident, true)),
4923 Node::ImplItem(&hir::ImplItem {
4925 kind: hir::ImplItemKind::Fn(ref sig, ..),
4927 }) => Some((&sig.decl, ident, false)),
4932 /// Given a `HirId`, return the `FnDecl` of the method it is enclosed by and whether a
4933 /// suggestion can be made, `None` otherwise.
4934 pub fn get_fn_decl(&self, blk_id: hir::HirId) -> Option<(&'tcx hir::FnDecl<'tcx>, bool)> {
4935 // Get enclosing Fn, if it is a function or a trait method, unless there's a `loop` or
4936 // `while` before reaching it, as block tail returns are not available in them.
4937 self.tcx.hir().get_return_block(blk_id).and_then(|blk_id| {
4938 let parent = self.tcx.hir().get(blk_id);
4939 self.get_node_fn_decl(parent).map(|(fn_decl, _, is_main)| (fn_decl, is_main))
4943 /// On implicit return expressions with mismatched types, provides the following suggestions:
4945 /// - Points out the method's return type as the reason for the expected type.
4946 /// - Possible missing semicolon.
4947 /// - Possible missing return type if the return type is the default, and not `fn main()`.
4948 pub fn suggest_mismatched_types_on_tail(
4950 err: &mut DiagnosticBuilder<'_>,
4951 expr: &'tcx hir::Expr<'tcx>,
4957 let expr = expr.peel_drop_temps();
4958 self.suggest_missing_semicolon(err, expr, expected, cause_span);
4959 let mut pointing_at_return_type = false;
4960 if let Some((fn_decl, can_suggest)) = self.get_fn_decl(blk_id) {
4961 pointing_at_return_type =
4962 self.suggest_missing_return_type(err, &fn_decl, expected, found, can_suggest);
4964 pointing_at_return_type
4967 /// When encountering an fn-like ctor that needs to unify with a value, check whether calling
4968 /// the ctor would successfully solve the type mismatch and if so, suggest it:
4970 /// fn foo(x: usize) -> usize { x }
4971 /// let x: usize = foo; // suggest calling the `foo` function: `foo(42)`
4975 err: &mut DiagnosticBuilder<'_>,
4976 expr: &hir::Expr<'_>,
4980 let hir = self.tcx.hir();
4981 let (def_id, sig) = match found.kind {
4982 ty::FnDef(def_id, _) => (def_id, found.fn_sig(self.tcx)),
4983 ty::Closure(def_id, substs) => (def_id, substs.as_closure().sig()),
4987 let sig = self.replace_bound_vars_with_fresh_vars(expr.span, infer::FnCall, &sig).0;
4988 let sig = self.normalize_associated_types_in(expr.span, &sig);
4989 if self.can_coerce(sig.output(), expected) {
4990 let (mut sugg_call, applicability) = if sig.inputs().is_empty() {
4991 (String::new(), Applicability::MachineApplicable)
4993 ("...".to_string(), Applicability::HasPlaceholders)
4995 let mut msg = "call this function";
4996 match hir.get_if_local(def_id) {
4998 Node::Item(hir::Item { kind: ItemKind::Fn(.., body_id), .. })
4999 | Node::ImplItem(hir::ImplItem {
5000 kind: hir::ImplItemKind::Fn(_, body_id), ..
5002 | Node::TraitItem(hir::TraitItem {
5003 kind: hir::TraitItemKind::Fn(.., hir::TraitFn::Provided(body_id)),
5007 let body = hir.body(*body_id);
5011 .map(|param| match ¶m.pat.kind {
5012 hir::PatKind::Binding(_, _, ident, None)
5013 if ident.name != kw::SelfLower =>
5017 _ => "_".to_string(),
5019 .collect::<Vec<_>>()
5022 Some(Node::Expr(hir::Expr {
5023 kind: ExprKind::Closure(_, _, body_id, _, _),
5024 span: full_closure_span,
5027 if *full_closure_span == expr.span {
5030 msg = "call this closure";
5031 let body = hir.body(*body_id);
5035 .map(|param| match ¶m.pat.kind {
5036 hir::PatKind::Binding(_, _, ident, None)
5037 if ident.name != kw::SelfLower =>
5041 _ => "_".to_string(),
5043 .collect::<Vec<_>>()
5046 Some(Node::Ctor(hir::VariantData::Tuple(fields, _))) => {
5047 sugg_call = fields.iter().map(|_| "_").collect::<Vec<_>>().join(", ");
5048 match def_id.as_local().map(|def_id| hir.def_kind(def_id)) {
5049 Some(DefKind::Ctor(hir::def::CtorOf::Variant, _)) => {
5050 msg = "instantiate this tuple variant";
5052 Some(DefKind::Ctor(CtorOf::Struct, _)) => {
5053 msg = "instantiate this tuple struct";
5058 Some(Node::ForeignItem(hir::ForeignItem {
5059 kind: hir::ForeignItemKind::Fn(_, idents, _),
5065 if ident.name != kw::SelfLower {
5071 .collect::<Vec<_>>()
5074 Some(Node::TraitItem(hir::TraitItem {
5075 kind: hir::TraitItemKind::Fn(.., hir::TraitFn::Required(idents)),
5081 if ident.name != kw::SelfLower {
5087 .collect::<Vec<_>>()
5092 err.span_suggestion_verbose(
5093 expr.span.shrink_to_hi(),
5094 &format!("use parentheses to {}", msg),
5095 format!("({})", sugg_call),
5103 pub fn suggest_deref_ref_or_into(
5105 err: &mut DiagnosticBuilder<'_>,
5106 expr: &hir::Expr<'_>,
5109 expected_ty_expr: Option<&'tcx hir::Expr<'tcx>>,
5111 if let Some((sp, msg, suggestion, applicability)) = self.check_ref(expr, found, expected) {
5112 err.span_suggestion(sp, msg, suggestion, applicability);
5113 } else if let (ty::FnDef(def_id, ..), true) =
5114 (&found.kind, self.suggest_fn_call(err, expr, expected, found))
5116 if let Some(sp) = self.tcx.hir().span_if_local(*def_id) {
5117 let sp = self.sess().source_map().guess_head_span(sp);
5118 err.span_label(sp, &format!("{} defined here", found));
5120 } else if !self.check_for_cast(err, expr, found, expected, expected_ty_expr) {
5121 let is_struct_pat_shorthand_field =
5122 self.is_hir_id_from_struct_pattern_shorthand_field(expr.hir_id, expr.span);
5123 let methods = self.get_conversion_methods(expr.span, expected, found, expr.hir_id);
5124 if let Ok(expr_text) = self.sess().source_map().span_to_snippet(expr.span) {
5125 let mut suggestions = iter::repeat(&expr_text)
5126 .zip(methods.iter())
5127 .filter_map(|(receiver, method)| {
5128 let method_call = format!(".{}()", method.ident);
5129 if receiver.ends_with(&method_call) {
5130 None // do not suggest code that is already there (#53348)
5132 let method_call_list = [".to_vec()", ".to_string()"];
5133 let sugg = if receiver.ends_with(".clone()")
5134 && method_call_list.contains(&method_call.as_str())
5136 let max_len = receiver.rfind('.').unwrap();
5137 format!("{}{}", &receiver[..max_len], method_call)
5139 if expr.precedence().order() < ExprPrecedence::MethodCall.order() {
5140 format!("({}){}", receiver, method_call)
5142 format!("{}{}", receiver, method_call)
5145 Some(if is_struct_pat_shorthand_field {
5146 format!("{}: {}", receiver, sugg)
5153 if suggestions.peek().is_some() {
5154 err.span_suggestions(
5156 "try using a conversion method",
5158 Applicability::MaybeIncorrect,
5165 /// When encountering the expected boxed value allocated in the stack, suggest allocating it
5166 /// in the heap by calling `Box::new()`.
5167 fn suggest_boxing_when_appropriate(
5169 err: &mut DiagnosticBuilder<'_>,
5170 expr: &hir::Expr<'_>,
5174 if self.tcx.hir().is_inside_const_context(expr.hir_id) {
5175 // Do not suggest `Box::new` in const context.
5178 if !expected.is_box() || found.is_box() {
5181 let boxed_found = self.tcx.mk_box(found);
5182 if let (true, Ok(snippet)) = (
5183 self.can_coerce(boxed_found, expected),
5184 self.sess().source_map().span_to_snippet(expr.span),
5186 err.span_suggestion(
5188 "store this in the heap by calling `Box::new`",
5189 format!("Box::new({})", snippet),
5190 Applicability::MachineApplicable,
5193 "for more on the distinction between the stack and the heap, read \
5194 https://doc.rust-lang.org/book/ch15-01-box.html, \
5195 https://doc.rust-lang.org/rust-by-example/std/box.html, and \
5196 https://doc.rust-lang.org/std/boxed/index.html",
5201 fn note_internal_mutation_in_method(
5203 err: &mut DiagnosticBuilder<'_>,
5204 expr: &hir::Expr<'_>,
5208 if found != self.tcx.types.unit {
5211 if let ExprKind::MethodCall(path_segment, _, [rcvr, ..], _) = expr.kind {
5215 .expr_ty_adjusted_opt(rcvr)
5216 .map_or(true, |ty| expected.peel_refs() != ty.peel_refs())
5220 let mut sp = MultiSpan::from_span(path_segment.ident.span);
5222 path_segment.ident.span,
5224 "this call modifies {} in-place",
5226 ExprKind::Path(QPath::Resolved(
5228 hir::Path { segments: [segment], .. },
5229 )) => format!("`{}`", segment.ident),
5230 _ => "its receiver".to_string(),
5236 "you probably want to use this value after calling the method...".to_string(),
5240 &format!("method `{}` modifies its receiver in-place", path_segment.ident),
5242 err.note(&format!("...instead of the `()` output of method `{}`", path_segment.ident));
5246 /// When encountering an `impl Future` where `BoxFuture` is expected, suggest `Box::pin`.
5247 fn suggest_calling_boxed_future_when_appropriate(
5249 err: &mut DiagnosticBuilder<'_>,
5250 expr: &hir::Expr<'_>,
5256 if self.tcx.hir().is_inside_const_context(expr.hir_id) {
5257 // Do not suggest `Box::new` in const context.
5260 let pin_did = self.tcx.lang_items().pin_type();
5261 match expected.kind {
5262 ty::Adt(def, _) if Some(def.did) != pin_did => return false,
5263 // This guards the `unwrap` and `mk_box` below.
5264 _ if pin_did.is_none() || self.tcx.lang_items().owned_box().is_none() => return false,
5267 let boxed_found = self.tcx.mk_box(found);
5268 let new_found = self.tcx.mk_lang_item(boxed_found, PinTypeLangItem).unwrap();
5269 if let (true, Ok(snippet)) = (
5270 self.can_coerce(new_found, expected),
5271 self.sess().source_map().span_to_snippet(expr.span),
5274 ty::Adt(def, _) if def.is_box() => {
5275 err.help("use `Box::pin`");
5278 err.span_suggestion(
5280 "you need to pin and box this expression",
5281 format!("Box::pin({})", snippet),
5282 Applicability::MachineApplicable,
5292 /// A common error is to forget to add a semicolon at the end of a block, e.g.,
5296 /// bar_that_returns_u32()
5300 /// This routine checks if the return expression in a block would make sense on its own as a
5301 /// statement and the return type has been left as default or has been specified as `()`. If so,
5302 /// it suggests adding a semicolon.
5303 fn suggest_missing_semicolon(
5305 err: &mut DiagnosticBuilder<'_>,
5306 expression: &'tcx hir::Expr<'tcx>,
5310 if expected.is_unit() {
5311 // `BlockTailExpression` only relevant if the tail expr would be
5312 // useful on its own.
5313 match expression.kind {
5315 | ExprKind::MethodCall(..)
5316 | ExprKind::Loop(..)
5317 | ExprKind::Match(..)
5318 | ExprKind::Block(..) => {
5319 err.span_suggestion(
5320 cause_span.shrink_to_hi(),
5321 "try adding a semicolon",
5323 Applicability::MachineApplicable,
5331 /// A possible error is to forget to add a return type that is needed:
5335 /// bar_that_returns_u32()
5339 /// This routine checks if the return type is left as default, the method is not part of an
5340 /// `impl` block and that it isn't the `main` method. If so, it suggests setting the return
5342 fn suggest_missing_return_type(
5344 err: &mut DiagnosticBuilder<'_>,
5345 fn_decl: &hir::FnDecl<'_>,
5350 // Only suggest changing the return type for methods that
5351 // haven't set a return type at all (and aren't `fn main()` or an impl).
5352 match (&fn_decl.output, found.is_suggestable(), can_suggest, expected.is_unit()) {
5353 (&hir::FnRetTy::DefaultReturn(span), true, true, true) => {
5354 err.span_suggestion(
5356 "try adding a return type",
5357 format!("-> {} ", self.resolve_vars_with_obligations(found)),
5358 Applicability::MachineApplicable,
5362 (&hir::FnRetTy::DefaultReturn(span), false, true, true) => {
5363 err.span_label(span, "possibly return type missing here?");
5366 (&hir::FnRetTy::DefaultReturn(span), _, false, true) => {
5367 // `fn main()` must return `()`, do not suggest changing return type
5368 err.span_label(span, "expected `()` because of default return type");
5371 // expectation was caused by something else, not the default return
5372 (&hir::FnRetTy::DefaultReturn(_), _, _, false) => false,
5373 (&hir::FnRetTy::Return(ref ty), _, _, _) => {
5374 // Only point to return type if the expected type is the return type, as if they
5375 // are not, the expectation must have been caused by something else.
5376 debug!("suggest_missing_return_type: return type {:?} node {:?}", ty, ty.kind);
5378 let ty = AstConv::ast_ty_to_ty(self, ty);
5379 debug!("suggest_missing_return_type: return type {:?}", ty);
5380 debug!("suggest_missing_return_type: expected type {:?}", ty);
5381 if ty.kind == expected.kind {
5382 err.span_label(sp, format!("expected `{}` because of return type", expected));
5390 /// A possible error is to forget to add `.await` when using futures:
5393 /// async fn make_u32() -> u32 {
5397 /// fn take_u32(x: u32) {}
5399 /// async fn foo() {
5400 /// let x = make_u32();
5405 /// This routine checks if the found type `T` implements `Future<Output=U>` where `U` is the
5406 /// expected type. If this is the case, and we are inside of an async body, it suggests adding
5407 /// `.await` to the tail of the expression.
5408 fn suggest_missing_await(
5410 err: &mut DiagnosticBuilder<'_>,
5411 expr: &hir::Expr<'_>,
5415 debug!("suggest_missing_await: expr={:?} expected={:?}, found={:?}", expr, expected, found);
5416 // `.await` is not permitted outside of `async` bodies, so don't bother to suggest if the
5417 // body isn't `async`.
5418 let item_id = self.tcx().hir().get_parent_node(self.body_id);
5419 if let Some(body_id) = self.tcx().hir().maybe_body_owned_by(item_id) {
5420 let body = self.tcx().hir().body(body_id);
5421 if let Some(hir::GeneratorKind::Async(_)) = body.generator_kind {
5423 // Check for `Future` implementations by constructing a predicate to
5424 // prove: `<T as Future>::Output == U`
5425 let future_trait = self.tcx.require_lang_item(FutureTraitLangItem, Some(sp));
5426 let item_def_id = self
5428 .associated_items(future_trait)
5429 .in_definition_order()
5433 // `<T as Future>::Output`
5434 let projection_ty = ty::ProjectionTy {
5438 .mk_substs_trait(found, self.fresh_substs_for_item(sp, item_def_id)),
5443 let predicate = ty::PredicateAtom::Projection(ty::ProjectionPredicate {
5447 .potentially_quantified(self.tcx, ty::PredicateKind::ForAll);
5448 let obligation = traits::Obligation::new(self.misc(sp), self.param_env, predicate);
5450 debug!("suggest_missing_await: trying obligation {:?}", obligation);
5452 if self.infcx.predicate_may_hold(&obligation) {
5453 debug!("suggest_missing_await: obligation held: {:?}", obligation);
5454 if let Ok(code) = self.sess().source_map().span_to_snippet(sp) {
5455 err.span_suggestion(
5457 "consider using `.await` here",
5458 format!("{}.await", code),
5459 Applicability::MaybeIncorrect,
5462 debug!("suggest_missing_await: no snippet for {:?}", sp);
5465 debug!("suggest_missing_await: obligation did not hold: {:?}", obligation)
5471 fn suggest_missing_parentheses(&self, err: &mut DiagnosticBuilder<'_>, expr: &hir::Expr<'_>) {
5472 let sp = self.tcx.sess.source_map().start_point(expr.span);
5473 if let Some(sp) = self.tcx.sess.parse_sess.ambiguous_block_expr_parse.borrow().get(&sp) {
5474 // `{ 42 } &&x` (#61475) or `{ 42 } && if x { 1 } else { 0 }`
5475 self.tcx.sess.parse_sess.expr_parentheses_needed(err, *sp, None);
5479 fn note_need_for_fn_pointer(
5481 err: &mut DiagnosticBuilder<'_>,
5485 let (sig, did, substs) = match (&expected.kind, &found.kind) {
5486 (ty::FnDef(did1, substs1), ty::FnDef(did2, substs2)) => {
5487 let sig1 = self.tcx.fn_sig(*did1).subst(self.tcx, substs1);
5488 let sig2 = self.tcx.fn_sig(*did2).subst(self.tcx, substs2);
5493 "different `fn` items always have unique types, even if their signatures are \
5496 (sig1, *did1, substs1)
5498 (ty::FnDef(did, substs), ty::FnPtr(sig2)) => {
5499 let sig1 = self.tcx.fn_sig(*did).subst(self.tcx, substs);
5503 (sig1, *did, substs)
5507 err.help(&format!("change the expected type to be function pointer `{}`", sig));
5509 "if the expected type is due to type inference, cast the expected `fn` to a function \
5510 pointer: `{} as {}`",
5511 self.tcx.def_path_str_with_substs(did, substs),
5516 /// A common error is to add an extra semicolon:
5519 /// fn foo() -> usize {
5524 /// This routine checks if the final statement in a block is an
5525 /// expression with an explicit semicolon whose type is compatible
5526 /// with `expected_ty`. If so, it suggests removing the semicolon.
5527 fn consider_hint_about_removing_semicolon(
5529 blk: &'tcx hir::Block<'tcx>,
5530 expected_ty: Ty<'tcx>,
5531 err: &mut DiagnosticBuilder<'_>,
5533 if let Some(span_semi) = self.could_remove_semicolon(blk, expected_ty) {
5534 err.span_suggestion(
5536 "consider removing this semicolon",
5538 Applicability::MachineApplicable,
5543 fn could_remove_semicolon(
5545 blk: &'tcx hir::Block<'tcx>,
5546 expected_ty: Ty<'tcx>,
5548 // Be helpful when the user wrote `{... expr;}` and
5549 // taking the `;` off is enough to fix the error.
5550 let last_stmt = blk.stmts.last()?;
5551 let last_expr = match last_stmt.kind {
5552 hir::StmtKind::Semi(ref e) => e,
5555 let last_expr_ty = self.node_ty(last_expr.hir_id);
5556 if matches!(last_expr_ty.kind, ty::Error(_))
5557 || self.can_sub(self.param_env, last_expr_ty, expected_ty).is_err()
5561 let original_span = original_sp(last_stmt.span, blk.span);
5562 Some(original_span.with_lo(original_span.hi() - BytePos(1)))
5565 // Instantiates the given path, which must refer to an item with the given
5566 // number of type parameters and type.
5567 pub fn instantiate_value_path(
5569 segments: &[hir::PathSegment<'_>],
5570 self_ty: Option<Ty<'tcx>>,
5574 ) -> (Ty<'tcx>, Res) {
5576 "instantiate_value_path(segments={:?}, self_ty={:?}, res={:?}, hir_id={})",
5577 segments, self_ty, res, hir_id,
5582 let path_segs = match res {
5583 Res::Local(_) | Res::SelfCtor(_) => vec![],
5584 Res::Def(kind, def_id) => {
5585 AstConv::def_ids_for_value_path_segments(self, segments, self_ty, kind, def_id)
5587 _ => bug!("instantiate_value_path on {:?}", res),
5590 let mut user_self_ty = None;
5591 let mut is_alias_variant_ctor = false;
5593 Res::Def(DefKind::Ctor(CtorOf::Variant, _), _) => {
5594 if let Some(self_ty) = self_ty {
5595 let adt_def = self_ty.ty_adt_def().unwrap();
5596 user_self_ty = Some(UserSelfTy { impl_def_id: adt_def.did, self_ty });
5597 is_alias_variant_ctor = true;
5600 Res::Def(DefKind::AssocFn | DefKind::AssocConst, def_id) => {
5601 let container = tcx.associated_item(def_id).container;
5602 debug!("instantiate_value_path: def_id={:?} container={:?}", def_id, container);
5604 ty::TraitContainer(trait_did) => {
5605 callee::check_legal_trait_for_method_call(tcx, span, None, trait_did)
5607 ty::ImplContainer(impl_def_id) => {
5608 if segments.len() == 1 {
5609 // `<T>::assoc` will end up here, and so
5610 // can `T::assoc`. It this came from an
5611 // inherent impl, we need to record the
5612 // `T` for posterity (see `UserSelfTy` for
5614 let self_ty = self_ty.expect("UFCS sugared assoc missing Self");
5615 user_self_ty = Some(UserSelfTy { impl_def_id, self_ty });
5623 // Now that we have categorized what space the parameters for each
5624 // segment belong to, let's sort out the parameters that the user
5625 // provided (if any) into their appropriate spaces. We'll also report
5626 // errors if type parameters are provided in an inappropriate place.
5628 let generic_segs: FxHashSet<_> = path_segs.iter().map(|PathSeg(_, index)| index).collect();
5629 let generics_has_err = AstConv::prohibit_generics(
5631 segments.iter().enumerate().filter_map(|(index, seg)| {
5632 if !generic_segs.contains(&index) || is_alias_variant_ctor {
5640 if let Res::Local(hid) = res {
5641 let ty = self.local_ty(span, hid).decl_ty;
5642 let ty = self.normalize_associated_types_in(span, &ty);
5643 self.write_ty(hir_id, ty);
5647 if generics_has_err {
5648 // Don't try to infer type parameters when prohibited generic arguments were given.
5649 user_self_ty = None;
5652 // Now we have to compare the types that the user *actually*
5653 // provided against the types that were *expected*. If the user
5654 // did not provide any types, then we want to substitute inference
5655 // variables. If the user provided some types, we may still need
5656 // to add defaults. If the user provided *too many* types, that's
5659 let mut infer_args_for_err = FxHashSet::default();
5660 for &PathSeg(def_id, index) in &path_segs {
5661 let seg = &segments[index];
5662 let generics = tcx.generics_of(def_id);
5663 // Argument-position `impl Trait` is treated as a normal generic
5664 // parameter internally, but we don't allow users to specify the
5665 // parameter's value explicitly, so we have to do some error-
5667 if let GenericArgCountResult {
5668 correct: Err(GenericArgCountMismatch { reported: Some(ErrorReported), .. }),
5670 } = AstConv::check_generic_arg_count_for_call(
5671 tcx, span, &generics, &seg, false, // `is_method_call`
5673 infer_args_for_err.insert(index);
5674 self.set_tainted_by_errors(); // See issue #53251.
5678 let has_self = path_segs
5680 .map(|PathSeg(def_id, _)| tcx.generics_of(*def_id).has_self)
5683 let (res, self_ctor_substs) = if let Res::SelfCtor(impl_def_id) = res {
5684 let ty = self.normalize_ty(span, tcx.at(span).type_of(impl_def_id));
5686 ty::Adt(adt_def, substs) if adt_def.has_ctor() => {
5687 let variant = adt_def.non_enum_variant();
5688 let ctor_def_id = variant.ctor_def_id.unwrap();
5690 Res::Def(DefKind::Ctor(CtorOf::Struct, variant.ctor_kind), ctor_def_id),
5695 let mut err = tcx.sess.struct_span_err(
5697 "the `Self` constructor can only be used with tuple or unit structs",
5699 if let Some(adt_def) = ty.ty_adt_def() {
5700 match adt_def.adt_kind() {
5702 err.help("did you mean to use one of the enum's variants?");
5704 AdtKind::Struct | AdtKind::Union => {
5705 err.span_suggestion(
5707 "use curly brackets",
5708 String::from("Self { /* fields */ }"),
5709 Applicability::HasPlaceholders,
5716 return (tcx.ty_error(), res);
5722 let def_id = res.def_id();
5724 // The things we are substituting into the type should not contain
5725 // escaping late-bound regions, and nor should the base type scheme.
5726 let ty = tcx.type_of(def_id);
5728 let arg_count = GenericArgCountResult {
5729 explicit_late_bound: ExplicitLateBound::No,
5730 correct: if infer_args_for_err.is_empty() {
5733 Err(GenericArgCountMismatch::default())
5737 let substs = self_ctor_substs.unwrap_or_else(|| {
5738 AstConv::create_substs_for_generic_args(
5745 // Provide the generic args, and whether types should be inferred.
5747 if let Some(&PathSeg(_, index)) =
5748 path_segs.iter().find(|&PathSeg(did, _)| *did == def_id)
5750 // If we've encountered an `impl Trait`-related error, we're just
5751 // going to infer the arguments for better error messages.
5752 if !infer_args_for_err.contains(&index) {
5753 // Check whether the user has provided generic arguments.
5754 if let Some(ref data) = segments[index].args {
5755 return (Some(data), segments[index].infer_args);
5758 return (None, segments[index].infer_args);
5763 // Provide substitutions for parameters for which (valid) arguments have been provided.
5764 |param, arg| match (¶m.kind, arg) {
5765 (GenericParamDefKind::Lifetime, GenericArg::Lifetime(lt)) => {
5766 AstConv::ast_region_to_region(self, lt, Some(param)).into()
5768 (GenericParamDefKind::Type { .. }, GenericArg::Type(ty)) => {
5769 self.to_ty(ty).into()
5771 (GenericParamDefKind::Const, GenericArg::Const(ct)) => {
5772 self.const_arg_to_const(&ct.value, param.def_id).into()
5774 _ => unreachable!(),
5776 // Provide substitutions for parameters for which arguments are inferred.
5777 |substs, param, infer_args| {
5779 GenericParamDefKind::Lifetime => {
5780 self.re_infer(Some(param), span).unwrap().into()
5782 GenericParamDefKind::Type { has_default, .. } => {
5783 if !infer_args && has_default {
5784 // If we have a default, then we it doesn't matter that we're not
5785 // inferring the type arguments: we provide the default where any
5787 let default = tcx.type_of(param.def_id);
5790 default.subst_spanned(tcx, substs.unwrap(), Some(span)),
5794 // If no type arguments were provided, we have to infer them.
5795 // This case also occurs as a result of some malformed input, e.g.
5796 // a lifetime argument being given instead of a type parameter.
5797 // Using inference instead of `Error` gives better error messages.
5798 self.var_for_def(span, param)
5801 GenericParamDefKind::Const => {
5802 // FIXME(const_generics:defaults)
5803 // No const parameters were provided, we have to infer them.
5804 self.var_for_def(span, param)
5810 assert!(!substs.has_escaping_bound_vars());
5811 assert!(!ty.has_escaping_bound_vars());
5813 // First, store the "user substs" for later.
5814 self.write_user_type_annotation_from_substs(hir_id, def_id, substs, user_self_ty);
5816 self.add_required_obligations(span, def_id, &substs);
5818 // Substitute the values for the type parameters into the type of
5819 // the referenced item.
5820 let ty_substituted = self.instantiate_type_scheme(span, &substs, &ty);
5822 if let Some(UserSelfTy { impl_def_id, self_ty }) = user_self_ty {
5823 // In the case of `Foo<T>::method` and `<Foo<T>>::method`, if `method`
5824 // is inherent, there is no `Self` parameter; instead, the impl needs
5825 // type parameters, which we can infer by unifying the provided `Self`
5826 // with the substituted impl type.
5827 // This also occurs for an enum variant on a type alias.
5828 let ty = tcx.type_of(impl_def_id);
5830 let impl_ty = self.instantiate_type_scheme(span, &substs, &ty);
5831 match self.at(&self.misc(span), self.param_env).sup(impl_ty, self_ty) {
5832 Ok(ok) => self.register_infer_ok_obligations(ok),
5834 self.tcx.sess.delay_span_bug(
5837 "instantiate_value_path: (UFCS) {:?} was a subtype of {:?} but now is not?",
5846 self.check_rustc_args_require_const(def_id, hir_id, span);
5848 debug!("instantiate_value_path: type of {:?} is {:?}", hir_id, ty_substituted);
5849 self.write_substs(hir_id, substs);
5851 (ty_substituted, res)
5854 /// Add all the obligations that are required, substituting and normalized appropriately.
5855 fn add_required_obligations(&self, span: Span, def_id: DefId, substs: &SubstsRef<'tcx>) {
5856 let (bounds, spans) = self.instantiate_bounds(span, def_id, &substs);
5858 for (i, mut obligation) in traits::predicates_for_generics(
5859 traits::ObligationCause::new(span, self.body_id, traits::ItemObligation(def_id)),
5865 // This makes the error point at the bound, but we want to point at the argument
5866 if let Some(span) = spans.get(i) {
5867 obligation.cause.make_mut().code = traits::BindingObligation(def_id, *span);
5869 self.register_predicate(obligation);
5873 fn check_rustc_args_require_const(&self, def_id: DefId, hir_id: hir::HirId, span: Span) {
5874 // We're only interested in functions tagged with
5875 // #[rustc_args_required_const], so ignore anything that's not.
5876 if !self.tcx.has_attr(def_id, sym::rustc_args_required_const) {
5880 // If our calling expression is indeed the function itself, we're good!
5881 // If not, generate an error that this can only be called directly.
5882 if let Node::Expr(expr) = self.tcx.hir().get(self.tcx.hir().get_parent_node(hir_id)) {
5883 if let ExprKind::Call(ref callee, ..) = expr.kind {
5884 if callee.hir_id == hir_id {
5890 self.tcx.sess.span_err(
5892 "this function can only be invoked directly, not through a function pointer",
5896 /// Resolves `typ` by a single level if `typ` is a type variable.
5897 /// If no resolution is possible, then an error is reported.
5898 /// Numeric inference variables may be left unresolved.
5899 pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
5900 let ty = self.resolve_vars_with_obligations(ty);
5901 if !ty.is_ty_var() {
5904 if !self.is_tainted_by_errors() {
5905 self.need_type_info_err((**self).body_id, sp, ty, E0282)
5906 .note("type must be known at this point")
5909 let err = self.tcx.ty_error();
5910 self.demand_suptype(sp, err, ty);
5915 fn with_breakable_ctxt<F: FnOnce() -> R, R>(
5918 ctxt: BreakableCtxt<'tcx>,
5920 ) -> (BreakableCtxt<'tcx>, R) {
5923 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5924 index = enclosing_breakables.stack.len();
5925 enclosing_breakables.by_id.insert(id, index);
5926 enclosing_breakables.stack.push(ctxt);
5930 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5931 debug_assert!(enclosing_breakables.stack.len() == index + 1);
5932 enclosing_breakables.by_id.remove(&id).expect("missing breakable context");
5933 enclosing_breakables.stack.pop().expect("missing breakable context")
5938 /// Instantiate a QueryResponse in a probe context, without a
5939 /// good ObligationCause.
5940 fn probe_instantiate_query_response(
5943 original_values: &OriginalQueryValues<'tcx>,
5944 query_result: &Canonical<'tcx, QueryResponse<'tcx, Ty<'tcx>>>,
5945 ) -> InferResult<'tcx, Ty<'tcx>> {
5946 self.instantiate_query_response_and_region_obligations(
5947 &traits::ObligationCause::misc(span, self.body_id),
5954 /// Returns `true` if an expression is contained inside the LHS of an assignment expression.
5955 fn expr_in_place(&self, mut expr_id: hir::HirId) -> bool {
5956 let mut contained_in_place = false;
5958 while let hir::Node::Expr(parent_expr) =
5959 self.tcx.hir().get(self.tcx.hir().get_parent_node(expr_id))
5961 match &parent_expr.kind {
5962 hir::ExprKind::Assign(lhs, ..) | hir::ExprKind::AssignOp(_, lhs, ..) => {
5963 if lhs.hir_id == expr_id {
5964 contained_in_place = true;
5970 expr_id = parent_expr.hir_id;
5977 fn check_type_params_are_used<'tcx>(tcx: TyCtxt<'tcx>, generics: &ty::Generics, ty: Ty<'tcx>) {
5978 debug!("check_type_params_are_used(generics={:?}, ty={:?})", generics, ty);
5980 assert_eq!(generics.parent, None);
5982 if generics.own_counts().types == 0 {
5986 let mut params_used = BitSet::new_empty(generics.params.len());
5988 if ty.references_error() {
5989 // If there is already another error, do not emit
5990 // an error for not using a type parameter.
5991 assert!(tcx.sess.has_errors());
5995 for leaf in ty.walk() {
5996 if let GenericArgKind::Type(leaf_ty) = leaf.unpack() {
5997 if let ty::Param(param) = leaf_ty.kind {
5998 debug!("found use of ty param {:?}", param);
5999 params_used.insert(param.index);
6004 for param in &generics.params {
6005 if !params_used.contains(param.index) {
6006 if let ty::GenericParamDefKind::Type { .. } = param.kind {
6007 let span = tcx.def_span(param.def_id);
6012 "type parameter `{}` is unused",
6015 .span_label(span, "unused type parameter")
6022 fn fatally_break_rust(sess: &Session) {
6023 let handler = sess.diagnostic();
6024 handler.span_bug_no_panic(
6026 "It looks like you're trying to break rust; would you like some ICE?",
6028 handler.note_without_error("the compiler expectedly panicked. this is a feature.");
6029 handler.note_without_error(
6030 "we would appreciate a joke overview: \
6031 https://github.com/rust-lang/rust/issues/43162#issuecomment-320764675",
6033 handler.note_without_error(&format!(
6034 "rustc {} running on {}",
6035 option_env!("CFG_VERSION").unwrap_or("unknown_version"),
6036 config::host_triple(),
6040 fn potentially_plural_count(count: usize, word: &str) -> String {
6041 format!("{} {}{}", count, word, pluralize!(count))