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 - vtable: find and records the impls to use for each trait bound that
35 appears on a type parameter.
37 - writeback: writes the final types within a function body, replacing
38 type variables with their final inferred types. These final types
39 are written into the `tcx.node_types` table, which should *never* contain
40 any reference to a type variable.
44 While type checking a function, the intermediate types for the
45 expressions, blocks, and so forth contained within the function are
46 stored in `fcx.node_types` and `fcx.node_substs`. These types
47 may contain unresolved type variables. After type checking is
48 complete, the functions in the writeback module are used to take the
49 types from this table, resolve them, and then write them into their
50 permanent home in the type context `tcx`.
52 This means that during inferencing you should use `fcx.write_ty()`
53 and `fcx.expr_ty()` / `fcx.node_ty()` to write/obtain the types of
54 nodes within the function.
56 The types of top-level items, which never contain unbound type
57 variables, are stored directly into the `tcx` tables.
59 N.B., a type variable is not the same thing as a type parameter. A
60 type variable is rather an "instance" of a type parameter: that is,
61 given a generic function `fn foo<T>(t: T)`: while checking the
62 function `foo`, the type `ty_param(0)` refers to the type `T`, which
63 is treated in abstract. When `foo()` is called, however, `T` will be
64 substituted for a fresh type variable `N`. This variable will
65 eventually be resolved to some concrete type (which might itself be
80 mod generator_interior;
90 use crate::astconv::{AstConv, GenericArgCountMismatch, PathSeg};
91 use crate::middle::lang_items;
92 use rustc::hir::map::blocks::FnLikeNode;
93 use rustc::hir::map::Map;
94 use rustc::middle::region;
95 use rustc::mir::interpret::ConstValue;
96 use rustc::session::parse::feature_err;
97 use rustc::ty::adjustment::{
98 Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability, PointerCast,
100 use rustc::ty::fold::{TypeFoldable, TypeFolder};
101 use rustc::ty::layout::VariantIdx;
102 use rustc::ty::query::Providers;
103 use rustc::ty::subst::{GenericArgKind, InternalSubsts, Subst, SubstsRef, UserSelfTy, UserSubsts};
104 use rustc::ty::util::{Discr, IntTypeExt, Representability};
106 self, AdtKind, CanonicalUserType, Const, GenericParamDefKind, RegionKind, ToPolyTraitRef,
107 ToPredicate, Ty, TyCtxt, UserType, WithConstness,
110 use rustc_ast::util::parser::ExprPrecedence;
111 use rustc_attr as attr;
112 use rustc_data_structures::captures::Captures;
113 use rustc_data_structures::fx::{FxHashMap, FxHashSet};
114 use rustc_errors::{pluralize, struct_span_err, Applicability, DiagnosticBuilder, DiagnosticId};
115 use rustc_hir as hir;
116 use rustc_hir::def::{CtorOf, DefKind, Res};
117 use rustc_hir::def_id::{CrateNum, DefId, DefIdMap, DefIdSet, LOCAL_CRATE};
118 use rustc_hir::intravisit::{self, NestedVisitorMap, Visitor};
119 use rustc_hir::itemlikevisit::ItemLikeVisitor;
120 use rustc_hir::{ExprKind, GenericArg, HirIdMap, Item, ItemKind, Node, PatKind, QPath};
121 use rustc_index::vec::Idx;
122 use rustc_infer::infer::canonical::{Canonical, OriginalQueryValues, QueryResponse};
123 use rustc_infer::infer::error_reporting::TypeAnnotationNeeded::E0282;
124 use rustc_infer::infer::opaque_types::OpaqueTypeDecl;
125 use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
126 use rustc_infer::infer::unify_key::{ConstVariableOrigin, ConstVariableOriginKind};
127 use rustc_infer::infer::{self, InferCtxt, InferOk, InferResult, TyCtxtInferExt};
128 use rustc_infer::traits::error_reporting::recursive_type_with_infinite_size_error;
129 use rustc_infer::traits::{self, ObligationCause, ObligationCauseCode, TraitEngine};
130 use rustc_span::hygiene::DesugaringKind;
131 use rustc_span::source_map::{original_sp, DUMMY_SP};
132 use rustc_span::symbol::{kw, sym, Ident};
133 use rustc_span::{self, BytePos, MultiSpan, Span};
134 use rustc_target::spec::abi::Abi;
136 use std::cell::{Cell, Ref, RefCell, RefMut};
138 use std::collections::hash_map::Entry;
140 use std::mem::replace;
141 use std::ops::{self, Deref};
145 use crate::require_c_abi_if_c_variadic;
146 use crate::session::config::EntryFnType;
147 use crate::session::Session;
148 use crate::util::common::{indenter, ErrorReported};
149 use crate::TypeAndSubsts;
151 use self::autoderef::Autoderef;
152 use self::callee::DeferredCallResolution;
153 use self::coercion::{CoerceMany, DynamicCoerceMany};
154 use self::compare_method::{compare_const_impl, compare_impl_method, compare_ty_impl};
155 use self::method::{MethodCallee, SelfSource};
156 pub use self::Expectation::*;
157 use self::TupleArgumentsFlag::*;
160 macro_rules! type_error_struct {
161 ($session:expr, $span:expr, $typ:expr, $code:ident, $($message:tt)*) => ({
162 if $typ.references_error() {
163 $session.diagnostic().struct_dummy()
165 rustc_errors::struct_span_err!($session, $span, $code, $($message)*)
170 /// The type of a local binding, including the revealed type for anon types.
171 #[derive(Copy, Clone, Debug)]
172 pub struct LocalTy<'tcx> {
174 revealed_ty: Ty<'tcx>,
177 /// A wrapper for `InferCtxt`'s `in_progress_tables` field.
178 #[derive(Copy, Clone)]
179 struct MaybeInProgressTables<'a, 'tcx> {
180 maybe_tables: Option<&'a RefCell<ty::TypeckTables<'tcx>>>,
183 impl<'a, 'tcx> MaybeInProgressTables<'a, 'tcx> {
184 fn borrow(self) -> Ref<'a, ty::TypeckTables<'tcx>> {
185 match self.maybe_tables {
186 Some(tables) => tables.borrow(),
187 None => bug!("MaybeInProgressTables: inh/fcx.tables.borrow() with no tables"),
191 fn borrow_mut(self) -> RefMut<'a, ty::TypeckTables<'tcx>> {
192 match self.maybe_tables {
193 Some(tables) => tables.borrow_mut(),
194 None => bug!("MaybeInProgressTables: inh/fcx.tables.borrow_mut() with no tables"),
199 /// Closures defined within the function. For example:
202 /// bar(move|| { ... })
205 /// Here, the function `foo()` and the closure passed to
206 /// `bar()` will each have their own `FnCtxt`, but they will
207 /// share the inherited fields.
208 pub struct Inherited<'a, 'tcx> {
209 infcx: InferCtxt<'a, 'tcx>,
211 tables: MaybeInProgressTables<'a, 'tcx>,
213 locals: RefCell<HirIdMap<LocalTy<'tcx>>>,
215 fulfillment_cx: RefCell<Box<dyn TraitEngine<'tcx>>>,
217 // Some additional `Sized` obligations badly affect type inference.
218 // These obligations are added in a later stage of typeck.
219 deferred_sized_obligations: RefCell<Vec<(Ty<'tcx>, Span, traits::ObligationCauseCode<'tcx>)>>,
221 // When we process a call like `c()` where `c` is a closure type,
222 // we may not have decided yet whether `c` is a `Fn`, `FnMut`, or
223 // `FnOnce` closure. In that case, we defer full resolution of the
224 // call until upvar inference can kick in and make the
225 // decision. We keep these deferred resolutions grouped by the
226 // def-id of the closure, so that once we decide, we can easily go
227 // back and process them.
228 deferred_call_resolutions: RefCell<DefIdMap<Vec<DeferredCallResolution<'tcx>>>>,
230 deferred_cast_checks: RefCell<Vec<cast::CastCheck<'tcx>>>,
232 deferred_generator_interiors: RefCell<Vec<(hir::BodyId, Ty<'tcx>, hir::GeneratorKind)>>,
234 // Opaque types found in explicit return types and their
235 // associated fresh inference variable. Writeback resolves these
236 // variables to get the concrete type, which can be used to
237 // 'de-opaque' OpaqueTypeDecl, after typeck is done with all functions.
238 opaque_types: RefCell<DefIdMap<OpaqueTypeDecl<'tcx>>>,
240 /// A map from inference variables created from opaque
241 /// type instantiations (`ty::Infer`) to the actual opaque
242 /// type (`ty::Opaque`). Used during fallback to map unconstrained
243 /// opaque type inference variables to their corresponding
245 opaque_types_vars: RefCell<FxHashMap<Ty<'tcx>, Ty<'tcx>>>,
247 /// Each type parameter has an implicit region bound that
248 /// indicates it must outlive at least the function body (the user
249 /// may specify stronger requirements). This field indicates the
250 /// region of the callee. If it is `None`, then the parameter
251 /// environment is for an item or something where the "callee" is
253 implicit_region_bound: Option<ty::Region<'tcx>>,
255 body_id: Option<hir::BodyId>,
258 impl<'a, 'tcx> Deref for Inherited<'a, 'tcx> {
259 type Target = InferCtxt<'a, 'tcx>;
260 fn deref(&self) -> &Self::Target {
265 /// When type-checking an expression, we propagate downward
266 /// whatever type hint we are able in the form of an `Expectation`.
267 #[derive(Copy, Clone, Debug)]
268 pub enum Expectation<'tcx> {
269 /// We know nothing about what type this expression should have.
272 /// This expression should have the type given (or some subtype).
273 ExpectHasType(Ty<'tcx>),
275 /// This expression will be cast to the `Ty`.
276 ExpectCastableToType(Ty<'tcx>),
278 /// This rvalue expression will be wrapped in `&` or `Box` and coerced
279 /// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
280 ExpectRvalueLikeUnsized(Ty<'tcx>),
283 impl<'a, 'tcx> Expectation<'tcx> {
284 // Disregard "castable to" expectations because they
285 // can lead us astray. Consider for example `if cond
286 // {22} else {c} as u8` -- if we propagate the
287 // "castable to u8" constraint to 22, it will pick the
288 // type 22u8, which is overly constrained (c might not
289 // be a u8). In effect, the problem is that the
290 // "castable to" expectation is not the tightest thing
291 // we can say, so we want to drop it in this case.
292 // The tightest thing we can say is "must unify with
293 // else branch". Note that in the case of a "has type"
294 // constraint, this limitation does not hold.
296 // If the expected type is just a type variable, then don't use
297 // an expected type. Otherwise, we might write parts of the type
298 // when checking the 'then' block which are incompatible with the
300 fn adjust_for_branches(&self, fcx: &FnCtxt<'a, 'tcx>) -> Expectation<'tcx> {
302 ExpectHasType(ety) => {
303 let ety = fcx.shallow_resolve(ety);
304 if !ety.is_ty_var() { ExpectHasType(ety) } else { NoExpectation }
306 ExpectRvalueLikeUnsized(ety) => ExpectRvalueLikeUnsized(ety),
311 /// Provides an expectation for an rvalue expression given an *optional*
312 /// hint, which is not required for type safety (the resulting type might
313 /// be checked higher up, as is the case with `&expr` and `box expr`), but
314 /// is useful in determining the concrete type.
316 /// The primary use case is where the expected type is a fat pointer,
317 /// like `&[isize]`. For example, consider the following statement:
319 /// let x: &[isize] = &[1, 2, 3];
321 /// In this case, the expected type for the `&[1, 2, 3]` expression is
322 /// `&[isize]`. If however we were to say that `[1, 2, 3]` has the
323 /// expectation `ExpectHasType([isize])`, that would be too strong --
324 /// `[1, 2, 3]` does not have the type `[isize]` but rather `[isize; 3]`.
325 /// It is only the `&[1, 2, 3]` expression as a whole that can be coerced
326 /// to the type `&[isize]`. Therefore, we propagate this more limited hint,
327 /// which still is useful, because it informs integer literals and the like.
328 /// See the test case `test/ui/coerce-expect-unsized.rs` and #20169
329 /// for examples of where this comes up,.
330 fn rvalue_hint(fcx: &FnCtxt<'a, 'tcx>, ty: Ty<'tcx>) -> Expectation<'tcx> {
331 match fcx.tcx.struct_tail_without_normalization(ty).kind {
332 ty::Slice(_) | ty::Str | ty::Dynamic(..) => ExpectRvalueLikeUnsized(ty),
333 _ => ExpectHasType(ty),
337 // Resolves `expected` by a single level if it is a variable. If
338 // there is no expected type or resolution is not possible (e.g.,
339 // no constraints yet present), just returns `None`.
340 fn resolve(self, fcx: &FnCtxt<'a, 'tcx>) -> Expectation<'tcx> {
342 NoExpectation => NoExpectation,
343 ExpectCastableToType(t) => ExpectCastableToType(fcx.resolve_vars_if_possible(&t)),
344 ExpectHasType(t) => ExpectHasType(fcx.resolve_vars_if_possible(&t)),
345 ExpectRvalueLikeUnsized(t) => ExpectRvalueLikeUnsized(fcx.resolve_vars_if_possible(&t)),
349 fn to_option(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
350 match self.resolve(fcx) {
351 NoExpectation => None,
352 ExpectCastableToType(ty) | ExpectHasType(ty) | ExpectRvalueLikeUnsized(ty) => Some(ty),
356 /// It sometimes happens that we want to turn an expectation into
357 /// a **hard constraint** (i.e., something that must be satisfied
358 /// for the program to type-check). `only_has_type` will return
359 /// such a constraint, if it exists.
360 fn only_has_type(self, fcx: &FnCtxt<'a, 'tcx>) -> Option<Ty<'tcx>> {
361 match self.resolve(fcx) {
362 ExpectHasType(ty) => Some(ty),
363 NoExpectation | ExpectCastableToType(_) | ExpectRvalueLikeUnsized(_) => None,
367 /// Like `only_has_type`, but instead of returning `None` if no
368 /// hard constraint exists, creates a fresh type variable.
369 fn coercion_target_type(self, fcx: &FnCtxt<'a, 'tcx>, span: Span) -> Ty<'tcx> {
370 self.only_has_type(fcx).unwrap_or_else(|| {
371 fcx.next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::MiscVariable, span })
376 #[derive(Copy, Clone, Debug, PartialEq, Eq)]
383 fn maybe_mut_place(m: hir::Mutability) -> Self {
385 hir::Mutability::Mut => Needs::MutPlace,
386 hir::Mutability::Not => Needs::None,
391 #[derive(Copy, Clone)]
392 pub struct UnsafetyState {
394 pub unsafety: hir::Unsafety,
395 pub unsafe_push_count: u32,
400 pub fn function(unsafety: hir::Unsafety, def: hir::HirId) -> UnsafetyState {
401 UnsafetyState { def, unsafety, unsafe_push_count: 0, from_fn: true }
404 pub fn recurse(&mut self, blk: &hir::Block<'_>) -> UnsafetyState {
405 use hir::BlockCheckMode;
406 match self.unsafety {
407 // If this unsafe, then if the outer function was already marked as
408 // unsafe we shouldn't attribute the unsafe'ness to the block. This
409 // way the block can be warned about instead of ignoring this
410 // extraneous block (functions are never warned about).
411 hir::Unsafety::Unsafe if self.from_fn => *self,
414 let (unsafety, def, count) = match blk.rules {
415 BlockCheckMode::PushUnsafeBlock(..) => {
416 (unsafety, blk.hir_id, self.unsafe_push_count.checked_add(1).unwrap())
418 BlockCheckMode::PopUnsafeBlock(..) => {
419 (unsafety, blk.hir_id, self.unsafe_push_count.checked_sub(1).unwrap())
421 BlockCheckMode::UnsafeBlock(..) => {
422 (hir::Unsafety::Unsafe, blk.hir_id, self.unsafe_push_count)
424 BlockCheckMode::DefaultBlock => (unsafety, self.def, self.unsafe_push_count),
426 UnsafetyState { def, unsafety, unsafe_push_count: count, from_fn: false }
432 #[derive(Debug, Copy, Clone)]
438 /// Tracks whether executing a node may exit normally (versus
439 /// return/break/panic, which "diverge", leaving dead code in their
440 /// wake). Tracked semi-automatically (through type variables marked
441 /// as diverging), with some manual adjustments for control-flow
442 /// primitives (approximating a CFG).
443 #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)]
445 /// Potentially unknown, some cases converge,
446 /// others require a CFG to determine them.
449 /// Definitely known to diverge and therefore
450 /// not reach the next sibling or its parent.
452 /// The `Span` points to the expression
453 /// that caused us to diverge
454 /// (e.g. `return`, `break`, etc).
456 /// In some cases (e.g. a `match` expression
457 /// where all arms diverge), we may be
458 /// able to provide a more informative
459 /// message to the user.
460 /// If this is `None`, a default messsage
461 /// will be generated, which is suitable
463 custom_note: Option<&'static str>,
466 /// Same as `Always` but with a reachability
467 /// warning already emitted.
471 // Convenience impls for combining `Diverges`.
473 impl ops::BitAnd for Diverges {
475 fn bitand(self, other: Self) -> Self {
476 cmp::min(self, other)
480 impl ops::BitOr for Diverges {
482 fn bitor(self, other: Self) -> Self {
483 cmp::max(self, other)
487 impl ops::BitAndAssign for Diverges {
488 fn bitand_assign(&mut self, other: Self) {
489 *self = *self & other;
493 impl ops::BitOrAssign for Diverges {
494 fn bitor_assign(&mut self, other: Self) {
495 *self = *self | other;
500 /// Creates a `Diverges::Always` with the provided `span` and the default note message.
501 fn always(span: Span) -> Diverges {
502 Diverges::Always { span, custom_note: None }
505 fn is_always(self) -> bool {
506 // Enum comparison ignores the
507 // contents of fields, so we just
508 // fill them in with garbage here.
509 self >= Diverges::Always { span: DUMMY_SP, custom_note: None }
513 pub struct BreakableCtxt<'tcx> {
516 // this is `null` for loops where break with a value is illegal,
517 // such as `while`, `for`, and `while let`
518 coerce: Option<DynamicCoerceMany<'tcx>>,
521 pub struct EnclosingBreakables<'tcx> {
522 stack: Vec<BreakableCtxt<'tcx>>,
523 by_id: HirIdMap<usize>,
526 impl<'tcx> EnclosingBreakables<'tcx> {
527 fn find_breakable(&mut self, target_id: hir::HirId) -> &mut BreakableCtxt<'tcx> {
528 self.opt_find_breakable(target_id).unwrap_or_else(|| {
529 bug!("could not find enclosing breakable with id {}", target_id);
533 fn opt_find_breakable(&mut self, target_id: hir::HirId) -> Option<&mut BreakableCtxt<'tcx>> {
534 match self.by_id.get(&target_id) {
535 Some(ix) => Some(&mut self.stack[*ix]),
541 pub struct FnCtxt<'a, 'tcx> {
544 /// The parameter environment used for proving trait obligations
545 /// in this function. This can change when we descend into
546 /// closures (as they bring new things into scope), hence it is
547 /// not part of `Inherited` (as of the time of this writing,
548 /// closures do not yet change the environment, but they will
550 param_env: ty::ParamEnv<'tcx>,
552 /// Number of errors that had been reported when we started
553 /// checking this function. On exit, if we find that *more* errors
554 /// have been reported, we will skip regionck and other work that
555 /// expects the types within the function to be consistent.
556 // FIXME(matthewjasper) This should not exist, and it's not correct
557 // if type checking is run in parallel.
558 err_count_on_creation: usize,
560 /// If `Some`, this stores coercion information for returned
561 /// expressions. If `None`, this is in a context where return is
562 /// inappropriate, such as a const expression.
564 /// This is a `RefCell<DynamicCoerceMany>`, which means that we
565 /// can track all the return expressions and then use them to
566 /// compute a useful coercion from the set, similar to a match
567 /// expression or other branching context. You can use methods
568 /// like `expected_ty` to access the declared return type (if
570 ret_coercion: Option<RefCell<DynamicCoerceMany<'tcx>>>,
572 /// First span of a return site that we find. Used in error messages.
573 ret_coercion_span: RefCell<Option<Span>>,
575 resume_yield_tys: Option<(Ty<'tcx>, Ty<'tcx>)>,
577 ps: RefCell<UnsafetyState>,
579 /// Whether the last checked node generates a divergence (e.g.,
580 /// `return` will set this to `Always`). In general, when entering
581 /// an expression or other node in the tree, the initial value
582 /// indicates whether prior parts of the containing expression may
583 /// have diverged. It is then typically set to `Maybe` (and the
584 /// old value remembered) for processing the subparts of the
585 /// current expression. As each subpart is processed, they may set
586 /// the flag to `Always`, etc. Finally, at the end, we take the
587 /// result and "union" it with the original value, so that when we
588 /// return the flag indicates if any subpart of the parent
589 /// expression (up to and including this part) has diverged. So,
590 /// if you read it after evaluating a subexpression `X`, the value
591 /// you get indicates whether any subexpression that was
592 /// evaluating up to and including `X` diverged.
594 /// We currently use this flag only for diagnostic purposes:
596 /// - To warn about unreachable code: if, after processing a
597 /// sub-expression but before we have applied the effects of the
598 /// current node, we see that the flag is set to `Always`, we
599 /// can issue a warning. This corresponds to something like
600 /// `foo(return)`; we warn on the `foo()` expression. (We then
601 /// update the flag to `WarnedAlways` to suppress duplicate
602 /// reports.) Similarly, if we traverse to a fresh statement (or
603 /// tail expression) from a `Always` setting, we will issue a
604 /// warning. This corresponds to something like `{return;
605 /// foo();}` or `{return; 22}`, where we would warn on the
608 /// An expression represents dead code if, after checking it,
609 /// the diverges flag is set to something other than `Maybe`.
610 diverges: Cell<Diverges>,
612 /// Whether any child nodes have any type errors.
613 has_errors: Cell<bool>,
615 enclosing_breakables: RefCell<EnclosingBreakables<'tcx>>,
617 inh: &'a Inherited<'a, 'tcx>,
620 impl<'a, 'tcx> Deref for FnCtxt<'a, 'tcx> {
621 type Target = Inherited<'a, 'tcx>;
622 fn deref(&self) -> &Self::Target {
627 /// Helper type of a temporary returned by `Inherited::build(...)`.
628 /// Necessary because we can't write the following bound:
629 /// `F: for<'b, 'tcx> where 'tcx FnOnce(Inherited<'b, 'tcx>)`.
630 pub struct InheritedBuilder<'tcx> {
631 infcx: infer::InferCtxtBuilder<'tcx>,
635 impl Inherited<'_, 'tcx> {
636 pub fn build(tcx: TyCtxt<'tcx>, def_id: DefId) -> InheritedBuilder<'tcx> {
637 let hir_id_root = if def_id.is_local() {
638 let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
639 DefId::local(hir_id.owner)
645 infcx: tcx.infer_ctxt().with_fresh_in_progress_tables(hir_id_root),
651 impl<'tcx> InheritedBuilder<'tcx> {
652 fn enter<F, R>(&mut self, f: F) -> R
654 F: for<'a> FnOnce(Inherited<'a, 'tcx>) -> R,
656 let def_id = self.def_id;
657 self.infcx.enter(|infcx| f(Inherited::new(infcx, def_id)))
661 impl Inherited<'a, 'tcx> {
662 fn new(infcx: InferCtxt<'a, 'tcx>, def_id: DefId) -> Self {
664 let item_id = tcx.hir().as_local_hir_id(def_id);
665 let body_id = item_id.and_then(|id| tcx.hir().maybe_body_owned_by(id));
666 let implicit_region_bound = body_id.map(|body_id| {
667 let body = tcx.hir().body(body_id);
668 tcx.mk_region(ty::ReScope(region::Scope {
669 id: body.value.hir_id.local_id,
670 data: region::ScopeData::CallSite,
675 tables: MaybeInProgressTables { maybe_tables: infcx.in_progress_tables },
677 fulfillment_cx: RefCell::new(TraitEngine::new(tcx)),
678 locals: RefCell::new(Default::default()),
679 deferred_sized_obligations: RefCell::new(Vec::new()),
680 deferred_call_resolutions: RefCell::new(Default::default()),
681 deferred_cast_checks: RefCell::new(Vec::new()),
682 deferred_generator_interiors: RefCell::new(Vec::new()),
683 opaque_types: RefCell::new(Default::default()),
684 opaque_types_vars: RefCell::new(Default::default()),
685 implicit_region_bound,
690 fn register_predicate(&self, obligation: traits::PredicateObligation<'tcx>) {
691 debug!("register_predicate({:?})", obligation);
692 if obligation.has_escaping_bound_vars() {
693 span_bug!(obligation.cause.span, "escaping bound vars in predicate {:?}", obligation);
695 self.fulfillment_cx.borrow_mut().register_predicate_obligation(self, obligation);
698 fn register_predicates<I>(&self, obligations: I)
700 I: IntoIterator<Item = traits::PredicateObligation<'tcx>>,
702 for obligation in obligations {
703 self.register_predicate(obligation);
707 fn register_infer_ok_obligations<T>(&self, infer_ok: InferOk<'tcx, T>) -> T {
708 self.register_predicates(infer_ok.obligations);
712 fn normalize_associated_types_in<T>(
716 param_env: ty::ParamEnv<'tcx>,
720 T: TypeFoldable<'tcx>,
722 let ok = self.partially_normalize_associated_types_in(span, body_id, param_env, value);
723 self.register_infer_ok_obligations(ok)
727 struct CheckItemTypesVisitor<'tcx> {
731 impl ItemLikeVisitor<'tcx> for CheckItemTypesVisitor<'tcx> {
732 fn visit_item(&mut self, i: &'tcx hir::Item<'tcx>) {
733 check_item_type(self.tcx, i);
735 fn visit_trait_item(&mut self, _: &'tcx hir::TraitItem<'tcx>) {}
736 fn visit_impl_item(&mut self, _: &'tcx hir::ImplItem<'tcx>) {}
739 pub fn check_wf_new(tcx: TyCtxt<'_>) {
740 let mut visit = wfcheck::CheckTypeWellFormedVisitor::new(tcx);
741 tcx.hir().krate().par_visit_all_item_likes(&mut visit);
744 fn check_mod_item_types(tcx: TyCtxt<'_>, module_def_id: DefId) {
745 tcx.hir().visit_item_likes_in_module(module_def_id, &mut CheckItemTypesVisitor { tcx });
748 fn typeck_item_bodies(tcx: TyCtxt<'_>, crate_num: CrateNum) {
749 debug_assert!(crate_num == LOCAL_CRATE);
750 tcx.par_body_owners(|body_owner_def_id| {
751 tcx.ensure().typeck_tables_of(body_owner_def_id);
755 fn check_item_well_formed(tcx: TyCtxt<'_>, def_id: DefId) {
756 wfcheck::check_item_well_formed(tcx, def_id);
759 fn check_trait_item_well_formed(tcx: TyCtxt<'_>, def_id: DefId) {
760 wfcheck::check_trait_item(tcx, def_id);
763 fn check_impl_item_well_formed(tcx: TyCtxt<'_>, def_id: DefId) {
764 wfcheck::check_impl_item(tcx, def_id);
767 pub fn provide(providers: &mut Providers<'_>) {
768 method::provide(providers);
769 *providers = Providers {
772 diagnostic_only_typeck_tables_of,
776 check_item_well_formed,
777 check_trait_item_well_formed,
778 check_impl_item_well_formed,
779 check_mod_item_types,
784 fn adt_destructor(tcx: TyCtxt<'_>, def_id: DefId) -> Option<ty::Destructor> {
785 tcx.calculate_dtor(def_id, &mut dropck::check_drop_impl)
788 /// If this `DefId` is a "primary tables entry", returns
789 /// `Some((body_id, header, decl))` with information about
790 /// it's body-id, fn-header and fn-decl (if any). Otherwise,
793 /// If this function returns `Some`, then `typeck_tables(def_id)` will
794 /// succeed; if it returns `None`, then `typeck_tables(def_id)` may or
795 /// may not succeed. In some cases where this function returns `None`
796 /// (notably closures), `typeck_tables(def_id)` would wind up
797 /// redirecting to the owning function.
801 ) -> Option<(hir::BodyId, Option<&hir::Ty<'_>>, Option<&hir::FnHeader>, Option<&hir::FnDecl<'_>>)> {
802 match tcx.hir().get(id) {
803 Node::Item(item) => match item.kind {
804 hir::ItemKind::Const(ref ty, body) | hir::ItemKind::Static(ref ty, _, body) => {
805 Some((body, Some(ty), None, None))
807 hir::ItemKind::Fn(ref sig, .., body) => {
808 Some((body, None, Some(&sig.header), Some(&sig.decl)))
812 Node::TraitItem(item) => match item.kind {
813 hir::TraitItemKind::Const(ref ty, Some(body)) => Some((body, Some(ty), None, None)),
814 hir::TraitItemKind::Method(ref sig, hir::TraitMethod::Provided(body)) => {
815 Some((body, None, Some(&sig.header), Some(&sig.decl)))
819 Node::ImplItem(item) => match item.kind {
820 hir::ImplItemKind::Const(ref ty, body) => Some((body, Some(ty), None, None)),
821 hir::ImplItemKind::Method(ref sig, body) => {
822 Some((body, None, Some(&sig.header), Some(&sig.decl)))
826 Node::AnonConst(constant) => Some((constant.body, None, None, None)),
831 fn has_typeck_tables(tcx: TyCtxt<'_>, def_id: DefId) -> bool {
832 // Closures' tables come from their outermost function,
833 // as they are part of the same "inference environment".
834 let outer_def_id = tcx.closure_base_def_id(def_id);
835 if outer_def_id != def_id {
836 return tcx.has_typeck_tables(outer_def_id);
839 if let Some(id) = tcx.hir().as_local_hir_id(def_id) {
840 primary_body_of(tcx, id).is_some()
846 fn used_trait_imports(tcx: TyCtxt<'_>, def_id: DefId) -> &DefIdSet {
847 &*tcx.typeck_tables_of(def_id).used_trait_imports
850 /// Inspects the substs of opaque types, replacing any inference variables
851 /// with proper generic parameter from the identity substs.
853 /// This is run after we normalize the function signature, to fix any inference
854 /// variables introduced by the projection of associated types. This ensures that
855 /// any opaque types used in the signature continue to refer to generic parameters,
856 /// allowing them to be considered for defining uses in the function body
858 /// For example, consider this code.
863 /// fn use_it(self) -> Self::MyItem
865 /// impl<T, I> MyTrait for T where T: Iterator<Item = I> {
866 /// type MyItem = impl Iterator<Item = I>;
867 /// fn use_it(self) -> Self::MyItem {
873 /// When we normalize the signature of `use_it` from the impl block,
874 /// we will normalize `Self::MyItem` to the opaque type `impl Iterator<Item = I>`
875 /// However, this projection result may contain inference variables, due
876 /// to the way that projection works. We didn't have any inference variables
877 /// in the signature to begin with - leaving them in will cause us to incorrectly
878 /// conclude that we don't have a defining use of `MyItem`. By mapping inference
879 /// variables back to the actual generic parameters, we will correctly see that
880 /// we have a defining use of `MyItem`
881 fn fixup_opaque_types<'tcx, T>(tcx: TyCtxt<'tcx>, val: &T) -> T
883 T: TypeFoldable<'tcx>,
885 struct FixupFolder<'tcx> {
889 impl<'tcx> TypeFolder<'tcx> for FixupFolder<'tcx> {
890 fn tcx<'a>(&'a self) -> TyCtxt<'tcx> {
894 fn fold_ty(&mut self, ty: Ty<'tcx>) -> Ty<'tcx> {
896 ty::Opaque(def_id, substs) => {
897 debug!("fixup_opaque_types: found type {:?}", ty);
898 // Here, we replace any inference variables that occur within
899 // the substs of an opaque type. By definition, any type occuring
900 // in the substs has a corresponding generic parameter, which is what
901 // we replace it with.
902 // This replacement is only run on the function signature, so any
903 // inference variables that we come across must be the rust of projection
904 // (there's no other way for a user to get inference variables into
905 // a function signature).
906 if ty.needs_infer() {
907 let new_substs = InternalSubsts::for_item(self.tcx, def_id, |param, _| {
908 let old_param = substs[param.index as usize];
909 match old_param.unpack() {
910 GenericArgKind::Type(old_ty) => {
911 if let ty::Infer(_) = old_ty.kind {
912 // Replace inference type with a generic parameter
913 self.tcx.mk_param_from_def(param)
915 old_param.fold_with(self)
918 GenericArgKind::Const(old_const) => {
919 if let ty::ConstKind::Infer(_) = old_const.val {
920 // This should never happen - we currently do not support
921 // 'const projections', e.g.:
922 // `impl<T: SomeTrait> MyTrait for T where <T as SomeTrait>::MyConst == 25`
923 // which should be the only way for us to end up with a const inference
924 // variable after projection. If Rust ever gains support for this kind
925 // of projection, this should *probably* be changed to
926 // `self.tcx.mk_param_from_def(param)`
928 "Found infer const: `{:?}` in opaque type: {:?}",
933 old_param.fold_with(self)
936 GenericArgKind::Lifetime(old_region) => {
937 if let RegionKind::ReVar(_) = old_region {
938 self.tcx.mk_param_from_def(param)
940 old_param.fold_with(self)
945 let new_ty = self.tcx.mk_opaque(def_id, new_substs);
946 debug!("fixup_opaque_types: new type: {:?}", new_ty);
952 _ => ty.super_fold_with(self),
957 debug!("fixup_opaque_types({:?})", val);
958 val.fold_with(&mut FixupFolder { tcx })
961 fn typeck_tables_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) -> &ty::TypeckTables<'tcx> {
962 let fallback = move || tcx.type_of(def_id);
963 typeck_tables_of_with_fallback(tcx, def_id, fallback)
966 /// Used only to get `TypeckTables` for type inference during error recovery.
967 /// Currently only used for type inference of `static`s and `const`s to avoid type cycle errors.
968 fn diagnostic_only_typeck_tables_of<'tcx>(
971 ) -> &ty::TypeckTables<'tcx> {
972 assert!(def_id.is_local());
973 let fallback = move || {
974 let span = tcx.hir().span(tcx.hir().as_local_hir_id(def_id).unwrap());
975 tcx.sess.delay_span_bug(span, "diagnostic only typeck table used");
978 typeck_tables_of_with_fallback(tcx, def_id, fallback)
981 fn typeck_tables_of_with_fallback<'tcx>(
984 fallback: impl Fn() -> Ty<'tcx> + 'tcx,
985 ) -> &'tcx ty::TypeckTables<'tcx> {
986 // Closures' tables come from their outermost function,
987 // as they are part of the same "inference environment".
988 let outer_def_id = tcx.closure_base_def_id(def_id);
989 if outer_def_id != def_id {
990 return tcx.typeck_tables_of(outer_def_id);
993 let id = tcx.hir().as_local_hir_id(def_id).unwrap();
994 let span = tcx.hir().span(id);
996 // Figure out what primary body this item has.
997 let (body_id, body_ty, fn_header, fn_decl) = primary_body_of(tcx, id).unwrap_or_else(|| {
998 span_bug!(span, "can't type-check body of {:?}", def_id);
1000 let body = tcx.hir().body(body_id);
1002 let tables = Inherited::build(tcx, def_id).enter(|inh| {
1003 let param_env = tcx.param_env(def_id);
1004 let fcx = if let (Some(header), Some(decl)) = (fn_header, fn_decl) {
1005 let fn_sig = if crate::collect::get_infer_ret_ty(&decl.output).is_some() {
1006 let fcx = FnCtxt::new(&inh, param_env, body.value.hir_id);
1007 AstConv::ty_of_fn(&fcx, header.unsafety, header.abi, decl, &[], None)
1012 check_abi(tcx, span, fn_sig.abi());
1014 // Compute the fty from point of view of inside the fn.
1015 let fn_sig = tcx.liberate_late_bound_regions(def_id, &fn_sig);
1016 let fn_sig = inh.normalize_associated_types_in(
1023 let fn_sig = fixup_opaque_types(tcx, &fn_sig);
1025 let fcx = check_fn(&inh, param_env, fn_sig, decl, id, body, None).0;
1028 let fcx = FnCtxt::new(&inh, param_env, body.value.hir_id);
1029 let expected_type = body_ty
1030 .and_then(|ty| match ty.kind {
1031 hir::TyKind::Infer => Some(AstConv::ast_ty_to_ty(&fcx, ty)),
1034 .unwrap_or_else(fallback);
1035 let expected_type = fcx.normalize_associated_types_in(body.value.span, &expected_type);
1036 fcx.require_type_is_sized(expected_type, body.value.span, traits::ConstSized);
1038 let revealed_ty = if tcx.features().impl_trait_in_bindings {
1039 fcx.instantiate_opaque_types_from_value(id, &expected_type, body.value.span)
1044 // Gather locals in statics (because of block expressions).
1045 GatherLocalsVisitor { fcx: &fcx, parent_id: id }.visit_body(body);
1047 fcx.check_expr_coercable_to_type(&body.value, revealed_ty);
1049 fcx.write_ty(id, revealed_ty);
1054 // All type checking constraints were added, try to fallback unsolved variables.
1055 fcx.select_obligations_where_possible(false, |_| {});
1056 let mut fallback_has_occurred = false;
1058 // We do fallback in two passes, to try to generate
1059 // better error messages.
1060 // The first time, we do *not* replace opaque types.
1061 for ty in &fcx.unsolved_variables() {
1062 fallback_has_occurred |= fcx.fallback_if_possible(ty, FallbackMode::NoOpaque);
1064 // We now see if we can make progress. This might
1065 // cause us to unify inference variables for opaque types,
1066 // since we may have unified some other type variables
1067 // during the first phase of fallback.
1068 // This means that we only replace inference variables with their underlying
1069 // opaque types as a last resort.
1071 // In code like this:
1074 // type MyType = impl Copy;
1075 // fn produce() -> MyType { true }
1076 // fn bad_produce() -> MyType { panic!() }
1079 // we want to unify the opaque inference variable in `bad_produce`
1080 // with the diverging fallback for `panic!` (e.g. `()` or `!`).
1081 // This will produce a nice error message about conflicting concrete
1082 // types for `MyType`.
1084 // If we had tried to fallback the opaque inference variable to `MyType`,
1085 // we will generate a confusing type-check error that does not explicitly
1086 // refer to opaque types.
1087 fcx.select_obligations_where_possible(fallback_has_occurred, |_| {});
1089 // We now run fallback again, but this time we allow it to replace
1090 // unconstrained opaque type variables, in addition to performing
1091 // other kinds of fallback.
1092 for ty in &fcx.unsolved_variables() {
1093 fallback_has_occurred |= fcx.fallback_if_possible(ty, FallbackMode::All);
1096 // See if we can make any more progress.
1097 fcx.select_obligations_where_possible(fallback_has_occurred, |_| {});
1099 // Even though coercion casts provide type hints, we check casts after fallback for
1100 // backwards compatibility. This makes fallback a stronger type hint than a cast coercion.
1103 // Closure and generator analysis may run after fallback
1104 // because they don't constrain other type variables.
1105 fcx.closure_analyze(body);
1106 assert!(fcx.deferred_call_resolutions.borrow().is_empty());
1107 fcx.resolve_generator_interiors(def_id);
1109 for (ty, span, code) in fcx.deferred_sized_obligations.borrow_mut().drain(..) {
1110 let ty = fcx.normalize_ty(span, ty);
1111 fcx.require_type_is_sized(ty, span, code);
1114 fcx.select_all_obligations_or_error();
1116 if fn_decl.is_some() {
1117 fcx.regionck_fn(id, body);
1119 fcx.regionck_expr(body);
1122 fcx.resolve_type_vars_in_body(body)
1125 // Consistency check our TypeckTables instance can hold all ItemLocalIds
1126 // it will need to hold.
1127 assert_eq!(tables.local_id_root, Some(DefId::local(id.owner)));
1132 fn check_abi(tcx: TyCtxt<'_>, span: Span, abi: Abi) {
1133 if !tcx.sess.target.target.is_abi_supported(abi) {
1138 "The ABI `{}` is not supported for the current target",
1145 struct GatherLocalsVisitor<'a, 'tcx> {
1146 fcx: &'a FnCtxt<'a, 'tcx>,
1147 parent_id: hir::HirId,
1150 impl<'a, 'tcx> GatherLocalsVisitor<'a, 'tcx> {
1151 fn assign(&mut self, span: Span, nid: hir::HirId, ty_opt: Option<LocalTy<'tcx>>) -> Ty<'tcx> {
1154 // infer the variable's type
1155 let var_ty = self.fcx.next_ty_var(TypeVariableOrigin {
1156 kind: TypeVariableOriginKind::TypeInference,
1162 .insert(nid, LocalTy { decl_ty: var_ty, revealed_ty: var_ty });
1166 // take type that the user specified
1167 self.fcx.locals.borrow_mut().insert(nid, typ);
1174 impl<'a, 'tcx> Visitor<'tcx> for GatherLocalsVisitor<'a, 'tcx> {
1175 type Map = Map<'tcx>;
1177 fn nested_visit_map(&mut self) -> NestedVisitorMap<'_, Self::Map> {
1178 NestedVisitorMap::None
1181 // Add explicitly-declared locals.
1182 fn visit_local(&mut self, local: &'tcx hir::Local<'tcx>) {
1183 let local_ty = match local.ty {
1185 let o_ty = self.fcx.to_ty(&ty);
1187 let revealed_ty = if self.fcx.tcx.features().impl_trait_in_bindings {
1188 self.fcx.instantiate_opaque_types_from_value(self.parent_id, &o_ty, ty.span)
1197 .canonicalize_user_type_annotation(&UserType::Ty(revealed_ty));
1199 "visit_local: ty.hir_id={:?} o_ty={:?} revealed_ty={:?} c_ty={:?}",
1200 ty.hir_id, o_ty, revealed_ty, c_ty
1202 self.fcx.tables.borrow_mut().user_provided_types_mut().insert(ty.hir_id, c_ty);
1204 Some(LocalTy { decl_ty: o_ty, revealed_ty })
1208 self.assign(local.span, local.hir_id, local_ty);
1211 "local variable {:?} is assigned type {}",
1213 self.fcx.ty_to_string(&*self.fcx.locals.borrow().get(&local.hir_id).unwrap().decl_ty)
1215 intravisit::walk_local(self, local);
1218 // Add pattern bindings.
1219 fn visit_pat(&mut self, p: &'tcx hir::Pat<'tcx>) {
1220 if let PatKind::Binding(_, _, ident, _) = p.kind {
1221 let var_ty = self.assign(p.span, p.hir_id, None);
1223 if !self.fcx.tcx.features().unsized_locals {
1224 self.fcx.require_type_is_sized(var_ty, p.span, traits::VariableType(p.hir_id));
1228 "pattern binding {} is assigned to {} with type {:?}",
1230 self.fcx.ty_to_string(&*self.fcx.locals.borrow().get(&p.hir_id).unwrap().decl_ty),
1234 intravisit::walk_pat(self, p);
1237 // Don't descend into the bodies of nested closures
1240 _: intravisit::FnKind<'tcx>,
1241 _: &'tcx hir::FnDecl<'tcx>,
1249 /// When `check_fn` is invoked on a generator (i.e., a body that
1250 /// includes yield), it returns back some information about the yield
1252 struct GeneratorTypes<'tcx> {
1253 /// Type of generator argument / values returned by `yield`.
1254 resume_ty: Ty<'tcx>,
1256 /// Type of value that is yielded.
1259 /// Types that are captured (see `GeneratorInterior` for more).
1262 /// Indicates if the generator is movable or static (immovable).
1263 movability: hir::Movability,
1266 /// Helper used for fns and closures. Does the grungy work of checking a function
1267 /// body and returns the function context used for that purpose, since in the case of a fn item
1268 /// there is still a bit more to do.
1271 /// * inherited: other fields inherited from the enclosing fn (if any)
1272 fn check_fn<'a, 'tcx>(
1273 inherited: &'a Inherited<'a, 'tcx>,
1274 param_env: ty::ParamEnv<'tcx>,
1275 fn_sig: ty::FnSig<'tcx>,
1276 decl: &'tcx hir::FnDecl<'tcx>,
1278 body: &'tcx hir::Body<'tcx>,
1279 can_be_generator: Option<hir::Movability>,
1280 ) -> (FnCtxt<'a, 'tcx>, Option<GeneratorTypes<'tcx>>) {
1281 let mut fn_sig = fn_sig;
1283 debug!("check_fn(sig={:?}, fn_id={}, param_env={:?})", fn_sig, fn_id, param_env);
1285 // Create the function context. This is either derived from scratch or,
1286 // in the case of closures, based on the outer context.
1287 let mut fcx = FnCtxt::new(inherited, param_env, body.value.hir_id);
1288 *fcx.ps.borrow_mut() = UnsafetyState::function(fn_sig.unsafety, fn_id);
1291 let sess = tcx.sess;
1292 let hir = tcx.hir();
1294 let declared_ret_ty = fn_sig.output();
1295 fcx.require_type_is_sized(declared_ret_ty, decl.output.span(), traits::SizedReturnType);
1296 let revealed_ret_ty =
1297 fcx.instantiate_opaque_types_from_value(fn_id, &declared_ret_ty, decl.output.span());
1298 debug!("check_fn: declared_ret_ty: {}, revealed_ret_ty: {}", declared_ret_ty, revealed_ret_ty);
1299 fcx.ret_coercion = Some(RefCell::new(CoerceMany::new(revealed_ret_ty)));
1300 fn_sig = tcx.mk_fn_sig(
1301 fn_sig.inputs().iter().cloned(),
1308 let span = body.value.span;
1310 fn_maybe_err(tcx, span, fn_sig.abi);
1312 if body.generator_kind.is_some() && can_be_generator.is_some() {
1314 .next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::TypeInference, span });
1315 fcx.require_type_is_sized(yield_ty, span, traits::SizedYieldType);
1317 // Resume type defaults to `()` if the generator has no argument.
1318 let resume_ty = fn_sig.inputs().get(0).copied().unwrap_or_else(|| tcx.mk_unit());
1320 fcx.resume_yield_tys = Some((resume_ty, yield_ty));
1323 let outer_def_id = tcx.closure_base_def_id(hir.local_def_id(fn_id));
1324 let outer_hir_id = hir.as_local_hir_id(outer_def_id).unwrap();
1325 GatherLocalsVisitor { fcx: &fcx, parent_id: outer_hir_id }.visit_body(body);
1327 // C-variadic fns also have a `VaList` input that's not listed in `fn_sig`
1328 // (as it's created inside the body itself, not passed in from outside).
1329 let maybe_va_list = if fn_sig.c_variadic {
1330 let va_list_did = tcx.require_lang_item(
1331 lang_items::VaListTypeLangItem,
1332 Some(body.params.last().unwrap().span),
1334 let region = tcx.mk_region(ty::ReScope(region::Scope {
1335 id: body.value.hir_id.local_id,
1336 data: region::ScopeData::CallSite,
1339 Some(tcx.type_of(va_list_did).subst(tcx, &[region.into()]))
1344 // Add formal parameters.
1345 let inputs_hir = hir.fn_decl_by_hir_id(fn_id).map(|decl| &decl.inputs);
1346 let inputs_fn = fn_sig.inputs().iter().copied();
1347 for (idx, (param_ty, param)) in inputs_fn.chain(maybe_va_list).zip(body.params).enumerate() {
1348 // Check the pattern.
1349 fcx.check_pat_top(¶m.pat, param_ty, try { inputs_hir?.get(idx)?.span }, false);
1351 // Check that argument is Sized.
1352 // The check for a non-trivial pattern is a hack to avoid duplicate warnings
1353 // for simple cases like `fn foo(x: Trait)`,
1354 // where we would error once on the parameter as a whole, and once on the binding `x`.
1355 if param.pat.simple_ident().is_none() && !tcx.features().unsized_locals {
1356 fcx.require_type_is_sized(param_ty, param.pat.span, traits::SizedArgumentType);
1359 fcx.write_ty(param.hir_id, param_ty);
1362 inherited.tables.borrow_mut().liberated_fn_sigs_mut().insert(fn_id, fn_sig);
1364 fcx.check_return_expr(&body.value);
1366 // We insert the deferred_generator_interiors entry after visiting the body.
1367 // This ensures that all nested generators appear before the entry of this generator.
1368 // resolve_generator_interiors relies on this property.
1369 let gen_ty = if let (Some(_), Some(gen_kind)) = (can_be_generator, body.generator_kind) {
1371 .next_ty_var(TypeVariableOrigin { kind: TypeVariableOriginKind::MiscVariable, span });
1372 fcx.deferred_generator_interiors.borrow_mut().push((body.id(), interior, gen_kind));
1374 let (resume_ty, yield_ty) = fcx.resume_yield_tys.unwrap();
1375 Some(GeneratorTypes {
1379 movability: can_be_generator.unwrap(),
1385 // Finalize the return check by taking the LUB of the return types
1386 // we saw and assigning it to the expected return type. This isn't
1387 // really expected to fail, since the coercions would have failed
1388 // earlier when trying to find a LUB.
1390 // However, the behavior around `!` is sort of complex. In the
1391 // event that the `actual_return_ty` comes back as `!`, that
1392 // indicates that the fn either does not return or "returns" only
1393 // values of type `!`. In this case, if there is an expected
1394 // return type that is *not* `!`, that should be ok. But if the
1395 // return type is being inferred, we want to "fallback" to `!`:
1397 // let x = move || panic!();
1399 // To allow for that, I am creating a type variable with diverging
1400 // fallback. This was deemed ever so slightly better than unifying
1401 // the return value with `!` because it allows for the caller to
1402 // make more assumptions about the return type (e.g., they could do
1404 // let y: Option<u32> = Some(x());
1406 // which would then cause this return type to become `u32`, not
1408 let coercion = fcx.ret_coercion.take().unwrap().into_inner();
1409 let mut actual_return_ty = coercion.complete(&fcx);
1410 if actual_return_ty.is_never() {
1411 actual_return_ty = fcx.next_diverging_ty_var(TypeVariableOrigin {
1412 kind: TypeVariableOriginKind::DivergingFn,
1416 fcx.demand_suptype(span, revealed_ret_ty, actual_return_ty);
1418 // Check that the main return type implements the termination trait.
1419 if let Some(term_id) = tcx.lang_items().termination() {
1420 if let Some((def_id, EntryFnType::Main)) = tcx.entry_fn(LOCAL_CRATE) {
1421 let main_id = hir.as_local_hir_id(def_id).unwrap();
1422 if main_id == fn_id {
1423 let substs = tcx.mk_substs_trait(declared_ret_ty, &[]);
1424 let trait_ref = ty::TraitRef::new(term_id, substs);
1425 let return_ty_span = decl.output.span();
1426 let cause = traits::ObligationCause::new(
1429 ObligationCauseCode::MainFunctionType,
1432 inherited.register_predicate(traits::Obligation::new(
1435 trait_ref.without_const().to_predicate(),
1441 // Check that a function marked as `#[panic_handler]` has signature `fn(&PanicInfo) -> !`
1442 if let Some(panic_impl_did) = tcx.lang_items().panic_impl() {
1443 if panic_impl_did == hir.local_def_id(fn_id) {
1444 if let Some(panic_info_did) = tcx.lang_items().panic_info() {
1445 if declared_ret_ty.kind != ty::Never {
1446 sess.span_err(decl.output.span(), "return type should be `!`");
1449 let inputs = fn_sig.inputs();
1450 let span = hir.span(fn_id);
1451 if inputs.len() == 1 {
1452 let arg_is_panic_info = match inputs[0].kind {
1453 ty::Ref(region, ty, mutbl) => match ty.kind {
1454 ty::Adt(ref adt, _) => {
1455 adt.did == panic_info_did
1456 && mutbl == hir::Mutability::Not
1457 && *region != RegionKind::ReStatic
1464 if !arg_is_panic_info {
1465 sess.span_err(decl.inputs[0].span, "argument should be `&PanicInfo`");
1468 if let Node::Item(item) = hir.get(fn_id) {
1469 if let ItemKind::Fn(_, ref generics, _) = item.kind {
1470 if !generics.params.is_empty() {
1471 sess.span_err(span, "should have no type parameters");
1476 let span = sess.source_map().def_span(span);
1477 sess.span_err(span, "function should have one argument");
1480 sess.err("language item required, but not found: `panic_info`");
1485 // Check that a function marked as `#[alloc_error_handler]` has signature `fn(Layout) -> !`
1486 if let Some(alloc_error_handler_did) = tcx.lang_items().oom() {
1487 if alloc_error_handler_did == hir.local_def_id(fn_id) {
1488 if let Some(alloc_layout_did) = tcx.lang_items().alloc_layout() {
1489 if declared_ret_ty.kind != ty::Never {
1490 sess.span_err(decl.output.span(), "return type should be `!`");
1493 let inputs = fn_sig.inputs();
1494 let span = hir.span(fn_id);
1495 if inputs.len() == 1 {
1496 let arg_is_alloc_layout = match inputs[0].kind {
1497 ty::Adt(ref adt, _) => adt.did == alloc_layout_did,
1501 if !arg_is_alloc_layout {
1502 sess.span_err(decl.inputs[0].span, "argument should be `Layout`");
1505 if let Node::Item(item) = hir.get(fn_id) {
1506 if let ItemKind::Fn(_, ref generics, _) = item.kind {
1507 if !generics.params.is_empty() {
1510 "`#[alloc_error_handler]` function should have no type \
1517 let span = sess.source_map().def_span(span);
1518 sess.span_err(span, "function should have one argument");
1521 sess.err("language item required, but not found: `alloc_layout`");
1529 fn check_struct(tcx: TyCtxt<'_>, id: hir::HirId, span: Span) {
1530 let def_id = tcx.hir().local_def_id(id);
1531 let def = tcx.adt_def(def_id);
1532 def.destructor(tcx); // force the destructor to be evaluated
1533 check_representable(tcx, span, def_id);
1535 if def.repr.simd() {
1536 check_simd(tcx, span, def_id);
1539 check_transparent(tcx, span, def_id);
1540 check_packed(tcx, span, def_id);
1543 fn check_union(tcx: TyCtxt<'_>, id: hir::HirId, span: Span) {
1544 let def_id = tcx.hir().local_def_id(id);
1545 let def = tcx.adt_def(def_id);
1546 def.destructor(tcx); // force the destructor to be evaluated
1547 check_representable(tcx, span, def_id);
1548 check_transparent(tcx, span, def_id);
1549 check_union_fields(tcx, span, def_id);
1550 check_packed(tcx, span, def_id);
1553 /// When the `#![feature(untagged_unions)]` gate is active,
1554 /// check that the fields of the `union` does not contain fields that need dropping.
1555 fn check_union_fields(tcx: TyCtxt<'_>, span: Span, item_def_id: DefId) -> bool {
1556 let item_type = tcx.type_of(item_def_id);
1557 if let ty::Adt(def, substs) = item_type.kind {
1558 assert!(def.is_union());
1559 let fields = &def.non_enum_variant().fields;
1560 let param_env = tcx.param_env(item_def_id);
1561 for field in fields {
1562 let field_ty = field.ty(tcx, substs);
1563 // We are currently checking the type this field came from, so it must be local.
1564 let field_span = tcx.hir().span_if_local(field.did).unwrap();
1565 if field_ty.needs_drop(tcx, param_env) {
1570 "unions may not contain fields that need dropping"
1572 .span_note(field_span, "`std::mem::ManuallyDrop` can be used to wrap the type")
1578 span_bug!(span, "unions must be ty::Adt, but got {:?}", item_type.kind);
1583 /// Checks that an opaque type does not contain cycles and does not use `Self` or `T::Foo`
1584 /// projections that would result in "inheriting lifetimes".
1585 fn check_opaque<'tcx>(
1588 substs: SubstsRef<'tcx>,
1590 origin: &hir::OpaqueTyOrigin,
1592 check_opaque_for_inheriting_lifetimes(tcx, def_id, span);
1593 check_opaque_for_cycles(tcx, def_id, substs, span, origin);
1596 /// Checks that an opaque type does not use `Self` or `T::Foo` projections that would result
1597 /// in "inheriting lifetimes".
1598 fn check_opaque_for_inheriting_lifetimes(tcx: TyCtxt<'tcx>, def_id: DefId, span: Span) {
1600 tcx.hir().expect_item(tcx.hir().as_local_hir_id(def_id).expect("opaque type is not local"));
1602 "check_opaque_for_inheriting_lifetimes: def_id={:?} span={:?} item={:?}",
1607 struct ProhibitOpaqueVisitor<'tcx> {
1608 opaque_identity_ty: Ty<'tcx>,
1609 generics: &'tcx ty::Generics,
1612 impl<'tcx> ty::fold::TypeVisitor<'tcx> for ProhibitOpaqueVisitor<'tcx> {
1613 fn visit_ty(&mut self, t: Ty<'tcx>) -> bool {
1614 debug!("check_opaque_for_inheriting_lifetimes: (visit_ty) t={:?}", t);
1615 if t == self.opaque_identity_ty { false } else { t.super_visit_with(self) }
1618 fn visit_region(&mut self, r: ty::Region<'tcx>) -> bool {
1619 debug!("check_opaque_for_inheriting_lifetimes: (visit_region) r={:?}", r);
1620 if let RegionKind::ReEarlyBound(ty::EarlyBoundRegion { index, .. }) = r {
1621 return *index < self.generics.parent_count as u32;
1624 r.super_visit_with(self)
1628 let prohibit_opaque = match item.kind {
1629 ItemKind::OpaqueTy(hir::OpaqueTy { origin: hir::OpaqueTyOrigin::AsyncFn, .. })
1630 | ItemKind::OpaqueTy(hir::OpaqueTy { origin: hir::OpaqueTyOrigin::FnReturn, .. }) => {
1631 let mut visitor = ProhibitOpaqueVisitor {
1632 opaque_identity_ty: tcx
1633 .mk_opaque(def_id, InternalSubsts::identity_for_item(tcx, def_id)),
1634 generics: tcx.generics_of(def_id),
1636 debug!("check_opaque_for_inheriting_lifetimes: visitor={:?}", visitor);
1638 tcx.predicates_of(def_id)
1641 .any(|(predicate, _)| predicate.visit_with(&mut visitor))
1646 debug!("check_opaque_for_inheriting_lifetimes: prohibit_opaque={:?}", prohibit_opaque);
1647 if prohibit_opaque {
1648 let is_async = match item.kind {
1649 ItemKind::OpaqueTy(hir::OpaqueTy { origin, .. }) => match origin {
1650 hir::OpaqueTyOrigin::AsyncFn => true,
1653 _ => unreachable!(),
1656 tcx.sess.span_err(span, &format!(
1657 "`{}` return type cannot contain a projection or `Self` that references lifetimes from \
1659 if is_async { "async fn" } else { "impl Trait" },
1664 /// Checks that an opaque type does not contain cycles.
1665 fn check_opaque_for_cycles<'tcx>(
1668 substs: SubstsRef<'tcx>,
1670 origin: &hir::OpaqueTyOrigin,
1672 if let Err(partially_expanded_type) = tcx.try_expand_impl_trait_type(def_id, substs) {
1673 if let hir::OpaqueTyOrigin::AsyncFn = origin {
1674 struct_span_err!(tcx.sess, span, E0733, "recursion in an `async fn` requires boxing",)
1675 .span_label(span, "recursive `async fn`")
1676 .note("a recursive `async fn` must be rewritten to return a boxed `dyn Future`")
1680 struct_span_err!(tcx.sess, span, E0720, "opaque type expands to a recursive type",);
1681 err.span_label(span, "expands to a recursive type");
1682 if let ty::Opaque(..) = partially_expanded_type.kind {
1683 err.note("type resolves to itself");
1685 err.note(&format!("expanded type is `{}`", partially_expanded_type));
1692 // Forbid defining intrinsics in Rust code,
1693 // as they must always be defined by the compiler.
1694 fn fn_maybe_err(tcx: TyCtxt<'_>, sp: Span, abi: Abi) {
1695 if let Abi::RustIntrinsic | Abi::PlatformIntrinsic = abi {
1696 tcx.sess.span_err(sp, "intrinsic must be in `extern \"rust-intrinsic\" { ... }` block");
1700 pub fn check_item_type<'tcx>(tcx: TyCtxt<'tcx>, it: &'tcx hir::Item<'tcx>) {
1702 "check_item_type(it.hir_id={}, it.name={})",
1704 tcx.def_path_str(tcx.hir().local_def_id(it.hir_id))
1706 let _indenter = indenter();
1708 // Consts can play a role in type-checking, so they are included here.
1709 hir::ItemKind::Static(..) => {
1710 let def_id = tcx.hir().local_def_id(it.hir_id);
1711 tcx.typeck_tables_of(def_id);
1712 maybe_check_static_with_link_section(tcx, def_id, it.span);
1714 hir::ItemKind::Const(..) => {
1715 tcx.typeck_tables_of(tcx.hir().local_def_id(it.hir_id));
1717 hir::ItemKind::Enum(ref enum_definition, _) => {
1718 check_enum(tcx, it.span, &enum_definition.variants, it.hir_id);
1720 hir::ItemKind::Fn(..) => {} // entirely within check_item_body
1721 hir::ItemKind::Impl { ref items, .. } => {
1722 debug!("ItemKind::Impl {} with id {}", it.ident, it.hir_id);
1723 let impl_def_id = tcx.hir().local_def_id(it.hir_id);
1724 if let Some(impl_trait_ref) = tcx.impl_trait_ref(impl_def_id) {
1725 check_impl_items_against_trait(tcx, it.span, impl_def_id, impl_trait_ref, items);
1726 let trait_def_id = impl_trait_ref.def_id;
1727 check_on_unimplemented(tcx, trait_def_id, it);
1730 hir::ItemKind::Trait(_, _, _, _, ref items) => {
1731 let def_id = tcx.hir().local_def_id(it.hir_id);
1732 check_on_unimplemented(tcx, def_id, it);
1734 for item in items.iter() {
1735 let item = tcx.hir().trait_item(item.id);
1736 if let hir::TraitItemKind::Method(sig, _) = &item.kind {
1737 let abi = sig.header.abi;
1738 fn_maybe_err(tcx, item.ident.span, abi);
1742 hir::ItemKind::Struct(..) => {
1743 check_struct(tcx, it.hir_id, it.span);
1745 hir::ItemKind::Union(..) => {
1746 check_union(tcx, it.hir_id, it.span);
1748 hir::ItemKind::OpaqueTy(hir::OpaqueTy { origin, .. }) => {
1749 let def_id = tcx.hir().local_def_id(it.hir_id);
1751 let substs = InternalSubsts::identity_for_item(tcx, def_id);
1752 check_opaque(tcx, def_id, substs, it.span, &origin);
1754 hir::ItemKind::TyAlias(..) => {
1755 let def_id = tcx.hir().local_def_id(it.hir_id);
1756 let pty_ty = tcx.type_of(def_id);
1757 let generics = tcx.generics_of(def_id);
1758 check_bounds_are_used(tcx, &generics, pty_ty);
1760 hir::ItemKind::ForeignMod(ref m) => {
1761 check_abi(tcx, it.span, m.abi);
1763 if m.abi == Abi::RustIntrinsic {
1764 for item in m.items {
1765 intrinsic::check_intrinsic_type(tcx, item);
1767 } else if m.abi == Abi::PlatformIntrinsic {
1768 for item in m.items {
1769 intrinsic::check_platform_intrinsic_type(tcx, item);
1772 for item in m.items {
1773 let generics = tcx.generics_of(tcx.hir().local_def_id(item.hir_id));
1774 let own_counts = generics.own_counts();
1775 if generics.params.len() - own_counts.lifetimes != 0 {
1776 let (kinds, kinds_pl, egs) = match (own_counts.types, own_counts.consts) {
1777 (_, 0) => ("type", "types", Some("u32")),
1778 // We don't specify an example value, because we can't generate
1779 // a valid value for any type.
1780 (0, _) => ("const", "consts", None),
1781 _ => ("type or const", "types or consts", None),
1787 "foreign items may not have {} parameters",
1790 .span_label(item.span, &format!("can't have {} parameters", kinds))
1792 // FIXME: once we start storing spans for type arguments, turn this
1793 // into a suggestion.
1795 "replace the {} parameters with concrete {}{}",
1798 egs.map(|egs| format!(" like `{}`", egs)).unwrap_or_default(),
1804 if let hir::ForeignItemKind::Fn(ref fn_decl, _, _) = item.kind {
1805 require_c_abi_if_c_variadic(tcx, fn_decl, m.abi, item.span);
1810 _ => { /* nothing to do */ }
1814 fn maybe_check_static_with_link_section(tcx: TyCtxt<'_>, id: DefId, span: Span) {
1815 // Only restricted on wasm32 target for now
1816 if !tcx.sess.opts.target_triple.triple().starts_with("wasm32") {
1820 // If `#[link_section]` is missing, then nothing to verify
1821 let attrs = tcx.codegen_fn_attrs(id);
1822 if attrs.link_section.is_none() {
1826 // For the wasm32 target statics with `#[link_section]` are placed into custom
1827 // sections of the final output file, but this isn't link custom sections of
1828 // other executable formats. Namely we can only embed a list of bytes,
1829 // nothing with pointers to anything else or relocations. If any relocation
1830 // show up, reject them here.
1831 // `#[link_section]` may contain arbitrary, or even undefined bytes, but it is
1832 // the consumer's responsibility to ensure all bytes that have been read
1833 // have defined values.
1834 match tcx.const_eval_poly(id) {
1835 Ok(ConstValue::ByRef { alloc, .. }) => {
1836 if alloc.relocations().len() != 0 {
1837 let msg = "statics with a custom `#[link_section]` must be a \
1838 simple list of bytes on the wasm target with no \
1839 extra levels of indirection such as references";
1840 tcx.sess.span_err(span, msg);
1843 Ok(_) => bug!("Matching on non-ByRef static"),
1848 fn check_on_unimplemented(tcx: TyCtxt<'_>, trait_def_id: DefId, item: &hir::Item<'_>) {
1849 let item_def_id = tcx.hir().local_def_id(item.hir_id);
1850 // an error would be reported if this fails.
1851 let _ = traits::OnUnimplementedDirective::of_item(tcx, trait_def_id, item_def_id);
1854 fn report_forbidden_specialization(
1856 impl_item: &hir::ImplItem<'_>,
1859 let mut err = struct_span_err!(
1863 "`{}` specializes an item from a parent `impl`, but \
1864 that item is not marked `default`",
1867 err.span_label(impl_item.span, format!("cannot specialize default item `{}`", impl_item.ident));
1869 match tcx.span_of_impl(parent_impl) {
1871 err.span_label(span, "parent `impl` is here");
1873 "to specialize, `{}` in the parent `impl` must be marked `default`",
1878 err.note(&format!("parent implementation is in crate `{}`", cname));
1885 fn check_specialization_validity<'tcx>(
1887 trait_def: &ty::TraitDef,
1888 trait_item: &ty::AssocItem,
1890 impl_item: &hir::ImplItem<'_>,
1892 let kind = match impl_item.kind {
1893 hir::ImplItemKind::Const(..) => ty::AssocKind::Const,
1894 hir::ImplItemKind::Method(..) => ty::AssocKind::Method,
1895 hir::ImplItemKind::OpaqueTy(..) => ty::AssocKind::OpaqueTy,
1896 hir::ImplItemKind::TyAlias(_) => ty::AssocKind::Type,
1899 let mut ancestor_impls = trait_def
1900 .ancestors(tcx, impl_id)
1902 .filter_map(|parent| {
1903 if parent.is_from_trait() {
1906 Some((parent, parent.item(tcx, trait_item.ident, kind, trait_def.def_id)))
1911 if ancestor_impls.peek().is_none() {
1912 // No parent, nothing to specialize.
1916 let opt_result = ancestor_impls.find_map(|(parent_impl, parent_item)| {
1918 // Parent impl exists, and contains the parent item we're trying to specialize, but
1919 // doesn't mark it `default`.
1920 Some(parent_item) if traits::impl_item_is_final(tcx, &parent_item) => {
1921 Some(Err(parent_impl.def_id()))
1924 // Parent impl contains item and makes it specializable.
1925 Some(_) => Some(Ok(())),
1927 // Parent impl doesn't mention the item. This means it's inherited from the
1928 // grandparent. In that case, if parent is a `default impl`, inherited items use the
1929 // "defaultness" from the grandparent, else they are final.
1931 if traits::impl_is_default(tcx, parent_impl.def_id()) {
1934 Some(Err(parent_impl.def_id()))
1940 // If `opt_result` is `None`, we have only encoutered `default impl`s that don't contain the
1941 // item. This is allowed, the item isn't actually getting specialized here.
1942 let result = opt_result.unwrap_or(Ok(()));
1944 if let Err(parent_impl) = result {
1945 report_forbidden_specialization(tcx, impl_item, parent_impl);
1949 fn check_impl_items_against_trait<'tcx>(
1951 full_impl_span: Span,
1953 impl_trait_ref: ty::TraitRef<'tcx>,
1954 impl_item_refs: &[hir::ImplItemRef<'_>],
1956 let impl_span = tcx.sess.source_map().def_span(full_impl_span);
1958 // If the trait reference itself is erroneous (so the compilation is going
1959 // to fail), skip checking the items here -- the `impl_item` table in `tcx`
1960 // isn't populated for such impls.
1961 if impl_trait_ref.references_error() {
1965 // Locate trait definition and items
1966 let trait_def = tcx.trait_def(impl_trait_ref.def_id);
1968 let impl_items = || impl_item_refs.iter().map(|iiref| tcx.hir().impl_item(iiref.id));
1970 // Check existing impl methods to see if they are both present in trait
1971 // and compatible with trait signature
1972 for impl_item in impl_items() {
1973 let namespace = impl_item.kind.namespace();
1974 let ty_impl_item = tcx.associated_item(tcx.hir().local_def_id(impl_item.hir_id));
1975 let ty_trait_item = tcx
1976 .associated_items(impl_trait_ref.def_id)
1977 .find_by_name_and_namespace(tcx, ty_impl_item.ident, namespace, impl_trait_ref.def_id)
1979 // Not compatible, but needed for the error message
1980 tcx.associated_items(impl_trait_ref.def_id)
1981 .filter_by_name(tcx, ty_impl_item.ident, impl_trait_ref.def_id)
1985 // Check that impl definition matches trait definition
1986 if let Some(ty_trait_item) = ty_trait_item {
1987 match impl_item.kind {
1988 hir::ImplItemKind::Const(..) => {
1989 // Find associated const definition.
1990 if ty_trait_item.kind == ty::AssocKind::Const {
1999 let mut err = struct_span_err!(
2003 "item `{}` is an associated const, \
2004 which doesn't match its trait `{}`",
2006 impl_trait_ref.print_only_trait_path()
2008 err.span_label(impl_item.span, "does not match trait");
2009 // We can only get the spans from local trait definition
2010 // Same for E0324 and E0325
2011 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
2012 err.span_label(trait_span, "item in trait");
2017 hir::ImplItemKind::Method(..) => {
2018 let opt_trait_span = tcx.hir().span_if_local(ty_trait_item.def_id);
2019 if ty_trait_item.kind == ty::AssocKind::Method {
2020 compare_impl_method(
2029 let mut err = struct_span_err!(
2033 "item `{}` is an associated method, \
2034 which doesn't match its trait `{}`",
2036 impl_trait_ref.print_only_trait_path()
2038 err.span_label(impl_item.span, "does not match trait");
2039 if let Some(trait_span) = opt_trait_span {
2040 err.span_label(trait_span, "item in trait");
2045 hir::ImplItemKind::OpaqueTy(..) | hir::ImplItemKind::TyAlias(_) => {
2046 let opt_trait_span = tcx.hir().span_if_local(ty_trait_item.def_id);
2047 if ty_trait_item.kind == ty::AssocKind::Type {
2057 let mut err = struct_span_err!(
2061 "item `{}` is an associated type, \
2062 which doesn't match its trait `{}`",
2064 impl_trait_ref.print_only_trait_path()
2066 err.span_label(impl_item.span, "does not match trait");
2067 if let Some(trait_span) = opt_trait_span {
2068 err.span_label(trait_span, "item in trait");
2075 check_specialization_validity(tcx, trait_def, &ty_trait_item, impl_id, impl_item);
2079 // Check for missing items from trait
2080 let mut missing_items = Vec::new();
2081 for trait_item in tcx.associated_items(impl_trait_ref.def_id).in_definition_order() {
2082 let is_implemented = trait_def
2083 .ancestors(tcx, impl_id)
2084 .leaf_def(tcx, trait_item.ident, trait_item.kind)
2085 .map(|node_item| !node_item.node.is_from_trait())
2088 if !is_implemented && !traits::impl_is_default(tcx, impl_id) {
2089 if !trait_item.defaultness.has_value() {
2090 missing_items.push(*trait_item);
2095 if !missing_items.is_empty() {
2096 missing_items_err(tcx, impl_span, &missing_items, full_impl_span);
2100 fn missing_items_err(
2103 missing_items: &[ty::AssocItem],
2104 full_impl_span: Span,
2106 let missing_items_msg = missing_items
2108 .map(|trait_item| trait_item.ident.to_string())
2109 .collect::<Vec<_>>()
2112 let mut err = struct_span_err!(
2116 "not all trait items implemented, missing: `{}`",
2119 err.span_label(impl_span, format!("missing `{}` in implementation", missing_items_msg));
2121 // `Span` before impl block closing brace.
2122 let hi = full_impl_span.hi() - BytePos(1);
2123 // Point at the place right before the closing brace of the relevant `impl` to suggest
2124 // adding the associated item at the end of its body.
2125 let sugg_sp = full_impl_span.with_lo(hi).with_hi(hi);
2126 // Obtain the level of indentation ending in `sugg_sp`.
2127 let indentation = tcx.sess.source_map().span_to_margin(sugg_sp).unwrap_or(0);
2128 // Make the whitespace that will make the suggestion have the right indentation.
2129 let padding: String = (0..indentation).map(|_| " ").collect();
2131 for trait_item in missing_items {
2132 let snippet = suggestion_signature(&trait_item, tcx);
2133 let code = format!("{}{}\n{}", padding, snippet, padding);
2134 let msg = format!("implement the missing item: `{}`", snippet);
2135 let appl = Applicability::HasPlaceholders;
2136 if let Some(span) = tcx.hir().span_if_local(trait_item.def_id) {
2137 err.span_label(span, format!("`{}` from trait", trait_item.ident));
2138 err.tool_only_span_suggestion(sugg_sp, &msg, code, appl);
2140 err.span_suggestion_hidden(sugg_sp, &msg, code, appl);
2146 /// Resugar `ty::GenericPredicates` in a way suitable to be used in structured suggestions.
2147 fn bounds_from_generic_predicates(
2149 predicates: ty::GenericPredicates<'_>,
2150 ) -> (String, String) {
2151 let mut types: FxHashMap<Ty<'_>, Vec<DefId>> = FxHashMap::default();
2152 let mut projections = vec![];
2153 for (predicate, _) in predicates.predicates {
2154 debug!("predicate {:?}", predicate);
2156 ty::Predicate::Trait(trait_predicate, _) => {
2157 let entry = types.entry(trait_predicate.skip_binder().self_ty()).or_default();
2158 let def_id = trait_predicate.skip_binder().def_id();
2159 if Some(def_id) != tcx.lang_items().sized_trait() {
2160 // Type params are `Sized` by default, do not add that restriction to the list
2161 // if it is a positive requirement.
2162 entry.push(trait_predicate.skip_binder().def_id());
2165 ty::Predicate::Projection(projection_pred) => {
2166 projections.push(projection_pred);
2171 let generics = if types.is_empty() {
2178 .filter_map(|t| match t.kind {
2179 ty::Param(_) => Some(t.to_string()),
2180 // Avoid suggesting the following:
2181 // fn foo<T, <T as Trait>::Bar>(_: T) where T: Trait, <T as Trait>::Bar: Other {}
2184 .collect::<Vec<_>>()
2188 let mut where_clauses = vec![];
2189 for (ty, bounds) in types {
2190 for bound in &bounds {
2191 where_clauses.push(format!("{}: {}", ty, tcx.def_path_str(*bound)));
2194 for projection in &projections {
2195 let p = projection.skip_binder();
2196 // FIXME: this is not currently supported syntax, we should be looking at the `types` and
2197 // insert the associated types where they correspond, but for now let's be "lazy" and
2198 // propose this instead of the following valid resugaring:
2199 // `T: Trait, Trait::Assoc = K` → `T: Trait<Assoc = K>`
2200 where_clauses.push(format!("{} = {}", tcx.def_path_str(p.projection_ty.item_def_id), p.ty));
2202 let where_clauses = if where_clauses.is_empty() {
2205 format!(" where {}", where_clauses.join(", "))
2207 (generics, where_clauses)
2210 /// Return placeholder code for the given function.
2211 fn fn_sig_suggestion(
2213 sig: &ty::FnSig<'_>,
2215 predicates: ty::GenericPredicates<'_>,
2221 Some(match ty.kind {
2222 ty::Param(param) if param.name == kw::SelfUpper => "self".to_string(),
2223 ty::Ref(reg, ref_ty, mutability) => {
2224 let reg = match &format!("{}", reg)[..] {
2225 "'_" | "" => String::new(),
2226 reg => format!("{} ", reg),
2229 ty::Param(param) if param.name == kw::SelfUpper => {
2230 format!("&{}{}self", reg, mutability.prefix_str())
2232 _ => format!("_: {:?}", ty),
2235 _ => format!("_: {:?}", ty),
2238 .chain(std::iter::once(if sig.c_variadic { Some("...".to_string()) } else { None }))
2239 .filter_map(|arg| arg)
2240 .collect::<Vec<String>>()
2242 let output = sig.output();
2243 let output = if !output.is_unit() { format!(" -> {:?}", output) } else { String::new() };
2245 let unsafety = sig.unsafety.prefix_str();
2246 let (generics, where_clauses) = bounds_from_generic_predicates(tcx, predicates);
2248 // FIXME: this is not entirely correct, as the lifetimes from borrowed params will
2249 // not be present in the `fn` definition, not will we account for renamed
2250 // lifetimes between the `impl` and the `trait`, but this should be good enough to
2251 // fill in a significant portion of the missing code, and other subsequent
2252 // suggestions can help the user fix the code.
2254 "{}fn {}{}({}){}{} {{ todo!() }}",
2255 unsafety, ident, generics, args, output, where_clauses
2259 /// Return placeholder code for the given associated item.
2260 /// Similar to `ty::AssocItem::suggestion`, but appropriate for use as the code snippet of a
2261 /// structured suggestion.
2262 fn suggestion_signature(assoc: &ty::AssocItem, tcx: TyCtxt<'_>) -> String {
2264 ty::AssocKind::Method => {
2265 // We skip the binder here because the binder would deanonymize all
2266 // late-bound regions, and we don't want method signatures to show up
2267 // `as for<'r> fn(&'r MyType)`. Pretty-printing handles late-bound
2268 // regions just fine, showing `fn(&MyType)`.
2271 tcx.fn_sig(assoc.def_id).skip_binder(),
2273 tcx.predicates_of(assoc.def_id),
2276 ty::AssocKind::Type => format!("type {} = Type;", assoc.ident),
2277 // FIXME(type_alias_impl_trait): we should print bounds here too.
2278 ty::AssocKind::OpaqueTy => format!("type {} = Type;", assoc.ident),
2279 ty::AssocKind::Const => {
2280 let ty = tcx.type_of(assoc.def_id);
2281 let val = expr::ty_kind_suggestion(ty).unwrap_or("value");
2282 format!("const {}: {:?} = {};", assoc.ident, ty, val)
2287 /// Checks whether a type can be represented in memory. In particular, it
2288 /// identifies types that contain themselves without indirection through a
2289 /// pointer, which would mean their size is unbounded.
2290 fn check_representable(tcx: TyCtxt<'_>, sp: Span, item_def_id: DefId) -> bool {
2291 let rty = tcx.type_of(item_def_id);
2293 // Check that it is possible to represent this type. This call identifies
2294 // (1) types that contain themselves and (2) types that contain a different
2295 // recursive type. It is only necessary to throw an error on those that
2296 // contain themselves. For case 2, there must be an inner type that will be
2297 // caught by case 1.
2298 match rty.is_representable(tcx, sp) {
2299 Representability::SelfRecursive(spans) => {
2300 let mut err = recursive_type_with_infinite_size_error(tcx, item_def_id);
2302 err.span_label(span, "recursive without indirection");
2307 Representability::Representable | Representability::ContainsRecursive => (),
2312 pub fn check_simd(tcx: TyCtxt<'_>, sp: Span, def_id: DefId) {
2313 let t = tcx.type_of(def_id);
2314 if let ty::Adt(def, substs) = t.kind {
2315 if def.is_struct() {
2316 let fields = &def.non_enum_variant().fields;
2317 if fields.is_empty() {
2318 struct_span_err!(tcx.sess, sp, E0075, "SIMD vector cannot be empty").emit();
2321 let e = fields[0].ty(tcx, substs);
2322 if !fields.iter().all(|f| f.ty(tcx, substs) == e) {
2323 struct_span_err!(tcx.sess, sp, E0076, "SIMD vector should be homogeneous")
2324 .span_label(sp, "SIMD elements must have the same type")
2329 ty::Param(_) => { /* struct<T>(T, T, T, T) is ok */ }
2330 _ if e.is_machine() => { /* struct(u8, u8, u8, u8) is ok */ }
2336 "SIMD vector element type should be machine type"
2346 fn check_packed(tcx: TyCtxt<'_>, sp: Span, def_id: DefId) {
2347 let repr = tcx.adt_def(def_id).repr;
2349 for attr in tcx.get_attrs(def_id).iter() {
2350 for r in attr::find_repr_attrs(&tcx.sess.parse_sess, attr) {
2351 if let attr::ReprPacked(pack) = r {
2352 if let Some(repr_pack) = repr.pack {
2353 if pack as u64 != repr_pack.bytes() {
2358 "type has conflicting packed representation hints"
2366 if repr.align.is_some() {
2371 "type has conflicting packed and align representation hints"
2375 if let Some(def_spans) = check_packed_inner(tcx, def_id, &mut vec![]) {
2376 let mut err = struct_span_err!(
2380 "packed type cannot transitively contain a `#[repr(align)]` type"
2383 let hir = tcx.hir();
2384 if let Some(hir_id) = hir.as_local_hir_id(def_spans[0].0) {
2385 if let Node::Item(Item { ident, .. }) = hir.get(hir_id) {
2387 tcx.def_span(def_spans[0].0),
2388 &format!("`{}` has a `#[repr(align)]` attribute", ident),
2393 if def_spans.len() > 2 {
2394 let mut first = true;
2395 for (adt_def, span) in def_spans.iter().skip(1).rev() {
2396 if let Some(hir_id) = hir.as_local_hir_id(*adt_def) {
2397 if let Node::Item(Item { ident, .. }) = hir.get(hir_id) {
2402 "`{}` contains a field of type `{}`",
2403 tcx.type_of(def_id),
2407 format!("...which contains a field of type `{}`", ident)
2422 fn check_packed_inner(
2425 stack: &mut Vec<DefId>,
2426 ) -> Option<Vec<(DefId, Span)>> {
2427 if let ty::Adt(def, substs) = tcx.type_of(def_id).kind {
2428 if def.is_struct() || def.is_union() {
2429 if def.repr.align.is_some() {
2430 return Some(vec![(def.did, DUMMY_SP)]);
2434 for field in &def.non_enum_variant().fields {
2435 if let ty::Adt(def, _) = field.ty(tcx, substs).kind {
2436 if !stack.contains(&def.did) {
2437 if let Some(mut defs) = check_packed_inner(tcx, def.did, stack) {
2438 defs.push((def.did, field.ident.span));
2451 /// Emit an error when encountering more or less than one variant in a transparent enum.
2452 fn bad_variant_count<'tcx>(tcx: TyCtxt<'tcx>, adt: &'tcx ty::AdtDef, sp: Span, did: DefId) {
2453 let variant_spans: Vec<_> = adt
2456 .map(|variant| tcx.hir().span_if_local(variant.def_id).unwrap())
2458 let msg = format!("needs exactly one variant, but has {}", adt.variants.len(),);
2459 let mut err = struct_span_err!(tcx.sess, sp, E0731, "transparent enum {}", msg);
2460 err.span_label(sp, &msg);
2461 if let [start @ .., end] = &*variant_spans {
2462 for variant_span in start {
2463 err.span_label(*variant_span, "");
2465 err.span_label(*end, &format!("too many variants in `{}`", tcx.def_path_str(did)));
2470 /// Emit an error when encountering more or less than one non-zero-sized field in a transparent
2472 fn bad_non_zero_sized_fields<'tcx>(
2474 adt: &'tcx ty::AdtDef,
2476 field_spans: impl Iterator<Item = Span>,
2479 let msg = format!("needs exactly one non-zero-sized field, but has {}", field_count);
2480 let mut err = struct_span_err!(
2484 "{}transparent {} {}",
2485 if adt.is_enum() { "the variant of a " } else { "" },
2489 err.span_label(sp, &msg);
2490 for sp in field_spans {
2491 err.span_label(sp, "this field is non-zero-sized");
2496 fn check_transparent(tcx: TyCtxt<'_>, sp: Span, def_id: DefId) {
2497 let adt = tcx.adt_def(def_id);
2498 if !adt.repr.transparent() {
2501 let sp = tcx.sess.source_map().def_span(sp);
2503 if adt.is_union() && !tcx.features().transparent_unions {
2505 &tcx.sess.parse_sess,
2506 sym::transparent_unions,
2508 "transparent unions are unstable",
2513 if adt.variants.len() != 1 {
2514 bad_variant_count(tcx, adt, sp, def_id);
2515 if adt.variants.is_empty() {
2516 // Don't bother checking the fields. No variants (and thus no fields) exist.
2521 // For each field, figure out if it's known to be a ZST and align(1)
2522 let field_infos = adt.all_fields().map(|field| {
2523 let ty = field.ty(tcx, InternalSubsts::identity_for_item(tcx, field.did));
2524 let param_env = tcx.param_env(field.did);
2525 let layout = tcx.layout_of(param_env.and(ty));
2526 // We are currently checking the type this field came from, so it must be local
2527 let span = tcx.hir().span_if_local(field.did).unwrap();
2528 let zst = layout.map(|layout| layout.is_zst()).unwrap_or(false);
2529 let align1 = layout.map(|layout| layout.align.abi.bytes() == 1).unwrap_or(false);
2533 let non_zst_fields =
2534 field_infos.clone().filter_map(|(span, zst, _align1)| if !zst { Some(span) } else { None });
2535 let non_zst_count = non_zst_fields.clone().count();
2536 if non_zst_count != 1 {
2537 bad_non_zero_sized_fields(tcx, adt, non_zst_count, non_zst_fields, sp);
2539 for (span, zst, align1) in field_infos {
2545 "zero-sized field in transparent {} has alignment larger than 1",
2548 .span_label(span, "has alignment larger than 1")
2554 #[allow(trivial_numeric_casts)]
2555 pub fn check_enum<'tcx>(
2558 vs: &'tcx [hir::Variant<'tcx>],
2561 let def_id = tcx.hir().local_def_id(id);
2562 let def = tcx.adt_def(def_id);
2563 def.destructor(tcx); // force the destructor to be evaluated
2566 let attributes = tcx.get_attrs(def_id);
2567 if let Some(attr) = attr::find_by_name(&attributes, sym::repr) {
2572 "unsupported representation for zero-variant enum"
2574 .span_label(sp, "zero-variant enum")
2579 let repr_type_ty = def.repr.discr_type().to_ty(tcx);
2580 if repr_type_ty == tcx.types.i128 || repr_type_ty == tcx.types.u128 {
2581 if !tcx.features().repr128 {
2583 &tcx.sess.parse_sess,
2586 "repr with 128-bit type is unstable",
2593 if let Some(ref e) = v.disr_expr {
2594 tcx.typeck_tables_of(tcx.hir().local_def_id(e.hir_id));
2598 if tcx.adt_def(def_id).repr.int.is_none() && tcx.features().arbitrary_enum_discriminant {
2599 let is_unit = |var: &hir::Variant<'_>| match var.data {
2600 hir::VariantData::Unit(..) => true,
2604 let has_disr = |var: &hir::Variant<'_>| var.disr_expr.is_some();
2605 let has_non_units = vs.iter().any(|var| !is_unit(var));
2606 let disr_units = vs.iter().any(|var| is_unit(&var) && has_disr(&var));
2607 let disr_non_unit = vs.iter().any(|var| !is_unit(&var) && has_disr(&var));
2609 if disr_non_unit || (disr_units && has_non_units) {
2611 struct_span_err!(tcx.sess, sp, E0732, "`#[repr(inttype)]` must be specified");
2616 let mut disr_vals: Vec<Discr<'tcx>> = Vec::with_capacity(vs.len());
2617 for ((_, discr), v) in def.discriminants(tcx).zip(vs) {
2618 // Check for duplicate discriminant values
2619 if let Some(i) = disr_vals.iter().position(|&x| x.val == discr.val) {
2620 let variant_did = def.variants[VariantIdx::new(i)].def_id;
2621 let variant_i_hir_id = tcx.hir().as_local_hir_id(variant_did).unwrap();
2622 let variant_i = tcx.hir().expect_variant(variant_i_hir_id);
2623 let i_span = match variant_i.disr_expr {
2624 Some(ref expr) => tcx.hir().span(expr.hir_id),
2625 None => tcx.hir().span(variant_i_hir_id),
2627 let span = match v.disr_expr {
2628 Some(ref expr) => tcx.hir().span(expr.hir_id),
2635 "discriminant value `{}` already exists",
2638 .span_label(i_span, format!("first use of `{}`", disr_vals[i]))
2639 .span_label(span, format!("enum already has `{}`", disr_vals[i]))
2642 disr_vals.push(discr);
2645 check_representable(tcx, sp, def_id);
2646 check_transparent(tcx, sp, def_id);
2649 fn report_unexpected_variant_res(tcx: TyCtxt<'_>, res: Res, span: Span, qpath: &QPath<'_>) {
2654 "expected unit struct, unit variant or constant, found {} `{}`",
2656 hir::print::to_string(&tcx.hir(), |s| s.print_qpath(qpath, false))
2661 impl<'a, 'tcx> AstConv<'tcx> for FnCtxt<'a, 'tcx> {
2662 fn tcx<'b>(&'b self) -> TyCtxt<'tcx> {
2666 fn item_def_id(&self) -> Option<DefId> {
2670 fn default_constness_for_trait_bounds(&self) -> hir::Constness {
2671 // FIXME: refactor this into a method
2672 let node = self.tcx.hir().get(self.body_id);
2673 if let Some(fn_like) = FnLikeNode::from_node(node) {
2676 hir::Constness::NotConst
2680 fn get_type_parameter_bounds(&self, _: Span, def_id: DefId) -> ty::GenericPredicates<'tcx> {
2682 let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
2683 let item_id = tcx.hir().ty_param_owner(hir_id);
2684 let item_def_id = tcx.hir().local_def_id(item_id);
2685 let generics = tcx.generics_of(item_def_id);
2686 let index = generics.param_def_id_to_index[&def_id];
2687 ty::GenericPredicates {
2689 predicates: tcx.arena.alloc_from_iter(self.param_env.caller_bounds.iter().filter_map(
2690 |&predicate| match predicate {
2691 ty::Predicate::Trait(ref data, _)
2692 if data.skip_binder().self_ty().is_param(index) =>
2694 // HACK(eddyb) should get the original `Span`.
2695 let span = tcx.def_span(def_id);
2696 Some((predicate, span))
2704 fn re_infer(&self, def: Option<&ty::GenericParamDef>, span: Span) -> Option<ty::Region<'tcx>> {
2706 Some(def) => infer::EarlyBoundRegion(span, def.name),
2707 None => infer::MiscVariable(span),
2709 Some(self.next_region_var(v))
2712 fn allow_ty_infer(&self) -> bool {
2716 fn ty_infer(&self, param: Option<&ty::GenericParamDef>, span: Span) -> Ty<'tcx> {
2717 if let Some(param) = param {
2718 if let GenericArgKind::Type(ty) = self.var_for_def(span, param).unpack() {
2723 self.next_ty_var(TypeVariableOrigin {
2724 kind: TypeVariableOriginKind::TypeInference,
2733 param: Option<&ty::GenericParamDef>,
2735 ) -> &'tcx Const<'tcx> {
2736 if let Some(param) = param {
2737 if let GenericArgKind::Const(ct) = self.var_for_def(span, param).unpack() {
2742 self.next_const_var(
2744 ConstVariableOrigin { kind: ConstVariableOriginKind::ConstInference, span },
2749 fn projected_ty_from_poly_trait_ref(
2753 item_segment: &hir::PathSegment<'_>,
2754 poly_trait_ref: ty::PolyTraitRef<'tcx>,
2756 let (trait_ref, _) = self.replace_bound_vars_with_fresh_vars(
2758 infer::LateBoundRegionConversionTime::AssocTypeProjection(item_def_id),
2762 let item_substs = <dyn AstConv<'tcx>>::create_substs_for_associated_item(
2771 self.tcx().mk_projection(item_def_id, item_substs)
2774 fn normalize_ty(&self, span: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
2775 if ty.has_escaping_bound_vars() {
2776 ty // FIXME: normalization and escaping regions
2778 self.normalize_associated_types_in(span, &ty)
2782 fn set_tainted_by_errors(&self) {
2783 self.infcx.set_tainted_by_errors()
2786 fn record_ty(&self, hir_id: hir::HirId, ty: Ty<'tcx>, _span: Span) {
2787 self.write_ty(hir_id, ty)
2791 /// Controls whether the arguments are tupled. This is used for the call
2794 /// Tupling means that all call-side arguments are packed into a tuple and
2795 /// passed as a single parameter. For example, if tupling is enabled, this
2798 /// fn f(x: (isize, isize))
2800 /// Can be called as:
2807 #[derive(Clone, Eq, PartialEq)]
2808 enum TupleArgumentsFlag {
2813 /// Controls how we perform fallback for unconstrained
2816 /// Do not fallback type variables to opaque types.
2818 /// Perform all possible kinds of fallback, including
2819 /// turning type variables to opaque types.
2823 impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
2825 inh: &'a Inherited<'a, 'tcx>,
2826 param_env: ty::ParamEnv<'tcx>,
2827 body_id: hir::HirId,
2828 ) -> FnCtxt<'a, 'tcx> {
2832 err_count_on_creation: inh.tcx.sess.err_count(),
2834 ret_coercion_span: RefCell::new(None),
2835 resume_yield_tys: None,
2836 ps: RefCell::new(UnsafetyState::function(hir::Unsafety::Normal, hir::CRATE_HIR_ID)),
2837 diverges: Cell::new(Diverges::Maybe),
2838 has_errors: Cell::new(false),
2839 enclosing_breakables: RefCell::new(EnclosingBreakables {
2841 by_id: Default::default(),
2847 pub fn sess(&self) -> &Session {
2851 pub fn errors_reported_since_creation(&self) -> bool {
2852 self.tcx.sess.err_count() > self.err_count_on_creation
2855 /// Produces warning on the given node, if the current point in the
2856 /// function is unreachable, and there hasn't been another warning.
2857 fn warn_if_unreachable(&self, id: hir::HirId, span: Span, kind: &str) {
2858 // FIXME: Combine these two 'if' expressions into one once
2859 // let chains are implemented
2860 if let Diverges::Always { span: orig_span, custom_note } = self.diverges.get() {
2861 // If span arose from a desugaring of `if` or `while`, then it is the condition itself,
2862 // which diverges, that we are about to lint on. This gives suboptimal diagnostics.
2863 // Instead, stop here so that the `if`- or `while`-expression's block is linted instead.
2864 if !span.is_desugaring(DesugaringKind::CondTemporary)
2865 && !span.is_desugaring(DesugaringKind::Async)
2866 && !orig_span.is_desugaring(DesugaringKind::Await)
2868 self.diverges.set(Diverges::WarnedAlways);
2870 debug!("warn_if_unreachable: id={:?} span={:?} kind={}", id, span, kind);
2872 self.tcx().struct_span_lint_hir(lint::builtin::UNREACHABLE_CODE, id, span, |lint| {
2873 let msg = format!("unreachable {}", kind);
2875 .span_label(span, &msg)
2879 .unwrap_or("any code following this expression is unreachable"),
2887 pub fn cause(&self, span: Span, code: ObligationCauseCode<'tcx>) -> ObligationCause<'tcx> {
2888 ObligationCause::new(span, self.body_id, code)
2891 pub fn misc(&self, span: Span) -> ObligationCause<'tcx> {
2892 self.cause(span, ObligationCauseCode::MiscObligation)
2895 /// Resolves type and const variables in `ty` if possible. Unlike the infcx
2896 /// version (resolve_vars_if_possible), this version will
2897 /// also select obligations if it seems useful, in an effort
2898 /// to get more type information.
2899 fn resolve_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
2900 debug!("resolve_vars_with_obligations(ty={:?})", ty);
2902 // No Infer()? Nothing needs doing.
2903 if !ty.has_infer_types_or_consts() {
2904 debug!("resolve_vars_with_obligations: ty={:?}", ty);
2908 // If `ty` is a type variable, see whether we already know what it is.
2909 ty = self.resolve_vars_if_possible(&ty);
2910 if !ty.has_infer_types_or_consts() {
2911 debug!("resolve_vars_with_obligations: ty={:?}", ty);
2915 // If not, try resolving pending obligations as much as
2916 // possible. This can help substantially when there are
2917 // indirect dependencies that don't seem worth tracking
2919 self.select_obligations_where_possible(false, |_| {});
2920 ty = self.resolve_vars_if_possible(&ty);
2922 debug!("resolve_vars_with_obligations: ty={:?}", ty);
2926 fn record_deferred_call_resolution(
2928 closure_def_id: DefId,
2929 r: DeferredCallResolution<'tcx>,
2931 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
2932 deferred_call_resolutions.entry(closure_def_id).or_default().push(r);
2935 fn remove_deferred_call_resolutions(
2937 closure_def_id: DefId,
2938 ) -> Vec<DeferredCallResolution<'tcx>> {
2939 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
2940 deferred_call_resolutions.remove(&closure_def_id).unwrap_or(vec![])
2943 pub fn tag(&self) -> String {
2944 format!("{:p}", self)
2947 pub fn local_ty(&self, span: Span, nid: hir::HirId) -> LocalTy<'tcx> {
2948 self.locals.borrow().get(&nid).cloned().unwrap_or_else(|| {
2949 span_bug!(span, "no type for local variable {}", self.tcx.hir().node_to_string(nid))
2954 pub fn write_ty(&self, id: hir::HirId, ty: Ty<'tcx>) {
2956 "write_ty({:?}, {:?}) in fcx {}",
2958 self.resolve_vars_if_possible(&ty),
2961 self.tables.borrow_mut().node_types_mut().insert(id, ty);
2963 if ty.references_error() {
2964 self.has_errors.set(true);
2965 self.set_tainted_by_errors();
2969 pub fn write_field_index(&self, hir_id: hir::HirId, index: usize) {
2970 self.tables.borrow_mut().field_indices_mut().insert(hir_id, index);
2973 fn write_resolution(&self, hir_id: hir::HirId, r: Result<(DefKind, DefId), ErrorReported>) {
2974 self.tables.borrow_mut().type_dependent_defs_mut().insert(hir_id, r);
2977 pub fn write_method_call(&self, hir_id: hir::HirId, method: MethodCallee<'tcx>) {
2978 debug!("write_method_call(hir_id={:?}, method={:?})", hir_id, method);
2979 self.write_resolution(hir_id, Ok((DefKind::Method, method.def_id)));
2980 self.write_substs(hir_id, method.substs);
2982 // When the method is confirmed, the `method.substs` includes
2983 // parameters from not just the method, but also the impl of
2984 // the method -- in particular, the `Self` type will be fully
2985 // resolved. However, those are not something that the "user
2986 // specified" -- i.e., those types come from the inferred type
2987 // of the receiver, not something the user wrote. So when we
2988 // create the user-substs, we want to replace those earlier
2989 // types with just the types that the user actually wrote --
2990 // that is, those that appear on the *method itself*.
2992 // As an example, if the user wrote something like
2993 // `foo.bar::<u32>(...)` -- the `Self` type here will be the
2994 // type of `foo` (possibly adjusted), but we don't want to
2995 // include that. We want just the `[_, u32]` part.
2996 if !method.substs.is_noop() {
2997 let method_generics = self.tcx.generics_of(method.def_id);
2998 if !method_generics.params.is_empty() {
2999 let user_type_annotation = self.infcx.probe(|_| {
3000 let user_substs = UserSubsts {
3001 substs: InternalSubsts::for_item(self.tcx, method.def_id, |param, _| {
3002 let i = param.index as usize;
3003 if i < method_generics.parent_count {
3004 self.infcx.var_for_def(DUMMY_SP, param)
3009 user_self_ty: None, // not relevant here
3012 self.infcx.canonicalize_user_type_annotation(&UserType::TypeOf(
3018 debug!("write_method_call: user_type_annotation={:?}", user_type_annotation);
3019 self.write_user_type_annotation(hir_id, user_type_annotation);
3024 pub fn write_substs(&self, node_id: hir::HirId, substs: SubstsRef<'tcx>) {
3025 if !substs.is_noop() {
3026 debug!("write_substs({:?}, {:?}) in fcx {}", node_id, substs, self.tag());
3028 self.tables.borrow_mut().node_substs_mut().insert(node_id, substs);
3032 /// Given the substs that we just converted from the HIR, try to
3033 /// canonicalize them and store them as user-given substitutions
3034 /// (i.e., substitutions that must be respected by the NLL check).
3036 /// This should be invoked **before any unifications have
3037 /// occurred**, so that annotations like `Vec<_>` are preserved
3039 pub fn write_user_type_annotation_from_substs(
3043 substs: SubstsRef<'tcx>,
3044 user_self_ty: Option<UserSelfTy<'tcx>>,
3047 "write_user_type_annotation_from_substs: hir_id={:?} def_id={:?} substs={:?} \
3048 user_self_ty={:?} in fcx {}",
3056 if Self::can_contain_user_lifetime_bounds((substs, user_self_ty)) {
3057 let canonicalized = self.infcx.canonicalize_user_type_annotation(&UserType::TypeOf(
3059 UserSubsts { substs, user_self_ty },
3061 debug!("write_user_type_annotation_from_substs: canonicalized={:?}", canonicalized);
3062 self.write_user_type_annotation(hir_id, canonicalized);
3066 pub fn write_user_type_annotation(
3069 canonical_user_type_annotation: CanonicalUserType<'tcx>,
3072 "write_user_type_annotation: hir_id={:?} canonical_user_type_annotation={:?} tag={}",
3074 canonical_user_type_annotation,
3078 if !canonical_user_type_annotation.is_identity() {
3081 .user_provided_types_mut()
3082 .insert(hir_id, canonical_user_type_annotation);
3084 debug!("write_user_type_annotation: skipping identity substs");
3088 pub fn apply_adjustments(&self, expr: &hir::Expr<'_>, adj: Vec<Adjustment<'tcx>>) {
3089 debug!("apply_adjustments(expr={:?}, adj={:?})", expr, adj);
3095 match self.tables.borrow_mut().adjustments_mut().entry(expr.hir_id) {
3096 Entry::Vacant(entry) => {
3099 Entry::Occupied(mut entry) => {
3100 debug!(" - composing on top of {:?}", entry.get());
3101 match (&entry.get()[..], &adj[..]) {
3102 // Applying any adjustment on top of a NeverToAny
3103 // is a valid NeverToAny adjustment, because it can't
3105 (&[Adjustment { kind: Adjust::NeverToAny, .. }], _) => return,
3107 Adjustment { kind: Adjust::Deref(_), .. },
3108 Adjustment { kind: Adjust::Borrow(AutoBorrow::Ref(..)), .. },
3110 Adjustment { kind: Adjust::Deref(_), .. },
3111 .. // Any following adjustments are allowed.
3113 // A reborrow has no effect before a dereference.
3115 // FIXME: currently we never try to compose autoderefs
3116 // and ReifyFnPointer/UnsafeFnPointer, but we could.
3118 bug!("while adjusting {:?}, can't compose {:?} and {:?}",
3119 expr, entry.get(), adj)
3121 *entry.get_mut() = adj;
3126 /// Basically whenever we are converting from a type scheme into
3127 /// the fn body space, we always want to normalize associated
3128 /// types as well. This function combines the two.
3129 fn instantiate_type_scheme<T>(&self, span: Span, substs: SubstsRef<'tcx>, value: &T) -> T
3131 T: TypeFoldable<'tcx>,
3133 let value = value.subst(self.tcx, substs);
3134 let result = self.normalize_associated_types_in(span, &value);
3135 debug!("instantiate_type_scheme(value={:?}, substs={:?}) = {:?}", value, substs, result);
3139 /// As `instantiate_type_scheme`, but for the bounds found in a
3140 /// generic type scheme.
3141 fn instantiate_bounds(
3145 substs: SubstsRef<'tcx>,
3146 ) -> (ty::InstantiatedPredicates<'tcx>, Vec<Span>) {
3147 let bounds = self.tcx.predicates_of(def_id);
3148 let spans: Vec<Span> = bounds.predicates.iter().map(|(_, span)| *span).collect();
3149 let result = bounds.instantiate(self.tcx, substs);
3150 let result = self.normalize_associated_types_in(span, &result);
3152 "instantiate_bounds(bounds={:?}, substs={:?}) = {:?}, {:?}",
3153 bounds, substs, result, spans,
3158 /// Replaces the opaque types from the given value with type variables,
3159 /// and records the `OpaqueTypeMap` for later use during writeback. See
3160 /// `InferCtxt::instantiate_opaque_types` for more details.
3161 fn instantiate_opaque_types_from_value<T: TypeFoldable<'tcx>>(
3163 parent_id: hir::HirId,
3167 let parent_def_id = self.tcx.hir().local_def_id(parent_id);
3169 "instantiate_opaque_types_from_value(parent_def_id={:?}, value={:?})",
3170 parent_def_id, value
3173 let (value, opaque_type_map) =
3174 self.register_infer_ok_obligations(self.instantiate_opaque_types(
3182 let mut opaque_types = self.opaque_types.borrow_mut();
3183 let mut opaque_types_vars = self.opaque_types_vars.borrow_mut();
3184 for (ty, decl) in opaque_type_map {
3185 let _ = opaque_types.insert(ty, decl);
3186 let _ = opaque_types_vars.insert(decl.concrete_ty, decl.opaque_type);
3192 fn normalize_associated_types_in<T>(&self, span: Span, value: &T) -> T
3194 T: TypeFoldable<'tcx>,
3196 self.inh.normalize_associated_types_in(span, self.body_id, self.param_env, value)
3199 fn normalize_associated_types_in_as_infer_ok<T>(
3203 ) -> InferOk<'tcx, T>
3205 T: TypeFoldable<'tcx>,
3207 self.inh.partially_normalize_associated_types_in(span, self.body_id, self.param_env, value)
3210 pub fn require_type_meets(
3214 code: traits::ObligationCauseCode<'tcx>,
3217 self.register_bound(ty, def_id, traits::ObligationCause::new(span, self.body_id, code));
3220 pub fn require_type_is_sized(
3224 code: traits::ObligationCauseCode<'tcx>,
3226 if !ty.references_error() {
3227 let lang_item = self.tcx.require_lang_item(lang_items::SizedTraitLangItem, None);
3228 self.require_type_meets(ty, span, code, lang_item);
3232 pub fn require_type_is_sized_deferred(
3236 code: traits::ObligationCauseCode<'tcx>,
3238 if !ty.references_error() {
3239 self.deferred_sized_obligations.borrow_mut().push((ty, span, code));
3243 pub fn register_bound(
3247 cause: traits::ObligationCause<'tcx>,
3249 if !ty.references_error() {
3250 self.fulfillment_cx.borrow_mut().register_bound(
3260 pub fn to_ty(&self, ast_t: &hir::Ty<'_>) -> Ty<'tcx> {
3261 let t = AstConv::ast_ty_to_ty(self, ast_t);
3262 self.register_wf_obligation(t, ast_t.span, traits::MiscObligation);
3266 pub fn to_ty_saving_user_provided_ty(&self, ast_ty: &hir::Ty<'_>) -> Ty<'tcx> {
3267 let ty = self.to_ty(ast_ty);
3268 debug!("to_ty_saving_user_provided_ty: ty={:?}", ty);
3270 if Self::can_contain_user_lifetime_bounds(ty) {
3271 let c_ty = self.infcx.canonicalize_response(&UserType::Ty(ty));
3272 debug!("to_ty_saving_user_provided_ty: c_ty={:?}", c_ty);
3273 self.tables.borrow_mut().user_provided_types_mut().insert(ast_ty.hir_id, c_ty);
3279 /// Returns the `DefId` of the constant parameter that the provided expression is a path to.
3280 pub fn const_param_def_id(&self, hir_c: &hir::AnonConst) -> Option<DefId> {
3281 AstConv::const_param_def_id(self, &self.tcx.hir().body(hir_c.body).value)
3284 pub fn to_const(&self, ast_c: &hir::AnonConst, ty: Ty<'tcx>) -> &'tcx ty::Const<'tcx> {
3285 AstConv::ast_const_to_const(self, ast_c, ty)
3288 // If the type given by the user has free regions, save it for later, since
3289 // NLL would like to enforce those. Also pass in types that involve
3290 // projections, since those can resolve to `'static` bounds (modulo #54940,
3291 // which hopefully will be fixed by the time you see this comment, dear
3292 // reader, although I have my doubts). Also pass in types with inference
3293 // types, because they may be repeated. Other sorts of things are already
3294 // sufficiently enforced with erased regions. =)
3295 fn can_contain_user_lifetime_bounds<T>(t: T) -> bool
3297 T: TypeFoldable<'tcx>,
3299 t.has_free_regions() || t.has_projections() || t.has_infer_types()
3302 pub fn node_ty(&self, id: hir::HirId) -> Ty<'tcx> {
3303 match self.tables.borrow().node_types().get(id) {
3305 None if self.is_tainted_by_errors() => self.tcx.types.err,
3308 "no type for node {}: {} in fcx {}",
3310 self.tcx.hir().node_to_string(id),
3317 /// Registers an obligation for checking later, during regionck, that the type `ty` must
3318 /// outlive the region `r`.
3319 pub fn register_wf_obligation(
3323 code: traits::ObligationCauseCode<'tcx>,
3325 // WF obligations never themselves fail, so no real need to give a detailed cause:
3326 let cause = traits::ObligationCause::new(span, self.body_id, code);
3327 self.register_predicate(traits::Obligation::new(
3330 ty::Predicate::WellFormed(ty),
3334 /// Registers obligations that all types appearing in `substs` are well-formed.
3335 pub fn add_wf_bounds(&self, substs: SubstsRef<'tcx>, expr: &hir::Expr<'_>) {
3336 for ty in substs.types() {
3337 if !ty.references_error() {
3338 self.register_wf_obligation(ty, expr.span, traits::MiscObligation);
3343 /// Given a fully substituted set of bounds (`generic_bounds`), and the values with which each
3344 /// type/region parameter was instantiated (`substs`), creates and registers suitable
3345 /// trait/region obligations.
3347 /// For example, if there is a function:
3350 /// fn foo<'a,T:'a>(...)
3353 /// and a reference:
3359 /// Then we will create a fresh region variable `'$0` and a fresh type variable `$1` for `'a`
3360 /// and `T`. This routine will add a region obligation `$1:'$0` and register it locally.
3361 pub fn add_obligations_for_parameters(
3363 cause: traits::ObligationCause<'tcx>,
3364 predicates: &ty::InstantiatedPredicates<'tcx>,
3366 assert!(!predicates.has_escaping_bound_vars());
3368 debug!("add_obligations_for_parameters(predicates={:?})", predicates);
3370 for obligation in traits::predicates_for_generics(cause, self.param_env, predicates) {
3371 self.register_predicate(obligation);
3375 // FIXME(arielb1): use this instead of field.ty everywhere
3376 // Only for fields! Returns <none> for methods>
3377 // Indifferent to privacy flags
3381 field: &'tcx ty::FieldDef,
3382 substs: SubstsRef<'tcx>,
3384 self.normalize_associated_types_in(span, &field.ty(self.tcx, substs))
3387 fn check_casts(&self) {
3388 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
3389 for cast in deferred_cast_checks.drain(..) {
3394 fn resolve_generator_interiors(&self, def_id: DefId) {
3395 let mut generators = self.deferred_generator_interiors.borrow_mut();
3396 for (body_id, interior, kind) in generators.drain(..) {
3397 self.select_obligations_where_possible(false, |_| {});
3398 generator_interior::resolve_interior(self, def_id, body_id, interior, kind);
3402 // Tries to apply a fallback to `ty` if it is an unsolved variable.
3404 // - Unconstrained ints are replaced with `i32`.
3406 // - Unconstrained floats are replaced with with `f64`.
3408 // - Non-numerics get replaced with `!` when `#![feature(never_type_fallback)]`
3409 // is enabled. Otherwise, they are replaced with `()`.
3411 // Fallback becomes very dubious if we have encountered type-checking errors.
3412 // In that case, fallback to Error.
3413 // The return value indicates whether fallback has occurred.
3414 fn fallback_if_possible(&self, ty: Ty<'tcx>, mode: FallbackMode) -> bool {
3415 use rustc::ty::error::UnconstrainedNumeric::Neither;
3416 use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedFloat, UnconstrainedInt};
3418 assert!(ty.is_ty_infer());
3419 let fallback = match self.type_is_unconstrained_numeric(ty) {
3420 _ if self.is_tainted_by_errors() => self.tcx().types.err,
3421 UnconstrainedInt => self.tcx.types.i32,
3422 UnconstrainedFloat => self.tcx.types.f64,
3423 Neither if self.type_var_diverges(ty) => self.tcx.mk_diverging_default(),
3425 // This type variable was created from the instantiation of an opaque
3426 // type. The fact that we're attempting to perform fallback for it
3427 // means that the function neither constrained it to a concrete
3428 // type, nor to the opaque type itself.
3430 // For example, in this code:
3433 // type MyType = impl Copy;
3434 // fn defining_use() -> MyType { true }
3435 // fn other_use() -> MyType { defining_use() }
3438 // `defining_use` will constrain the instantiated inference
3439 // variable to `bool`, while `other_use` will constrain
3440 // the instantiated inference variable to `MyType`.
3442 // When we process opaque types during writeback, we
3443 // will handle cases like `other_use`, and not count
3444 // them as defining usages
3446 // However, we also need to handle cases like this:
3449 // pub type Foo = impl Copy;
3450 // fn produce() -> Option<Foo> {
3455 // In the above snippet, the inference varaible created by
3456 // instantiating `Option<Foo>` will be completely unconstrained.
3457 // We treat this as a non-defining use by making the inference
3458 // variable fall back to the opaque type itself.
3459 if let FallbackMode::All = mode {
3460 if let Some(opaque_ty) = self.opaque_types_vars.borrow().get(ty) {
3462 "fallback_if_possible: falling back opaque type var {:?} to {:?}",
3474 debug!("fallback_if_possible: defaulting `{:?}` to `{:?}`", ty, fallback);
3475 self.demand_eqtype(rustc_span::DUMMY_SP, ty, fallback);
3479 fn select_all_obligations_or_error(&self) {
3480 debug!("select_all_obligations_or_error");
3481 if let Err(errors) = self.fulfillment_cx.borrow_mut().select_all_or_error(&self) {
3482 self.report_fulfillment_errors(&errors, self.inh.body_id, false);
3486 /// Select as many obligations as we can at present.
3487 fn select_obligations_where_possible(
3489 fallback_has_occurred: bool,
3490 mutate_fullfillment_errors: impl Fn(&mut Vec<traits::FulfillmentError<'tcx>>),
3492 let result = self.fulfillment_cx.borrow_mut().select_where_possible(self);
3493 if let Err(mut errors) = result {
3494 mutate_fullfillment_errors(&mut errors);
3495 self.report_fulfillment_errors(&errors, self.inh.body_id, fallback_has_occurred);
3499 /// For the overloaded place expressions (`*x`, `x[3]`), the trait
3500 /// returns a type of `&T`, but the actual type we assign to the
3501 /// *expression* is `T`. So this function just peels off the return
3502 /// type by one layer to yield `T`.
3503 fn make_overloaded_place_return_type(
3505 method: MethodCallee<'tcx>,
3506 ) -> ty::TypeAndMut<'tcx> {
3507 // extract method return type, which will be &T;
3508 let ret_ty = method.sig.output();
3510 // method returns &T, but the type as visible to user is T, so deref
3511 ret_ty.builtin_deref(true).unwrap()
3516 expr: &hir::Expr<'_>,
3517 base_expr: &'tcx hir::Expr<'tcx>,
3521 ) -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)> {
3522 // FIXME(#18741) -- this is almost but not quite the same as the
3523 // autoderef that normal method probing does. They could likely be
3526 let mut autoderef = self.autoderef(base_expr.span, base_ty);
3527 let mut result = None;
3528 while result.is_none() && autoderef.next().is_some() {
3529 result = self.try_index_step(expr, base_expr, &autoderef, needs, idx_ty);
3531 autoderef.finalize(self);
3535 /// To type-check `base_expr[index_expr]`, we progressively autoderef
3536 /// (and otherwise adjust) `base_expr`, looking for a type which either
3537 /// supports builtin indexing or overloaded indexing.
3538 /// This loop implements one step in that search; the autoderef loop
3539 /// is implemented by `lookup_indexing`.
3542 expr: &hir::Expr<'_>,
3543 base_expr: &hir::Expr<'_>,
3544 autoderef: &Autoderef<'a, 'tcx>,
3547 ) -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)> {
3548 let adjusted_ty = autoderef.unambiguous_final_ty(self);
3550 "try_index_step(expr={:?}, base_expr={:?}, adjusted_ty={:?}, \
3552 expr, base_expr, adjusted_ty, index_ty
3555 for &unsize in &[false, true] {
3556 let mut self_ty = adjusted_ty;
3558 // We only unsize arrays here.
3559 if let ty::Array(element_ty, _) = adjusted_ty.kind {
3560 self_ty = self.tcx.mk_slice(element_ty);
3566 // If some lookup succeeds, write callee into table and extract index/element
3567 // type from the method signature.
3568 // If some lookup succeeded, install method in table
3569 let input_ty = self.next_ty_var(TypeVariableOrigin {
3570 kind: TypeVariableOriginKind::AutoDeref,
3571 span: base_expr.span,
3573 let method = self.try_overloaded_place_op(
3581 let result = method.map(|ok| {
3582 debug!("try_index_step: success, using overloaded indexing");
3583 let method = self.register_infer_ok_obligations(ok);
3585 let mut adjustments = autoderef.adjust_steps(self, needs);
3586 if let ty::Ref(region, _, r_mutbl) = method.sig.inputs()[0].kind {
3587 let mutbl = match r_mutbl {
3588 hir::Mutability::Not => AutoBorrowMutability::Not,
3589 hir::Mutability::Mut => AutoBorrowMutability::Mut {
3590 // Indexing can be desugared to a method call,
3591 // so maybe we could use two-phase here.
3592 // See the documentation of AllowTwoPhase for why that's
3593 // not the case today.
3594 allow_two_phase_borrow: AllowTwoPhase::No,
3597 adjustments.push(Adjustment {
3598 kind: Adjust::Borrow(AutoBorrow::Ref(region, mutbl)),
3601 .mk_ref(region, ty::TypeAndMut { mutbl: r_mutbl, ty: adjusted_ty }),
3605 adjustments.push(Adjustment {
3606 kind: Adjust::Pointer(PointerCast::Unsize),
3607 target: method.sig.inputs()[0],
3610 self.apply_adjustments(base_expr, adjustments);
3612 self.write_method_call(expr.hir_id, method);
3613 (input_ty, self.make_overloaded_place_return_type(method).ty)
3615 if result.is_some() {
3623 fn resolve_place_op(&self, op: PlaceOp, is_mut: bool) -> (Option<DefId>, ast::Ident) {
3624 let (tr, name) = match (op, is_mut) {
3625 (PlaceOp::Deref, false) => (self.tcx.lang_items().deref_trait(), sym::deref),
3626 (PlaceOp::Deref, true) => (self.tcx.lang_items().deref_mut_trait(), sym::deref_mut),
3627 (PlaceOp::Index, false) => (self.tcx.lang_items().index_trait(), sym::index),
3628 (PlaceOp::Index, true) => (self.tcx.lang_items().index_mut_trait(), sym::index_mut),
3630 (tr, ast::Ident::with_dummy_span(name))
3633 fn try_overloaded_place_op(
3637 arg_tys: &[Ty<'tcx>],
3640 ) -> Option<InferOk<'tcx, MethodCallee<'tcx>>> {
3641 debug!("try_overloaded_place_op({:?},{:?},{:?},{:?})", span, base_ty, needs, op);
3643 // Try Mut first, if needed.
3644 let (mut_tr, mut_op) = self.resolve_place_op(op, true);
3645 let method = match (needs, mut_tr) {
3646 (Needs::MutPlace, Some(trait_did)) => {
3647 self.lookup_method_in_trait(span, mut_op, trait_did, base_ty, Some(arg_tys))
3652 // Otherwise, fall back to the immutable version.
3653 let (imm_tr, imm_op) = self.resolve_place_op(op, false);
3654 let method = match (method, imm_tr) {
3655 (None, Some(trait_did)) => {
3656 self.lookup_method_in_trait(span, imm_op, trait_did, base_ty, Some(arg_tys))
3658 (method, _) => method,
3664 fn check_method_argument_types(
3667 expr: &'tcx hir::Expr<'tcx>,
3668 method: Result<MethodCallee<'tcx>, ()>,
3669 args_no_rcvr: &'tcx [hir::Expr<'tcx>],
3670 tuple_arguments: TupleArgumentsFlag,
3671 expected: Expectation<'tcx>,
3673 let has_error = match method {
3674 Ok(method) => method.substs.references_error() || method.sig.references_error(),
3678 let err_inputs = self.err_args(args_no_rcvr.len());
3680 let err_inputs = match tuple_arguments {
3681 DontTupleArguments => err_inputs,
3682 TupleArguments => vec![self.tcx.intern_tup(&err_inputs[..])],
3685 self.check_argument_types(
3695 return self.tcx.types.err;
3698 let method = method.unwrap();
3699 // HACK(eddyb) ignore self in the definition (see above).
3700 let expected_arg_tys = self.expected_inputs_for_expected_output(
3703 method.sig.output(),
3704 &method.sig.inputs()[1..],
3706 self.check_argument_types(
3709 &method.sig.inputs()[1..],
3710 &expected_arg_tys[..],
3712 method.sig.c_variadic,
3714 self.tcx.hir().span_if_local(method.def_id),
3719 fn self_type_matches_expected_vid(
3721 trait_ref: ty::PolyTraitRef<'tcx>,
3722 expected_vid: ty::TyVid,
3724 let self_ty = self.shallow_resolve(trait_ref.self_ty());
3726 "self_type_matches_expected_vid(trait_ref={:?}, self_ty={:?}, expected_vid={:?})",
3727 trait_ref, self_ty, expected_vid
3729 match self_ty.kind {
3730 ty::Infer(ty::TyVar(found_vid)) => {
3731 // FIXME: consider using `sub_root_var` here so we
3732 // can see through subtyping.
3733 let found_vid = self.root_var(found_vid);
3734 debug!("self_type_matches_expected_vid - found_vid={:?}", found_vid);
3735 expected_vid == found_vid
3741 fn obligations_for_self_ty<'b>(
3744 ) -> impl Iterator<Item = (ty::PolyTraitRef<'tcx>, traits::PredicateObligation<'tcx>)>
3747 // FIXME: consider using `sub_root_var` here so we
3748 // can see through subtyping.
3749 let ty_var_root = self.root_var(self_ty);
3751 "obligations_for_self_ty: self_ty={:?} ty_var_root={:?} pending_obligations={:?}",
3754 self.fulfillment_cx.borrow().pending_obligations()
3759 .pending_obligations()
3761 .filter_map(move |obligation| match obligation.predicate {
3762 ty::Predicate::Projection(ref data) => {
3763 Some((data.to_poly_trait_ref(self.tcx), obligation))
3765 ty::Predicate::Trait(ref data, _) => Some((data.to_poly_trait_ref(), obligation)),
3766 ty::Predicate::Subtype(..) => None,
3767 ty::Predicate::RegionOutlives(..) => None,
3768 ty::Predicate::TypeOutlives(..) => None,
3769 ty::Predicate::WellFormed(..) => None,
3770 ty::Predicate::ObjectSafe(..) => None,
3771 ty::Predicate::ConstEvaluatable(..) => None,
3772 // N.B., this predicate is created by breaking down a
3773 // `ClosureType: FnFoo()` predicate, where
3774 // `ClosureType` represents some `Closure`. It can't
3775 // possibly be referring to the current closure,
3776 // because we haven't produced the `Closure` for
3777 // this closure yet; this is exactly why the other
3778 // code is looking for a self type of a unresolved
3779 // inference variable.
3780 ty::Predicate::ClosureKind(..) => None,
3782 .filter(move |(tr, _)| self.self_type_matches_expected_vid(*tr, ty_var_root))
3785 fn type_var_is_sized(&self, self_ty: ty::TyVid) -> bool {
3786 self.obligations_for_self_ty(self_ty)
3787 .any(|(tr, _)| Some(tr.def_id()) == self.tcx.lang_items().sized_trait())
3790 /// Generic function that factors out common logic from function calls,
3791 /// method calls and overloaded operators.
3792 fn check_argument_types(
3795 expr: &'tcx hir::Expr<'tcx>,
3796 fn_inputs: &[Ty<'tcx>],
3797 expected_arg_tys: &[Ty<'tcx>],
3798 args: &'tcx [hir::Expr<'tcx>],
3800 tuple_arguments: TupleArgumentsFlag,
3801 def_span: Option<Span>,
3804 // Grab the argument types, supplying fresh type variables
3805 // if the wrong number of arguments were supplied
3806 let supplied_arg_count = if tuple_arguments == DontTupleArguments { args.len() } else { 1 };
3808 // All the input types from the fn signature must outlive the call
3809 // so as to validate implied bounds.
3810 for (fn_input_ty, arg_expr) in fn_inputs.iter().zip(args.iter()) {
3811 self.register_wf_obligation(fn_input_ty, arg_expr.span, traits::MiscObligation);
3814 let expected_arg_count = fn_inputs.len();
3816 let param_count_error = |expected_count: usize,
3821 let (span, start_span, args) = match &expr.kind {
3822 hir::ExprKind::Call(hir::Expr { span, .. }, args) => (*span, *span, &args[..]),
3823 hir::ExprKind::MethodCall(path_segment, span, args) => (
3825 // `sp` doesn't point at the whole `foo.bar()`, only at `bar`.
3828 .and_then(|args| args.args.iter().last())
3829 // Account for `foo.bar::<T>()`.
3831 // Skip the closing `>`.
3834 .next_point(tcx.sess.source_map().next_point(arg.span()))
3837 &args[1..], // Skip the receiver.
3839 k => span_bug!(sp, "checking argument types on a non-call: `{:?}`", k),
3841 let arg_spans = if args.is_empty() {
3843 // ^^^-- supplied 0 arguments
3845 // expected 2 arguments
3846 vec![tcx.sess.source_map().next_point(start_span).with_hi(sp.hi())]
3849 // ^^^ - - - supplied 3 arguments
3851 // expected 2 arguments
3852 args.iter().map(|arg| arg.span).collect::<Vec<Span>>()
3855 let mut err = tcx.sess.struct_span_err_with_code(
3858 "this function takes {}{} but {} {} supplied",
3859 if c_variadic { "at least " } else { "" },
3860 potentially_plural_count(expected_count, "argument"),
3861 potentially_plural_count(arg_count, "argument"),
3862 if arg_count == 1 { "was" } else { "were" }
3864 DiagnosticId::Error(error_code.to_owned()),
3866 let label = format!("supplied {}", potentially_plural_count(arg_count, "argument"));
3867 for (i, span) in arg_spans.into_iter().enumerate() {
3870 if arg_count == 0 || i + 1 == arg_count { &label } else { "" },
3874 if let Some(def_s) = def_span.map(|sp| tcx.sess.source_map().def_span(sp)) {
3875 err.span_label(def_s, "defined here");
3878 let sugg_span = tcx.sess.source_map().end_point(expr.span);
3879 // remove closing `)` from the span
3880 let sugg_span = sugg_span.shrink_to_lo();
3881 err.span_suggestion(
3883 "expected the unit value `()`; create it with empty parentheses",
3885 Applicability::MachineApplicable,
3892 if c_variadic { "at least " } else { "" },
3893 potentially_plural_count(expected_count, "argument")
3900 let mut expected_arg_tys = expected_arg_tys.to_vec();
3902 let formal_tys = if tuple_arguments == TupleArguments {
3903 let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
3904 match tuple_type.kind {
3905 ty::Tuple(arg_types) if arg_types.len() != args.len() => {
3906 param_count_error(arg_types.len(), args.len(), "E0057", false, false);
3907 expected_arg_tys = vec![];
3908 self.err_args(args.len())
3910 ty::Tuple(arg_types) => {
3911 expected_arg_tys = match expected_arg_tys.get(0) {
3912 Some(&ty) => match ty.kind {
3913 ty::Tuple(ref tys) => tys.iter().map(|k| k.expect_ty()).collect(),
3918 arg_types.iter().map(|k| k.expect_ty()).collect()
3925 "cannot use call notation; the first type parameter \
3926 for the function trait is neither a tuple nor unit"
3929 expected_arg_tys = vec![];
3930 self.err_args(args.len())
3933 } else if expected_arg_count == supplied_arg_count {
3935 } else if c_variadic {
3936 if supplied_arg_count >= expected_arg_count {
3939 param_count_error(expected_arg_count, supplied_arg_count, "E0060", true, false);
3940 expected_arg_tys = vec![];
3941 self.err_args(supplied_arg_count)
3944 // is the missing argument of type `()`?
3945 let sugg_unit = if expected_arg_tys.len() == 1 && supplied_arg_count == 0 {
3946 self.resolve_vars_if_possible(&expected_arg_tys[0]).is_unit()
3947 } else if fn_inputs.len() == 1 && supplied_arg_count == 0 {
3948 self.resolve_vars_if_possible(&fn_inputs[0]).is_unit()
3952 param_count_error(expected_arg_count, supplied_arg_count, "E0061", false, sugg_unit);
3954 expected_arg_tys = vec![];
3955 self.err_args(supplied_arg_count)
3959 "check_argument_types: formal_tys={:?}",
3960 formal_tys.iter().map(|t| self.ty_to_string(*t)).collect::<Vec<String>>()
3963 // If there is no expectation, expect formal_tys.
3964 let expected_arg_tys =
3965 if !expected_arg_tys.is_empty() { expected_arg_tys } else { formal_tys.clone() };
3967 let mut final_arg_types: Vec<(usize, Ty<'_>, Ty<'_>)> = vec![];
3969 // Check the arguments.
3970 // We do this in a pretty awful way: first we type-check any arguments
3971 // that are not closures, then we type-check the closures. This is so
3972 // that we have more information about the types of arguments when we
3973 // type-check the functions. This isn't really the right way to do this.
3974 for &check_closures in &[false, true] {
3975 debug!("check_closures={}", check_closures);
3977 // More awful hacks: before we check argument types, try to do
3978 // an "opportunistic" vtable resolution of any trait bounds on
3979 // the call. This helps coercions.
3981 self.select_obligations_where_possible(false, |errors| {
3982 self.point_at_type_arg_instead_of_call_if_possible(errors, expr);
3983 self.point_at_arg_instead_of_call_if_possible(
3985 &final_arg_types[..],
3992 // For C-variadic functions, we don't have a declared type for all of
3993 // the arguments hence we only do our usual type checking with
3994 // the arguments who's types we do know.
3995 let t = if c_variadic {
3997 } else if tuple_arguments == TupleArguments {
4002 for (i, arg) in args.iter().take(t).enumerate() {
4003 // Warn only for the first loop (the "no closures" one).
4004 // Closure arguments themselves can't be diverging, but
4005 // a previous argument can, e.g., `foo(panic!(), || {})`.
4006 if !check_closures {
4007 self.warn_if_unreachable(arg.hir_id, arg.span, "expression");
4010 let is_closure = match arg.kind {
4011 ExprKind::Closure(..) => true,
4015 if is_closure != check_closures {
4019 debug!("checking the argument");
4020 let formal_ty = formal_tys[i];
4022 // The special-cased logic below has three functions:
4023 // 1. Provide as good of an expected type as possible.
4024 let expected = Expectation::rvalue_hint(self, expected_arg_tys[i]);
4026 let checked_ty = self.check_expr_with_expectation(&arg, expected);
4028 // 2. Coerce to the most detailed type that could be coerced
4029 // to, which is `expected_ty` if `rvalue_hint` returns an
4030 // `ExpectHasType(expected_ty)`, or the `formal_ty` otherwise.
4031 let coerce_ty = expected.only_has_type(self).unwrap_or(formal_ty);
4032 // We're processing function arguments so we definitely want to use
4033 // two-phase borrows.
4034 self.demand_coerce(&arg, checked_ty, coerce_ty, AllowTwoPhase::Yes);
4035 final_arg_types.push((i, checked_ty, coerce_ty));
4037 // 3. Relate the expected type and the formal one,
4038 // if the expected type was used for the coercion.
4039 self.demand_suptype(arg.span, formal_ty, coerce_ty);
4043 // We also need to make sure we at least write the ty of the other
4044 // arguments which we skipped above.
4046 fn variadic_error<'tcx>(s: &Session, span: Span, t: Ty<'tcx>, cast_ty: &str) {
4047 use crate::structured_errors::{StructuredDiagnostic, VariadicError};
4048 VariadicError::new(s, span, t, cast_ty).diagnostic().emit();
4051 for arg in args.iter().skip(expected_arg_count) {
4052 let arg_ty = self.check_expr(&arg);
4054 // There are a few types which get autopromoted when passed via varargs
4055 // in C but we just error out instead and require explicit casts.
4056 let arg_ty = self.structurally_resolved_type(arg.span, arg_ty);
4058 ty::Float(ast::FloatTy::F32) => {
4059 variadic_error(tcx.sess, arg.span, arg_ty, "c_double");
4061 ty::Int(ast::IntTy::I8) | ty::Int(ast::IntTy::I16) | ty::Bool => {
4062 variadic_error(tcx.sess, arg.span, arg_ty, "c_int");
4064 ty::Uint(ast::UintTy::U8) | ty::Uint(ast::UintTy::U16) => {
4065 variadic_error(tcx.sess, arg.span, arg_ty, "c_uint");
4068 let ptr_ty = self.tcx.mk_fn_ptr(arg_ty.fn_sig(self.tcx));
4069 let ptr_ty = self.resolve_vars_if_possible(&ptr_ty);
4070 variadic_error(tcx.sess, arg.span, arg_ty, &ptr_ty.to_string());
4078 fn err_args(&self, len: usize) -> Vec<Ty<'tcx>> {
4079 vec![self.tcx.types.err; len]
4082 /// Given a vec of evaluated `FulfillmentError`s and an `fn` call argument expressions, we walk
4083 /// the checked and coerced types for each argument to see if any of the `FulfillmentError`s
4084 /// reference a type argument. The reason to walk also the checked type is that the coerced type
4085 /// can be not easily comparable with predicate type (because of coercion). If the types match
4086 /// for either checked or coerced type, and there's only *one* argument that does, we point at
4087 /// the corresponding argument's expression span instead of the `fn` call path span.
4088 fn point_at_arg_instead_of_call_if_possible(
4090 errors: &mut Vec<traits::FulfillmentError<'_>>,
4091 final_arg_types: &[(usize, Ty<'tcx>, Ty<'tcx>)],
4093 args: &'tcx [hir::Expr<'tcx>],
4095 // We *do not* do this for desugared call spans to keep good diagnostics when involving
4096 // the `?` operator.
4097 if call_sp.desugaring_kind().is_some() {
4101 for error in errors {
4102 // Only if the cause is somewhere inside the expression we want try to point at arg.
4103 // Otherwise, it means that the cause is somewhere else and we should not change
4104 // anything because we can break the correct span.
4105 if !call_sp.contains(error.obligation.cause.span) {
4109 if let ty::Predicate::Trait(predicate, _) = error.obligation.predicate {
4110 // Collect the argument position for all arguments that could have caused this
4111 // `FulfillmentError`.
4112 let mut referenced_in = final_arg_types
4114 .map(|(i, checked_ty, _)| (i, checked_ty))
4115 .chain(final_arg_types.iter().map(|(i, _, coerced_ty)| (i, coerced_ty)))
4116 .flat_map(|(i, ty)| {
4117 let ty = self.resolve_vars_if_possible(ty);
4118 // We walk the argument type because the argument's type could have
4119 // been `Option<T>`, but the `FulfillmentError` references `T`.
4121 .filter(|&ty| ty == predicate.skip_binder().self_ty())
4124 .collect::<Vec<_>>();
4126 // Both checked and coerced types could have matched, thus we need to remove
4128 referenced_in.dedup();
4130 if let (Some(ref_in), None) = (referenced_in.pop(), referenced_in.pop()) {
4131 // We make sure that only *one* argument matches the obligation failure
4132 // and we assign the obligation's span to its expression's.
4133 error.obligation.cause.span = args[ref_in].span;
4134 error.points_at_arg_span = true;
4140 /// Given a vec of evaluated `FulfillmentError`s and an `fn` call expression, we walk the
4141 /// `PathSegment`s and resolve their type parameters to see if any of the `FulfillmentError`s
4142 /// were caused by them. If they were, we point at the corresponding type argument's span
4143 /// instead of the `fn` call path span.
4144 fn point_at_type_arg_instead_of_call_if_possible(
4146 errors: &mut Vec<traits::FulfillmentError<'_>>,
4147 call_expr: &'tcx hir::Expr<'tcx>,
4149 if let hir::ExprKind::Call(path, _) = &call_expr.kind {
4150 if let hir::ExprKind::Path(qpath) = &path.kind {
4151 if let hir::QPath::Resolved(_, path) = &qpath {
4152 for error in errors {
4153 if let ty::Predicate::Trait(predicate, _) = error.obligation.predicate {
4154 // If any of the type arguments in this path segment caused the
4155 // `FullfillmentError`, point at its span (#61860).
4159 .filter_map(|seg| seg.args.as_ref())
4160 .flat_map(|a| a.args.iter())
4162 if let hir::GenericArg::Type(hir_ty) = &arg {
4163 if let hir::TyKind::Path(hir::QPath::TypeRelative(..)) =
4166 // Avoid ICE with associated types. As this is best
4167 // effort only, it's ok to ignore the case. It
4168 // would trigger in `is_send::<T::AssocType>();`
4169 // from `typeck-default-trait-impl-assoc-type.rs`.
4171 let ty = AstConv::ast_ty_to_ty(self, hir_ty);
4172 let ty = self.resolve_vars_if_possible(&ty);
4173 if ty == predicate.skip_binder().self_ty() {
4174 error.obligation.cause.span = hir_ty.span;
4186 // AST fragment checking
4187 fn check_lit(&self, lit: &hir::Lit, expected: Expectation<'tcx>) -> Ty<'tcx> {
4191 ast::LitKind::Str(..) => tcx.mk_static_str(),
4192 ast::LitKind::ByteStr(ref v) => {
4193 tcx.mk_imm_ref(tcx.lifetimes.re_static, tcx.mk_array(tcx.types.u8, v.len() as u64))
4195 ast::LitKind::Byte(_) => tcx.types.u8,
4196 ast::LitKind::Char(_) => tcx.types.char,
4197 ast::LitKind::Int(_, ast::LitIntType::Signed(t)) => tcx.mk_mach_int(t),
4198 ast::LitKind::Int(_, ast::LitIntType::Unsigned(t)) => tcx.mk_mach_uint(t),
4199 ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
4200 let opt_ty = expected.to_option(self).and_then(|ty| match ty.kind {
4201 ty::Int(_) | ty::Uint(_) => Some(ty),
4202 ty::Char => Some(tcx.types.u8),
4203 ty::RawPtr(..) => Some(tcx.types.usize),
4204 ty::FnDef(..) | ty::FnPtr(_) => Some(tcx.types.usize),
4207 opt_ty.unwrap_or_else(|| self.next_int_var())
4209 ast::LitKind::Float(_, ast::LitFloatType::Suffixed(t)) => tcx.mk_mach_float(t),
4210 ast::LitKind::Float(_, ast::LitFloatType::Unsuffixed) => {
4211 let opt_ty = expected.to_option(self).and_then(|ty| match ty.kind {
4212 ty::Float(_) => Some(ty),
4215 opt_ty.unwrap_or_else(|| self.next_float_var())
4217 ast::LitKind::Bool(_) => tcx.types.bool,
4218 ast::LitKind::Err(_) => tcx.types.err,
4222 // Determine the `Self` type, using fresh variables for all variables
4223 // declared on the impl declaration e.g., `impl<A,B> for Vec<(A,B)>`
4224 // would return `($0, $1)` where `$0` and `$1` are freshly instantiated type
4226 pub fn impl_self_ty(
4228 span: Span, // (potential) receiver for this impl
4230 ) -> TypeAndSubsts<'tcx> {
4231 let ity = self.tcx.type_of(did);
4232 debug!("impl_self_ty: ity={:?}", ity);
4234 let substs = self.fresh_substs_for_item(span, did);
4235 let substd_ty = self.instantiate_type_scheme(span, &substs, &ity);
4237 TypeAndSubsts { substs: substs, ty: substd_ty }
4240 /// Unifies the output type with the expected type early, for more coercions
4241 /// and forward type information on the input expressions.
4242 fn expected_inputs_for_expected_output(
4245 expected_ret: Expectation<'tcx>,
4246 formal_ret: Ty<'tcx>,
4247 formal_args: &[Ty<'tcx>],
4248 ) -> Vec<Ty<'tcx>> {
4249 let formal_ret = self.resolve_vars_with_obligations(formal_ret);
4250 let ret_ty = match expected_ret.only_has_type(self) {
4252 None => return Vec::new(),
4254 let expect_args = self
4255 .fudge_inference_if_ok(|| {
4256 // Attempt to apply a subtyping relationship between the formal
4257 // return type (likely containing type variables if the function
4258 // is polymorphic) and the expected return type.
4259 // No argument expectations are produced if unification fails.
4260 let origin = self.misc(call_span);
4261 let ures = self.at(&origin, self.param_env).sup(ret_ty, &formal_ret);
4263 // FIXME(#27336) can't use ? here, Try::from_error doesn't default
4264 // to identity so the resulting type is not constrained.
4267 // Process any obligations locally as much as
4268 // we can. We don't care if some things turn
4269 // out unconstrained or ambiguous, as we're
4270 // just trying to get hints here.
4271 self.save_and_restore_in_snapshot_flag(|_| {
4272 let mut fulfill = TraitEngine::new(self.tcx);
4273 for obligation in ok.obligations {
4274 fulfill.register_predicate_obligation(self, obligation);
4276 fulfill.select_where_possible(self)
4280 Err(_) => return Err(()),
4283 // Record all the argument types, with the substitutions
4284 // produced from the above subtyping unification.
4285 Ok(formal_args.iter().map(|ty| self.resolve_vars_if_possible(ty)).collect())
4287 .unwrap_or_default();
4289 "expected_inputs_for_expected_output(formal={:?} -> {:?}, expected={:?} -> {:?})",
4290 formal_args, formal_ret, expect_args, expected_ret
4295 pub fn check_struct_path(
4299 ) -> Option<(&'tcx ty::VariantDef, Ty<'tcx>)> {
4300 let path_span = match *qpath {
4301 QPath::Resolved(_, ref path) => path.span,
4302 QPath::TypeRelative(ref qself, _) => qself.span,
4304 let (def, ty) = self.finish_resolving_struct_path(qpath, path_span, hir_id);
4305 let variant = match def {
4307 self.set_tainted_by_errors();
4310 Res::Def(DefKind::Variant, _) => match ty.kind {
4311 ty::Adt(adt, substs) => Some((adt.variant_of_res(def), adt.did, substs)),
4312 _ => bug!("unexpected type: {:?}", ty),
4314 Res::Def(DefKind::Struct, _)
4315 | Res::Def(DefKind::Union, _)
4316 | Res::Def(DefKind::TyAlias, _)
4317 | Res::Def(DefKind::AssocTy, _)
4318 | Res::SelfTy(..) => match ty.kind {
4319 ty::Adt(adt, substs) if !adt.is_enum() => {
4320 Some((adt.non_enum_variant(), adt.did, substs))
4324 _ => bug!("unexpected definition: {:?}", def),
4327 if let Some((variant, did, substs)) = variant {
4328 debug!("check_struct_path: did={:?} substs={:?}", did, substs);
4329 self.write_user_type_annotation_from_substs(hir_id, did, substs, None);
4331 // Check bounds on type arguments used in the path.
4332 let (bounds, _) = self.instantiate_bounds(path_span, did, substs);
4334 traits::ObligationCause::new(path_span, self.body_id, traits::ItemObligation(did));
4335 self.add_obligations_for_parameters(cause, &bounds);
4343 "expected struct, variant or union type, found {}",
4344 ty.sort_string(self.tcx)
4346 .span_label(path_span, "not a struct")
4352 // Finish resolving a path in a struct expression or pattern `S::A { .. }` if necessary.
4353 // The newly resolved definition is written into `type_dependent_defs`.
4354 fn finish_resolving_struct_path(
4359 ) -> (Res, Ty<'tcx>) {
4361 QPath::Resolved(ref maybe_qself, ref path) => {
4362 let self_ty = maybe_qself.as_ref().map(|qself| self.to_ty(qself));
4363 let ty = AstConv::res_to_ty(self, self_ty, path, true);
4366 QPath::TypeRelative(ref qself, ref segment) => {
4367 let ty = self.to_ty(qself);
4369 let res = if let hir::TyKind::Path(QPath::Resolved(_, ref path)) = qself.kind {
4375 AstConv::associated_path_to_ty(self, hir_id, path_span, ty, res, segment, true);
4376 let ty = result.map(|(ty, _, _)| ty).unwrap_or(self.tcx().types.err);
4377 let result = result.map(|(_, kind, def_id)| (kind, def_id));
4379 // Write back the new resolution.
4380 self.write_resolution(hir_id, result);
4382 (result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err), ty)
4387 /// Resolves an associated value path into a base type and associated constant, or method
4388 /// resolution. The newly resolved definition is written into `type_dependent_defs`.
4389 pub fn resolve_ty_and_res_ufcs<'b>(
4391 qpath: &'b QPath<'b>,
4394 ) -> (Res, Option<Ty<'tcx>>, &'b [hir::PathSegment<'b>]) {
4395 debug!("resolve_ty_and_res_ufcs: qpath={:?} hir_id={:?} span={:?}", qpath, hir_id, span);
4396 let (ty, qself, item_segment) = match *qpath {
4397 QPath::Resolved(ref opt_qself, ref path) => {
4400 opt_qself.as_ref().map(|qself| self.to_ty(qself)),
4404 QPath::TypeRelative(ref qself, ref segment) => (self.to_ty(qself), qself, segment),
4406 if let Some(&cached_result) = self.tables.borrow().type_dependent_defs().get(hir_id) {
4407 // Return directly on cache hit. This is useful to avoid doubly reporting
4408 // errors with default match binding modes. See #44614.
4410 cached_result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err);
4411 return (def, Some(ty), slice::from_ref(&**item_segment));
4413 let item_name = item_segment.ident;
4414 let result = self.resolve_ufcs(span, item_name, ty, hir_id).or_else(|error| {
4415 let result = match error {
4416 method::MethodError::PrivateMatch(kind, def_id, _) => Ok((kind, def_id)),
4417 _ => Err(ErrorReported),
4419 if item_name.name != kw::Invalid {
4420 self.report_method_error(
4424 SelfSource::QPath(qself),
4428 .map(|mut e| e.emit());
4433 // Write back the new resolution.
4434 self.write_resolution(hir_id, result);
4436 result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err),
4438 slice::from_ref(&**item_segment),
4442 pub fn check_decl_initializer(
4444 local: &'tcx hir::Local<'tcx>,
4445 init: &'tcx hir::Expr<'tcx>,
4447 // FIXME(tschottdorf): `contains_explicit_ref_binding()` must be removed
4448 // for #42640 (default match binding modes).
4451 let ref_bindings = local.pat.contains_explicit_ref_binding();
4453 let local_ty = self.local_ty(init.span, local.hir_id).revealed_ty;
4454 if let Some(m) = ref_bindings {
4455 // Somewhat subtle: if we have a `ref` binding in the pattern,
4456 // we want to avoid introducing coercions for the RHS. This is
4457 // both because it helps preserve sanity and, in the case of
4458 // ref mut, for soundness (issue #23116). In particular, in
4459 // the latter case, we need to be clear that the type of the
4460 // referent for the reference that results is *equal to* the
4461 // type of the place it is referencing, and not some
4462 // supertype thereof.
4463 let init_ty = self.check_expr_with_needs(init, Needs::maybe_mut_place(m));
4464 self.demand_eqtype(init.span, local_ty, init_ty);
4467 self.check_expr_coercable_to_type(init, local_ty)
4471 /// Type check a `let` statement.
4472 pub fn check_decl_local(&self, local: &'tcx hir::Local<'tcx>) {
4473 // Determine and write the type which we'll check the pattern against.
4474 let ty = self.local_ty(local.span, local.hir_id).decl_ty;
4475 self.write_ty(local.hir_id, ty);
4477 // Type check the initializer.
4478 if let Some(ref init) = local.init {
4479 let init_ty = self.check_decl_initializer(local, &init);
4480 self.overwrite_local_ty_if_err(local, ty, init_ty);
4483 // Does the expected pattern type originate from an expression and what is the span?
4484 let (origin_expr, ty_span) = match (local.ty, local.init) {
4485 (Some(ty), _) => (false, Some(ty.span)), // Bias towards the explicit user type.
4486 (_, Some(init)) => (true, Some(init.span)), // No explicit type; so use the scrutinee.
4487 _ => (false, None), // We have `let $pat;`, so the expected type is unconstrained.
4490 // Type check the pattern. Override if necessary to avoid knock-on errors.
4491 self.check_pat_top(&local.pat, ty, ty_span, origin_expr);
4492 let pat_ty = self.node_ty(local.pat.hir_id);
4493 self.overwrite_local_ty_if_err(local, ty, pat_ty);
4496 fn overwrite_local_ty_if_err(
4498 local: &'tcx hir::Local<'tcx>,
4502 if ty.references_error() {
4503 // Override the types everywhere with `types.err` to avoid knock on errors.
4504 self.write_ty(local.hir_id, ty);
4505 self.write_ty(local.pat.hir_id, ty);
4506 let local_ty = LocalTy { decl_ty, revealed_ty: ty };
4507 self.locals.borrow_mut().insert(local.hir_id, local_ty);
4508 self.locals.borrow_mut().insert(local.pat.hir_id, local_ty);
4512 fn suggest_semicolon_at_end(&self, span: Span, err: &mut DiagnosticBuilder<'_>) {
4513 err.span_suggestion_short(
4514 span.shrink_to_hi(),
4515 "consider using a semicolon here",
4517 Applicability::MachineApplicable,
4521 pub fn check_stmt(&self, stmt: &'tcx hir::Stmt<'tcx>) {
4522 // Don't do all the complex logic below for `DeclItem`.
4524 hir::StmtKind::Item(..) => return,
4525 hir::StmtKind::Local(..) | hir::StmtKind::Expr(..) | hir::StmtKind::Semi(..) => {}
4528 self.warn_if_unreachable(stmt.hir_id, stmt.span, "statement");
4530 // Hide the outer diverging and `has_errors` flags.
4531 let old_diverges = self.diverges.replace(Diverges::Maybe);
4532 let old_has_errors = self.has_errors.replace(false);
4535 hir::StmtKind::Local(ref l) => {
4536 self.check_decl_local(&l);
4539 hir::StmtKind::Item(_) => {}
4540 hir::StmtKind::Expr(ref expr) => {
4541 // Check with expected type of `()`.
4542 self.check_expr_has_type_or_error(&expr, self.tcx.mk_unit(), |err| {
4543 self.suggest_semicolon_at_end(expr.span, err);
4546 hir::StmtKind::Semi(ref expr) => {
4547 self.check_expr(&expr);
4551 // Combine the diverging and `has_error` flags.
4552 self.diverges.set(self.diverges.get() | old_diverges);
4553 self.has_errors.set(self.has_errors.get() | old_has_errors);
4556 pub fn check_block_no_value(&self, blk: &'tcx hir::Block<'tcx>) {
4557 let unit = self.tcx.mk_unit();
4558 let ty = self.check_block_with_expected(blk, ExpectHasType(unit));
4560 // if the block produces a `!` value, that can always be
4561 // (effectively) coerced to unit.
4563 self.demand_suptype(blk.span, unit, ty);
4567 /// If `expr` is a `match` expression that has only one non-`!` arm, use that arm's tail
4568 /// expression's `Span`, otherwise return `expr.span`. This is done to give better errors
4569 /// when given code like the following:
4571 /// if false { return 0i32; } else { 1u32 }
4572 /// // ^^^^ point at this instead of the whole `if` expression
4574 fn get_expr_coercion_span(&self, expr: &hir::Expr<'_>) -> rustc_span::Span {
4575 if let hir::ExprKind::Match(_, arms, _) = &expr.kind {
4576 let arm_spans: Vec<Span> = arms
4579 self.in_progress_tables
4580 .and_then(|tables| tables.borrow().node_type_opt(arm.body.hir_id))
4581 .and_then(|arm_ty| {
4582 if arm_ty.is_never() {
4585 Some(match &arm.body.kind {
4586 // Point at the tail expression when possible.
4587 hir::ExprKind::Block(block, _) => {
4588 block.expr.as_ref().map(|e| e.span).unwrap_or(block.span)
4596 if arm_spans.len() == 1 {
4597 return arm_spans[0];
4603 fn check_block_with_expected(
4605 blk: &'tcx hir::Block<'tcx>,
4606 expected: Expectation<'tcx>,
4609 let mut fcx_ps = self.ps.borrow_mut();
4610 let unsafety_state = fcx_ps.recurse(blk);
4611 replace(&mut *fcx_ps, unsafety_state)
4614 // In some cases, blocks have just one exit, but other blocks
4615 // can be targeted by multiple breaks. This can happen both
4616 // with labeled blocks as well as when we desugar
4617 // a `try { ... }` expression.
4621 // 'a: { if true { break 'a Err(()); } Ok(()) }
4623 // Here we would wind up with two coercions, one from
4624 // `Err(())` and the other from the tail expression
4625 // `Ok(())`. If the tail expression is omitted, that's a
4626 // "forced unit" -- unless the block diverges, in which
4627 // case we can ignore the tail expression (e.g., `'a: {
4628 // break 'a 22; }` would not force the type of the block
4630 let tail_expr = blk.expr.as_ref();
4631 let coerce_to_ty = expected.coercion_target_type(self, blk.span);
4632 let coerce = if blk.targeted_by_break {
4633 CoerceMany::new(coerce_to_ty)
4635 let tail_expr: &[&hir::Expr<'_>] = match tail_expr {
4636 Some(e) => slice::from_ref(e),
4639 CoerceMany::with_coercion_sites(coerce_to_ty, tail_expr)
4642 let prev_diverges = self.diverges.get();
4643 let ctxt = BreakableCtxt { coerce: Some(coerce), may_break: false };
4645 let (ctxt, ()) = self.with_breakable_ctxt(blk.hir_id, ctxt, || {
4646 for s in blk.stmts {
4650 // check the tail expression **without** holding the
4651 // `enclosing_breakables` lock below.
4652 let tail_expr_ty = tail_expr.map(|t| self.check_expr_with_expectation(t, expected));
4654 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4655 let ctxt = enclosing_breakables.find_breakable(blk.hir_id);
4656 let coerce = ctxt.coerce.as_mut().unwrap();
4657 if let Some(tail_expr_ty) = tail_expr_ty {
4658 let tail_expr = tail_expr.unwrap();
4659 let span = self.get_expr_coercion_span(tail_expr);
4660 let cause = self.cause(span, ObligationCauseCode::BlockTailExpression(blk.hir_id));
4661 coerce.coerce(self, &cause, tail_expr, tail_expr_ty);
4663 // Subtle: if there is no explicit tail expression,
4664 // that is typically equivalent to a tail expression
4665 // of `()` -- except if the block diverges. In that
4666 // case, there is no value supplied from the tail
4667 // expression (assuming there are no other breaks,
4668 // this implies that the type of the block will be
4671 // #41425 -- label the implicit `()` as being the
4672 // "found type" here, rather than the "expected type".
4673 if !self.diverges.get().is_always() {
4674 // #50009 -- Do not point at the entire fn block span, point at the return type
4675 // span, as it is the cause of the requirement, and
4676 // `consider_hint_about_removing_semicolon` will point at the last expression
4677 // if it were a relevant part of the error. This improves usability in editors
4678 // that highlight errors inline.
4679 let mut sp = blk.span;
4680 let mut fn_span = None;
4681 if let Some((decl, ident)) = self.get_parent_fn_decl(blk.hir_id) {
4682 let ret_sp = decl.output.span();
4683 if let Some(block_sp) = self.parent_item_span(blk.hir_id) {
4684 // HACK: on some cases (`ui/liveness/liveness-issue-2163.rs`) the
4685 // output would otherwise be incorrect and even misleading. Make sure
4686 // the span we're aiming at correspond to a `fn` body.
4687 if block_sp == blk.span {
4689 fn_span = Some(ident.span);
4693 coerce.coerce_forced_unit(
4697 if let Some(expected_ty) = expected.only_has_type(self) {
4698 self.consider_hint_about_removing_semicolon(blk, expected_ty, err);
4700 if let Some(fn_span) = fn_span {
4703 "implicitly returns `()` as its body has no tail or `return` \
4715 // If we can break from the block, then the block's exit is always reachable
4716 // (... as long as the entry is reachable) - regardless of the tail of the block.
4717 self.diverges.set(prev_diverges);
4720 let mut ty = ctxt.coerce.unwrap().complete(self);
4722 if self.has_errors.get() || ty.references_error() {
4723 ty = self.tcx.types.err
4726 self.write_ty(blk.hir_id, ty);
4728 *self.ps.borrow_mut() = prev;
4732 fn parent_item_span(&self, id: hir::HirId) -> Option<Span> {
4733 let node = self.tcx.hir().get(self.tcx.hir().get_parent_item(id));
4735 Node::Item(&hir::Item { kind: hir::ItemKind::Fn(_, _, body_id), .. })
4736 | Node::ImplItem(&hir::ImplItem {
4737 kind: hir::ImplItemKind::Method(_, body_id), ..
4739 let body = self.tcx.hir().body(body_id);
4740 if let ExprKind::Block(block, _) = &body.value.kind {
4741 return Some(block.span);
4749 /// Given a function block's `HirId`, returns its `FnDecl` if it exists, or `None` otherwise.
4750 fn get_parent_fn_decl(
4753 ) -> Option<(&'tcx hir::FnDecl<'tcx>, ast::Ident)> {
4754 let parent = self.tcx.hir().get(self.tcx.hir().get_parent_item(blk_id));
4755 self.get_node_fn_decl(parent).map(|(fn_decl, ident, _)| (fn_decl, ident))
4758 /// Given a function `Node`, return its `FnDecl` if it exists, or `None` otherwise.
4759 fn get_node_fn_decl(
4762 ) -> Option<(&'tcx hir::FnDecl<'tcx>, ast::Ident, bool)> {
4764 Node::Item(&hir::Item { ident, kind: hir::ItemKind::Fn(ref sig, ..), .. }) => {
4765 // This is less than ideal, it will not suggest a return type span on any
4766 // method called `main`, regardless of whether it is actually the entry point,
4767 // but it will still present it as the reason for the expected type.
4768 Some((&sig.decl, ident, ident.name != sym::main))
4770 Node::TraitItem(&hir::TraitItem {
4772 kind: hir::TraitItemKind::Method(ref sig, ..),
4774 }) => Some((&sig.decl, ident, true)),
4775 Node::ImplItem(&hir::ImplItem {
4777 kind: hir::ImplItemKind::Method(ref sig, ..),
4779 }) => Some((&sig.decl, ident, false)),
4784 /// Given a `HirId`, return the `FnDecl` of the method it is enclosed by and whether a
4785 /// suggestion can be made, `None` otherwise.
4786 pub fn get_fn_decl(&self, blk_id: hir::HirId) -> Option<(&'tcx hir::FnDecl<'tcx>, bool)> {
4787 // Get enclosing Fn, if it is a function or a trait method, unless there's a `loop` or
4788 // `while` before reaching it, as block tail returns are not available in them.
4789 self.tcx.hir().get_return_block(blk_id).and_then(|blk_id| {
4790 let parent = self.tcx.hir().get(blk_id);
4791 self.get_node_fn_decl(parent).map(|(fn_decl, _, is_main)| (fn_decl, is_main))
4795 /// On implicit return expressions with mismatched types, provides the following suggestions:
4797 /// - Points out the method's return type as the reason for the expected type.
4798 /// - Possible missing semicolon.
4799 /// - Possible missing return type if the return type is the default, and not `fn main()`.
4800 pub fn suggest_mismatched_types_on_tail(
4802 err: &mut DiagnosticBuilder<'_>,
4803 expr: &'tcx hir::Expr<'tcx>,
4809 let expr = expr.peel_drop_temps();
4810 self.suggest_missing_semicolon(err, expr, expected, cause_span);
4811 let mut pointing_at_return_type = false;
4812 if let Some((fn_decl, can_suggest)) = self.get_fn_decl(blk_id) {
4813 pointing_at_return_type =
4814 self.suggest_missing_return_type(err, &fn_decl, expected, found, can_suggest);
4816 pointing_at_return_type
4819 /// When encountering an fn-like ctor that needs to unify with a value, check whether calling
4820 /// the ctor would successfully solve the type mismatch and if so, suggest it:
4822 /// fn foo(x: usize) -> usize { x }
4823 /// let x: usize = foo; // suggest calling the `foo` function: `foo(42)`
4827 err: &mut DiagnosticBuilder<'_>,
4828 expr: &hir::Expr<'_>,
4832 let hir = self.tcx.hir();
4833 let (def_id, sig) = match found.kind {
4834 ty::FnDef(def_id, _) => (def_id, found.fn_sig(self.tcx)),
4835 ty::Closure(def_id, substs) => {
4836 // We don't use `closure_sig` to account for malformed closures like
4837 // `|_: [_; continue]| {}` and instead we don't suggest anything.
4838 let closure_sig_ty = substs.as_closure().sig_ty(def_id, self.tcx);
4841 match closure_sig_ty.kind {
4842 ty::FnPtr(sig) => sig,
4850 let sig = self.replace_bound_vars_with_fresh_vars(expr.span, infer::FnCall, &sig).0;
4851 let sig = self.normalize_associated_types_in(expr.span, &sig);
4852 if self.can_coerce(sig.output(), expected) {
4853 let (mut sugg_call, applicability) = if sig.inputs().is_empty() {
4854 (String::new(), Applicability::MachineApplicable)
4856 ("...".to_string(), Applicability::HasPlaceholders)
4858 let mut msg = "call this function";
4859 match hir.get_if_local(def_id) {
4860 Some(Node::Item(hir::Item { kind: ItemKind::Fn(.., body_id), .. }))
4861 | Some(Node::ImplItem(hir::ImplItem {
4862 kind: hir::ImplItemKind::Method(_, body_id),
4865 | Some(Node::TraitItem(hir::TraitItem {
4866 kind: hir::TraitItemKind::Method(.., hir::TraitMethod::Provided(body_id)),
4869 let body = hir.body(*body_id);
4873 .map(|param| match ¶m.pat.kind {
4874 hir::PatKind::Binding(_, _, ident, None)
4875 if ident.name != kw::SelfLower =>
4879 _ => "_".to_string(),
4881 .collect::<Vec<_>>()
4884 Some(Node::Expr(hir::Expr {
4885 kind: ExprKind::Closure(_, _, body_id, _, _),
4886 span: full_closure_span,
4889 if *full_closure_span == expr.span {
4892 msg = "call this closure";
4893 let body = hir.body(*body_id);
4897 .map(|param| match ¶m.pat.kind {
4898 hir::PatKind::Binding(_, _, ident, None)
4899 if ident.name != kw::SelfLower =>
4903 _ => "_".to_string(),
4905 .collect::<Vec<_>>()
4908 Some(Node::Ctor(hir::VariantData::Tuple(fields, _))) => {
4909 sugg_call = fields.iter().map(|_| "_").collect::<Vec<_>>().join(", ");
4910 match hir.as_local_hir_id(def_id).and_then(|hir_id| hir.def_kind(hir_id)) {
4911 Some(hir::def::DefKind::Ctor(hir::def::CtorOf::Variant, _)) => {
4912 msg = "instantiate this tuple variant";
4914 Some(hir::def::DefKind::Ctor(hir::def::CtorOf::Struct, _)) => {
4915 msg = "instantiate this tuple struct";
4920 Some(Node::ForeignItem(hir::ForeignItem {
4921 kind: hir::ForeignItemKind::Fn(_, idents, _),
4927 if ident.name != kw::SelfLower {
4933 .collect::<Vec<_>>()
4936 Some(Node::TraitItem(hir::TraitItem {
4937 kind: hir::TraitItemKind::Method(.., hir::TraitMethod::Required(idents)),
4943 if ident.name != kw::SelfLower {
4949 .collect::<Vec<_>>()
4954 if let Ok(code) = self.sess().source_map().span_to_snippet(expr.span) {
4955 err.span_suggestion(
4957 &format!("use parentheses to {}", msg),
4958 format!("{}({})", code, sugg_call),
4967 pub fn suggest_ref_or_into(
4969 err: &mut DiagnosticBuilder<'_>,
4970 expr: &hir::Expr<'_>,
4974 if let Some((sp, msg, suggestion)) = self.check_ref(expr, found, expected) {
4975 err.span_suggestion(sp, msg, suggestion, Applicability::MachineApplicable);
4976 } else if let (ty::FnDef(def_id, ..), true) =
4977 (&found.kind, self.suggest_fn_call(err, expr, expected, found))
4979 if let Some(sp) = self.tcx.hir().span_if_local(*def_id) {
4980 let sp = self.sess().source_map().def_span(sp);
4981 err.span_label(sp, &format!("{} defined here", found));
4983 } else if !self.check_for_cast(err, expr, found, expected) {
4984 let is_struct_pat_shorthand_field =
4985 self.is_hir_id_from_struct_pattern_shorthand_field(expr.hir_id, expr.span);
4986 let methods = self.get_conversion_methods(expr.span, expected, found);
4987 if let Ok(expr_text) = self.sess().source_map().span_to_snippet(expr.span) {
4988 let mut suggestions = iter::repeat(&expr_text)
4989 .zip(methods.iter())
4990 .filter_map(|(receiver, method)| {
4991 let method_call = format!(".{}()", method.ident);
4992 if receiver.ends_with(&method_call) {
4993 None // do not suggest code that is already there (#53348)
4995 let method_call_list = [".to_vec()", ".to_string()"];
4996 let sugg = if receiver.ends_with(".clone()")
4997 && method_call_list.contains(&method_call.as_str())
4999 let max_len = receiver.rfind('.').unwrap();
5000 format!("{}{}", &receiver[..max_len], method_call)
5002 if expr.precedence().order() < ExprPrecedence::MethodCall.order() {
5003 format!("({}){}", receiver, method_call)
5005 format!("{}{}", receiver, method_call)
5008 Some(if is_struct_pat_shorthand_field {
5009 format!("{}: {}", receiver, sugg)
5016 if suggestions.peek().is_some() {
5017 err.span_suggestions(
5019 "try using a conversion method",
5021 Applicability::MaybeIncorrect,
5028 /// When encountering the expected boxed value allocated in the stack, suggest allocating it
5029 /// in the heap by calling `Box::new()`.
5030 fn suggest_boxing_when_appropriate(
5032 err: &mut DiagnosticBuilder<'_>,
5033 expr: &hir::Expr<'_>,
5037 if self.tcx.hir().is_const_context(expr.hir_id) {
5038 // Do not suggest `Box::new` in const context.
5041 if !expected.is_box() || found.is_box() {
5044 let boxed_found = self.tcx.mk_box(found);
5045 if let (true, Ok(snippet)) = (
5046 self.can_coerce(boxed_found, expected),
5047 self.sess().source_map().span_to_snippet(expr.span),
5049 err.span_suggestion(
5051 "store this in the heap by calling `Box::new`",
5052 format!("Box::new({})", snippet),
5053 Applicability::MachineApplicable,
5056 "for more on the distinction between the stack and the heap, read \
5057 https://doc.rust-lang.org/book/ch15-01-box.html, \
5058 https://doc.rust-lang.org/rust-by-example/std/box.html, and \
5059 https://doc.rust-lang.org/std/boxed/index.html",
5064 /// When encountering an `impl Future` where `BoxFuture` is expected, suggest `Box::pin`.
5065 fn suggest_calling_boxed_future_when_appropriate(
5067 err: &mut DiagnosticBuilder<'_>,
5068 expr: &hir::Expr<'_>,
5074 if self.tcx.hir().is_const_context(expr.hir_id) {
5075 // Do not suggest `Box::new` in const context.
5078 let pin_did = self.tcx.lang_items().pin_type();
5079 match expected.kind {
5080 ty::Adt(def, _) if Some(def.did) != pin_did => return false,
5081 // This guards the `unwrap` and `mk_box` below.
5082 _ if pin_did.is_none() || self.tcx.lang_items().owned_box().is_none() => return false,
5085 let boxed_found = self.tcx.mk_box(found);
5086 let new_found = self.tcx.mk_lang_item(boxed_found, lang_items::PinTypeLangItem).unwrap();
5087 if let (true, Ok(snippet)) = (
5088 self.can_coerce(new_found, expected),
5089 self.sess().source_map().span_to_snippet(expr.span),
5092 ty::Adt(def, _) if def.is_box() => {
5093 err.help("use `Box::pin`");
5096 err.span_suggestion(
5098 "you need to pin and box this expression",
5099 format!("Box::pin({})", snippet),
5100 Applicability::MachineApplicable,
5110 /// A common error is to forget to add a semicolon at the end of a block, e.g.,
5114 /// bar_that_returns_u32()
5118 /// This routine checks if the return expression in a block would make sense on its own as a
5119 /// statement and the return type has been left as default or has been specified as `()`. If so,
5120 /// it suggests adding a semicolon.
5121 fn suggest_missing_semicolon(
5123 err: &mut DiagnosticBuilder<'_>,
5124 expression: &'tcx hir::Expr<'tcx>,
5128 if expected.is_unit() {
5129 // `BlockTailExpression` only relevant if the tail expr would be
5130 // useful on its own.
5131 match expression.kind {
5133 | ExprKind::MethodCall(..)
5134 | ExprKind::Loop(..)
5135 | ExprKind::Match(..)
5136 | ExprKind::Block(..) => {
5137 err.span_suggestion(
5138 cause_span.shrink_to_hi(),
5139 "try adding a semicolon",
5141 Applicability::MachineApplicable,
5149 /// A possible error is to forget to add a return type that is needed:
5153 /// bar_that_returns_u32()
5157 /// This routine checks if the return type is left as default, the method is not part of an
5158 /// `impl` block and that it isn't the `main` method. If so, it suggests setting the return
5160 fn suggest_missing_return_type(
5162 err: &mut DiagnosticBuilder<'_>,
5163 fn_decl: &hir::FnDecl<'_>,
5168 // Only suggest changing the return type for methods that
5169 // haven't set a return type at all (and aren't `fn main()` or an impl).
5170 match (&fn_decl.output, found.is_suggestable(), can_suggest, expected.is_unit()) {
5171 (&hir::FnRetTy::DefaultReturn(span), true, true, true) => {
5172 err.span_suggestion(
5174 "try adding a return type",
5175 format!("-> {} ", self.resolve_vars_with_obligations(found)),
5176 Applicability::MachineApplicable,
5180 (&hir::FnRetTy::DefaultReturn(span), false, true, true) => {
5181 err.span_label(span, "possibly return type missing here?");
5184 (&hir::FnRetTy::DefaultReturn(span), _, false, true) => {
5185 // `fn main()` must return `()`, do not suggest changing return type
5186 err.span_label(span, "expected `()` because of default return type");
5189 // expectation was caused by something else, not the default return
5190 (&hir::FnRetTy::DefaultReturn(_), _, _, false) => false,
5191 (&hir::FnRetTy::Return(ref ty), _, _, _) => {
5192 // Only point to return type if the expected type is the return type, as if they
5193 // are not, the expectation must have been caused by something else.
5194 debug!("suggest_missing_return_type: return type {:?} node {:?}", ty, ty.kind);
5196 let ty = AstConv::ast_ty_to_ty(self, ty);
5197 debug!("suggest_missing_return_type: return type {:?}", ty);
5198 debug!("suggest_missing_return_type: expected type {:?}", ty);
5199 if ty.kind == expected.kind {
5200 err.span_label(sp, format!("expected `{}` because of return type", expected));
5208 /// A possible error is to forget to add `.await` when using futures:
5211 /// async fn make_u32() -> u32 {
5215 /// fn take_u32(x: u32) {}
5217 /// async fn foo() {
5218 /// let x = make_u32();
5223 /// This routine checks if the found type `T` implements `Future<Output=U>` where `U` is the
5224 /// expected type. If this is the case, and we are inside of an async body, it suggests adding
5225 /// `.await` to the tail of the expression.
5226 fn suggest_missing_await(
5228 err: &mut DiagnosticBuilder<'_>,
5229 expr: &hir::Expr<'_>,
5233 // `.await` is not permitted outside of `async` bodies, so don't bother to suggest if the
5234 // body isn't `async`.
5235 let item_id = self.tcx().hir().get_parent_node(self.body_id);
5236 if let Some(body_id) = self.tcx().hir().maybe_body_owned_by(item_id) {
5237 let body = self.tcx().hir().body(body_id);
5238 if let Some(hir::GeneratorKind::Async(_)) = body.generator_kind {
5240 // Check for `Future` implementations by constructing a predicate to
5241 // prove: `<T as Future>::Output == U`
5242 let future_trait = self.tcx.lang_items().future_trait().unwrap();
5243 let item_def_id = self
5245 .associated_items(future_trait)
5246 .in_definition_order()
5251 ty::Predicate::Projection(ty::Binder::bind(ty::ProjectionPredicate {
5252 // `<T as Future>::Output`
5253 projection_ty: ty::ProjectionTy {
5255 substs: self.tcx.mk_substs_trait(
5257 self.fresh_substs_for_item(sp, item_def_id),
5264 let obligation = traits::Obligation::new(self.misc(sp), self.param_env, predicate);
5265 debug!("suggest_missing_await: trying obligation {:?}", obligation);
5266 if self.infcx.predicate_may_hold(&obligation) {
5267 debug!("suggest_missing_await: obligation held: {:?}", obligation);
5268 if let Ok(code) = self.sess().source_map().span_to_snippet(sp) {
5269 err.span_suggestion(
5271 "consider using `.await` here",
5272 format!("{}.await", code),
5273 Applicability::MaybeIncorrect,
5276 debug!("suggest_missing_await: no snippet for {:?}", sp);
5279 debug!("suggest_missing_await: obligation did not hold: {:?}", obligation)
5285 /// A common error is to add an extra semicolon:
5288 /// fn foo() -> usize {
5293 /// This routine checks if the final statement in a block is an
5294 /// expression with an explicit semicolon whose type is compatible
5295 /// with `expected_ty`. If so, it suggests removing the semicolon.
5296 fn consider_hint_about_removing_semicolon(
5298 blk: &'tcx hir::Block<'tcx>,
5299 expected_ty: Ty<'tcx>,
5300 err: &mut DiagnosticBuilder<'_>,
5302 if let Some(span_semi) = self.could_remove_semicolon(blk, expected_ty) {
5303 err.span_suggestion(
5305 "consider removing this semicolon",
5307 Applicability::MachineApplicable,
5312 fn could_remove_semicolon(
5314 blk: &'tcx hir::Block<'tcx>,
5315 expected_ty: Ty<'tcx>,
5317 // Be helpful when the user wrote `{... expr;}` and
5318 // taking the `;` off is enough to fix the error.
5319 let last_stmt = blk.stmts.last()?;
5320 let last_expr = match last_stmt.kind {
5321 hir::StmtKind::Semi(ref e) => e,
5324 let last_expr_ty = self.node_ty(last_expr.hir_id);
5325 if self.can_sub(self.param_env, last_expr_ty, expected_ty).is_err() {
5328 let original_span = original_sp(last_stmt.span, blk.span);
5329 Some(original_span.with_lo(original_span.hi() - BytePos(1)))
5332 // Instantiates the given path, which must refer to an item with the given
5333 // number of type parameters and type.
5334 pub fn instantiate_value_path(
5336 segments: &[hir::PathSegment<'_>],
5337 self_ty: Option<Ty<'tcx>>,
5341 ) -> (Ty<'tcx>, Res) {
5343 "instantiate_value_path(segments={:?}, self_ty={:?}, res={:?}, hir_id={})",
5344 segments, self_ty, res, hir_id,
5349 let path_segs = match res {
5350 Res::Local(_) | Res::SelfCtor(_) => vec![],
5351 Res::Def(kind, def_id) => {
5352 AstConv::def_ids_for_value_path_segments(self, segments, self_ty, kind, def_id)
5354 _ => bug!("instantiate_value_path on {:?}", res),
5357 let mut user_self_ty = None;
5358 let mut is_alias_variant_ctor = false;
5360 Res::Def(DefKind::Ctor(CtorOf::Variant, _), _) => {
5361 if let Some(self_ty) = self_ty {
5362 let adt_def = self_ty.ty_adt_def().unwrap();
5363 user_self_ty = Some(UserSelfTy { impl_def_id: adt_def.did, self_ty });
5364 is_alias_variant_ctor = true;
5367 Res::Def(DefKind::Method, def_id) | Res::Def(DefKind::AssocConst, def_id) => {
5368 let container = tcx.associated_item(def_id).container;
5369 debug!("instantiate_value_path: def_id={:?} container={:?}", def_id, container);
5371 ty::TraitContainer(trait_did) => {
5372 callee::check_legal_trait_for_method_call(tcx, span, trait_did)
5374 ty::ImplContainer(impl_def_id) => {
5375 if segments.len() == 1 {
5376 // `<T>::assoc` will end up here, and so
5377 // can `T::assoc`. It this came from an
5378 // inherent impl, we need to record the
5379 // `T` for posterity (see `UserSelfTy` for
5381 let self_ty = self_ty.expect("UFCS sugared assoc missing Self");
5382 user_self_ty = Some(UserSelfTy { impl_def_id, self_ty });
5390 // Now that we have categorized what space the parameters for each
5391 // segment belong to, let's sort out the parameters that the user
5392 // provided (if any) into their appropriate spaces. We'll also report
5393 // errors if type parameters are provided in an inappropriate place.
5395 let generic_segs: FxHashSet<_> = path_segs.iter().map(|PathSeg(_, index)| index).collect();
5396 let generics_has_err = AstConv::prohibit_generics(
5398 segments.iter().enumerate().filter_map(|(index, seg)| {
5399 if !generic_segs.contains(&index) || is_alias_variant_ctor {
5407 if let Res::Local(hid) = res {
5408 let ty = self.local_ty(span, hid).decl_ty;
5409 let ty = self.normalize_associated_types_in(span, &ty);
5410 self.write_ty(hir_id, ty);
5414 if generics_has_err {
5415 // Don't try to infer type parameters when prohibited generic arguments were given.
5416 user_self_ty = None;
5419 // Now we have to compare the types that the user *actually*
5420 // provided against the types that were *expected*. If the user
5421 // did not provide any types, then we want to substitute inference
5422 // variables. If the user provided some types, we may still need
5423 // to add defaults. If the user provided *too many* types, that's
5426 let mut infer_args_for_err = FxHashSet::default();
5427 for &PathSeg(def_id, index) in &path_segs {
5428 let seg = &segments[index];
5429 let generics = tcx.generics_of(def_id);
5430 // Argument-position `impl Trait` is treated as a normal generic
5431 // parameter internally, but we don't allow users to specify the
5432 // parameter's value explicitly, so we have to do some error-
5434 if let Err(GenericArgCountMismatch { reported: Some(ErrorReported), .. }) =
5435 AstConv::check_generic_arg_count_for_call(
5436 tcx, span, &generics, &seg, false, // `is_method_call`
5439 infer_args_for_err.insert(index);
5440 self.set_tainted_by_errors(); // See issue #53251.
5444 let has_self = path_segs
5446 .map(|PathSeg(def_id, _)| tcx.generics_of(*def_id).has_self)
5449 let (res, self_ctor_substs) = if let Res::SelfCtor(impl_def_id) = res {
5450 let ty = self.normalize_ty(span, tcx.at(span).type_of(impl_def_id));
5452 ty::Adt(adt_def, substs) if adt_def.has_ctor() => {
5453 let variant = adt_def.non_enum_variant();
5454 let ctor_def_id = variant.ctor_def_id.unwrap();
5456 Res::Def(DefKind::Ctor(CtorOf::Struct, variant.ctor_kind), ctor_def_id),
5461 let mut err = tcx.sess.struct_span_err(
5463 "the `Self` constructor can only be used with tuple or unit structs",
5465 if let Some(adt_def) = ty.ty_adt_def() {
5466 match adt_def.adt_kind() {
5468 err.help("did you mean to use one of the enum's variants?");
5470 AdtKind::Struct | AdtKind::Union => {
5471 err.span_suggestion(
5473 "use curly brackets",
5474 String::from("Self { /* fields */ }"),
5475 Applicability::HasPlaceholders,
5482 return (tcx.types.err, res);
5488 let def_id = res.def_id();
5490 // The things we are substituting into the type should not contain
5491 // escaping late-bound regions, and nor should the base type scheme.
5492 let ty = tcx.type_of(def_id);
5494 let substs = self_ctor_substs.unwrap_or_else(|| {
5495 AstConv::create_substs_for_generic_args(
5501 infer_args_for_err.is_empty(),
5502 // Provide the generic args, and whether types should be inferred.
5504 if let Some(&PathSeg(_, index)) =
5505 path_segs.iter().find(|&PathSeg(did, _)| *did == def_id)
5507 // If we've encountered an `impl Trait`-related error, we're just
5508 // going to infer the arguments for better error messages.
5509 if !infer_args_for_err.contains(&index) {
5510 // Check whether the user has provided generic arguments.
5511 if let Some(ref data) = segments[index].args {
5512 return (Some(data), segments[index].infer_args);
5515 return (None, segments[index].infer_args);
5520 // Provide substitutions for parameters for which (valid) arguments have been provided.
5521 |param, arg| match (¶m.kind, arg) {
5522 (GenericParamDefKind::Lifetime, GenericArg::Lifetime(lt)) => {
5523 AstConv::ast_region_to_region(self, lt, Some(param)).into()
5525 (GenericParamDefKind::Type { .. }, GenericArg::Type(ty)) => {
5526 self.to_ty(ty).into()
5528 (GenericParamDefKind::Const, GenericArg::Const(ct)) => {
5529 self.to_const(&ct.value, self.tcx.type_of(param.def_id)).into()
5531 _ => unreachable!(),
5533 // Provide substitutions for parameters for which arguments are inferred.
5534 |substs, param, infer_args| {
5536 GenericParamDefKind::Lifetime => {
5537 self.re_infer(Some(param), span).unwrap().into()
5539 GenericParamDefKind::Type { has_default, .. } => {
5540 if !infer_args && has_default {
5541 // If we have a default, then we it doesn't matter that we're not
5542 // inferring the type arguments: we provide the default where any
5544 let default = tcx.type_of(param.def_id);
5547 default.subst_spanned(tcx, substs.unwrap(), Some(span)),
5551 // If no type arguments were provided, we have to infer them.
5552 // This case also occurs as a result of some malformed input, e.g.
5553 // a lifetime argument being given instead of a type parameter.
5554 // Using inference instead of `Error` gives better error messages.
5555 self.var_for_def(span, param)
5558 GenericParamDefKind::Const => {
5559 // FIXME(const_generics:defaults)
5560 // No const parameters were provided, we have to infer them.
5561 self.var_for_def(span, param)
5567 assert!(!substs.has_escaping_bound_vars());
5568 assert!(!ty.has_escaping_bound_vars());
5570 // First, store the "user substs" for later.
5571 self.write_user_type_annotation_from_substs(hir_id, def_id, substs, user_self_ty);
5573 self.add_required_obligations(span, def_id, &substs);
5575 // Substitute the values for the type parameters into the type of
5576 // the referenced item.
5577 let ty_substituted = self.instantiate_type_scheme(span, &substs, &ty);
5579 if let Some(UserSelfTy { impl_def_id, self_ty }) = user_self_ty {
5580 // In the case of `Foo<T>::method` and `<Foo<T>>::method`, if `method`
5581 // is inherent, there is no `Self` parameter; instead, the impl needs
5582 // type parameters, which we can infer by unifying the provided `Self`
5583 // with the substituted impl type.
5584 // This also occurs for an enum variant on a type alias.
5585 let ty = tcx.type_of(impl_def_id);
5587 let impl_ty = self.instantiate_type_scheme(span, &substs, &ty);
5588 match self.at(&self.misc(span), self.param_env).sup(impl_ty, self_ty) {
5589 Ok(ok) => self.register_infer_ok_obligations(ok),
5591 self.tcx.sess.delay_span_bug(span, &format!(
5592 "instantiate_value_path: (UFCS) {:?} was a subtype of {:?} but now is not?",
5600 self.check_rustc_args_require_const(def_id, hir_id, span);
5602 debug!("instantiate_value_path: type of {:?} is {:?}", hir_id, ty_substituted);
5603 self.write_substs(hir_id, substs);
5605 (ty_substituted, res)
5608 /// Add all the obligations that are required, substituting and normalized appropriately.
5609 fn add_required_obligations(&self, span: Span, def_id: DefId, substs: &SubstsRef<'tcx>) {
5610 let (bounds, spans) = self.instantiate_bounds(span, def_id, &substs);
5612 for (i, mut obligation) in traits::predicates_for_generics(
5613 traits::ObligationCause::new(span, self.body_id, traits::ItemObligation(def_id)),
5620 // This makes the error point at the bound, but we want to point at the argument
5621 if let Some(span) = spans.get(i) {
5622 obligation.cause.code = traits::BindingObligation(def_id, *span);
5624 self.register_predicate(obligation);
5628 fn check_rustc_args_require_const(&self, def_id: DefId, hir_id: hir::HirId, span: Span) {
5629 // We're only interested in functions tagged with
5630 // #[rustc_args_required_const], so ignore anything that's not.
5631 if !self.tcx.has_attr(def_id, sym::rustc_args_required_const) {
5635 // If our calling expression is indeed the function itself, we're good!
5636 // If not, generate an error that this can only be called directly.
5637 if let Node::Expr(expr) = self.tcx.hir().get(self.tcx.hir().get_parent_node(hir_id)) {
5638 if let ExprKind::Call(ref callee, ..) = expr.kind {
5639 if callee.hir_id == hir_id {
5645 self.tcx.sess.span_err(
5647 "this function can only be invoked directly, not through a function pointer",
5651 /// Resolves `typ` by a single level if `typ` is a type variable.
5652 /// If no resolution is possible, then an error is reported.
5653 /// Numeric inference variables may be left unresolved.
5654 pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
5655 let ty = self.resolve_vars_with_obligations(ty);
5656 if !ty.is_ty_var() {
5659 if !self.is_tainted_by_errors() {
5660 self.need_type_info_err((**self).body_id, sp, ty, E0282)
5661 .note("type must be known at this point")
5664 self.demand_suptype(sp, self.tcx.types.err, ty);
5669 fn with_breakable_ctxt<F: FnOnce() -> R, R>(
5672 ctxt: BreakableCtxt<'tcx>,
5674 ) -> (BreakableCtxt<'tcx>, R) {
5677 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5678 index = enclosing_breakables.stack.len();
5679 enclosing_breakables.by_id.insert(id, index);
5680 enclosing_breakables.stack.push(ctxt);
5684 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5685 debug_assert!(enclosing_breakables.stack.len() == index + 1);
5686 enclosing_breakables.by_id.remove(&id).expect("missing breakable context");
5687 enclosing_breakables.stack.pop().expect("missing breakable context")
5692 /// Instantiate a QueryResponse in a probe context, without a
5693 /// good ObligationCause.
5694 fn probe_instantiate_query_response(
5697 original_values: &OriginalQueryValues<'tcx>,
5698 query_result: &Canonical<'tcx, QueryResponse<'tcx, Ty<'tcx>>>,
5699 ) -> InferResult<'tcx, Ty<'tcx>> {
5700 self.instantiate_query_response_and_region_obligations(
5701 &traits::ObligationCause::misc(span, self.body_id),
5708 /// Returns `true` if an expression is contained inside the LHS of an assignment expression.
5709 fn expr_in_place(&self, mut expr_id: hir::HirId) -> bool {
5710 let mut contained_in_place = false;
5712 while let hir::Node::Expr(parent_expr) =
5713 self.tcx.hir().get(self.tcx.hir().get_parent_node(expr_id))
5715 match &parent_expr.kind {
5716 hir::ExprKind::Assign(lhs, ..) | hir::ExprKind::AssignOp(_, lhs, ..) => {
5717 if lhs.hir_id == expr_id {
5718 contained_in_place = true;
5724 expr_id = parent_expr.hir_id;
5731 pub fn check_bounds_are_used<'tcx>(tcx: TyCtxt<'tcx>, generics: &ty::Generics, ty: Ty<'tcx>) {
5732 let own_counts = generics.own_counts();
5734 "check_bounds_are_used(n_tys={}, n_cts={}, ty={:?})",
5735 own_counts.types, own_counts.consts, ty
5738 if own_counts.types == 0 {
5742 // Make a vector of booleans initially `false`; set to `true` when used.
5743 let mut types_used = vec![false; own_counts.types];
5745 for leaf_ty in ty.walk() {
5746 if let ty::Param(ty::ParamTy { index, .. }) = leaf_ty.kind {
5747 debug!("found use of ty param num {}", index);
5748 types_used[index as usize - own_counts.lifetimes] = true;
5749 } else if let ty::Error = leaf_ty.kind {
5750 // If there is already another error, do not emit
5751 // an error for not using a type parameter.
5752 assert!(tcx.sess.has_errors());
5757 let types = generics.params.iter().filter(|param| match param.kind {
5758 ty::GenericParamDefKind::Type { .. } => true,
5761 for (&used, param) in types_used.iter().zip(types) {
5763 let id = tcx.hir().as_local_hir_id(param.def_id).unwrap();
5764 let span = tcx.hir().span(id);
5765 struct_span_err!(tcx.sess, span, E0091, "type parameter `{}` is unused", param.name)
5766 .span_label(span, "unused type parameter")
5772 fn fatally_break_rust(sess: &Session) {
5773 let handler = sess.diagnostic();
5774 handler.span_bug_no_panic(
5776 "It looks like you're trying to break rust; would you like some ICE?",
5778 handler.note_without_error("the compiler expectedly panicked. this is a feature.");
5779 handler.note_without_error(
5780 "we would appreciate a joke overview: \
5781 https://github.com/rust-lang/rust/issues/43162#issuecomment-320764675",
5783 handler.note_without_error(&format!(
5784 "rustc {} running on {}",
5785 option_env!("CFG_VERSION").unwrap_or("unknown_version"),
5786 crate::session::config::host_triple(),
5790 fn potentially_plural_count(count: usize, word: &str) -> String {
5791 format!("{} {}{}", count, word, pluralize!(count))