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
84 mod generator_interior;
88 use crate::astconv::{AstConv, PathSeg};
89 use errors::{Applicability, DiagnosticBuilder, DiagnosticId};
90 use rustc::hir::{self, ExprKind, GenericArg, ItemKind, Node, PatKind, QPath};
91 use rustc::hir::def::{CtorOf, CtorKind, Res, DefKind};
92 use rustc::hir::def_id::{CrateNum, DefId, LOCAL_CRATE};
93 use rustc::hir::intravisit::{self, Visitor, NestedVisitorMap};
94 use rustc::hir::itemlikevisit::ItemLikeVisitor;
95 use crate::middle::lang_items;
96 use crate::namespace::Namespace;
97 use rustc::infer::{self, InferCtxt, InferOk, InferResult};
98 use rustc::infer::canonical::{Canonical, OriginalQueryValues, QueryResponse};
99 use rustc_data_structures::indexed_vec::Idx;
100 use rustc_target::spec::abi::Abi;
101 use rustc::infer::opaque_types::OpaqueTypeDecl;
102 use rustc::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
103 use rustc::infer::unify_key::{ConstVariableOrigin, ConstVariableOriginKind};
104 use rustc::middle::region;
105 use rustc::mir::interpret::{ConstValue, GlobalId};
106 use rustc::traits::{self, ObligationCause, ObligationCauseCode, TraitEngine};
108 self, AdtKind, CanonicalUserType, Ty, TyCtxt, Const, GenericParamDefKind, Visibility,
109 ToPolyTraitRef, ToPredicate, RegionKind, UserType
111 use rustc::ty::adjustment::{
112 Adjust, Adjustment, AllowTwoPhase, AutoBorrow, AutoBorrowMutability, PointerCast
114 use rustc::ty::fold::TypeFoldable;
115 use rustc::ty::query::Providers;
116 use rustc::ty::subst::{UnpackedKind, Subst, InternalSubsts, SubstsRef, UserSelfTy, UserSubsts};
117 use rustc::ty::util::{Representability, IntTypeExt, Discr};
118 use rustc::ty::layout::VariantIdx;
119 use syntax_pos::{self, BytePos, Span, MultiSpan};
120 use syntax_pos::hygiene::CompilerDesugaringKind;
123 use syntax::feature_gate::{GateIssue, emit_feature_err};
125 use syntax::source_map::{DUMMY_SP, original_sp};
126 use syntax::symbol::{Symbol, LocalInternedString, kw, sym};
127 use syntax::util::lev_distance::find_best_match_for_name;
129 use std::cell::{Cell, RefCell, Ref, RefMut};
130 use std::collections::hash_map::Entry;
132 use std::fmt::Display;
134 use std::mem::replace;
135 use std::ops::{self, Deref};
138 use crate::require_c_abi_if_c_variadic;
139 use crate::session::Session;
140 use crate::session::config::EntryFnType;
141 use crate::TypeAndSubsts;
143 use crate::util::captures::Captures;
144 use crate::util::common::{ErrorReported, indenter};
145 use crate::util::nodemap::{DefIdMap, DefIdSet, FxHashMap, FxHashSet, HirIdMap};
147 pub use self::Expectation::*;
148 use self::autoderef::Autoderef;
149 use self::callee::DeferredCallResolution;
150 use self::coercion::{CoerceMany, DynamicCoerceMany};
151 pub use self::compare_method::{compare_impl_method, compare_const_impl};
152 use self::method::{MethodCallee, SelfSource};
153 use self::TupleArgumentsFlag::*;
155 /// The type of a local binding, including the revealed type for anon types.
156 #[derive(Copy, Clone)]
157 pub struct LocalTy<'tcx> {
159 revealed_ty: Ty<'tcx>
162 /// A wrapper for `InferCtxt`'s `in_progress_tables` field.
163 #[derive(Copy, Clone)]
164 struct MaybeInProgressTables<'a, 'tcx: 'a> {
165 maybe_tables: Option<&'a RefCell<ty::TypeckTables<'tcx>>>,
168 impl<'a, 'tcx> MaybeInProgressTables<'a, 'tcx> {
169 fn borrow(self) -> Ref<'a, ty::TypeckTables<'tcx>> {
170 match self.maybe_tables {
171 Some(tables) => tables.borrow(),
173 bug!("MaybeInProgressTables: inh/fcx.tables.borrow() with no tables")
178 fn borrow_mut(self) -> RefMut<'a, ty::TypeckTables<'tcx>> {
179 match self.maybe_tables {
180 Some(tables) => tables.borrow_mut(),
182 bug!("MaybeInProgressTables: inh/fcx.tables.borrow_mut() with no tables")
188 /// Closures defined within the function. For example:
191 /// bar(move|| { ... })
194 /// Here, the function `foo()` and the closure passed to
195 /// `bar()` will each have their own `FnCtxt`, but they will
196 /// share the inherited fields.
197 pub struct Inherited<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
198 infcx: InferCtxt<'a, 'gcx, 'tcx>,
200 tables: MaybeInProgressTables<'a, 'tcx>,
202 locals: RefCell<HirIdMap<LocalTy<'tcx>>>,
204 fulfillment_cx: RefCell<Box<dyn TraitEngine<'tcx>>>,
206 // Some additional `Sized` obligations badly affect type inference.
207 // These obligations are added in a later stage of typeck.
208 deferred_sized_obligations: RefCell<Vec<(Ty<'tcx>, Span, traits::ObligationCauseCode<'tcx>)>>,
210 // When we process a call like `c()` where `c` is a closure type,
211 // we may not have decided yet whether `c` is a `Fn`, `FnMut`, or
212 // `FnOnce` closure. In that case, we defer full resolution of the
213 // call until upvar inference can kick in and make the
214 // decision. We keep these deferred resolutions grouped by the
215 // def-id of the closure, so that once we decide, we can easily go
216 // back and process them.
217 deferred_call_resolutions: RefCell<DefIdMap<Vec<DeferredCallResolution<'gcx, 'tcx>>>>,
219 deferred_cast_checks: RefCell<Vec<cast::CastCheck<'tcx>>>,
221 deferred_generator_interiors: RefCell<Vec<(hir::BodyId, Ty<'tcx>)>>,
223 // Opaque types found in explicit return types and their
224 // associated fresh inference variable. Writeback resolves these
225 // variables to get the concrete type, which can be used to
226 // 'de-opaque' OpaqueTypeDecl, after typeck is done with all functions.
227 opaque_types: RefCell<DefIdMap<OpaqueTypeDecl<'tcx>>>,
229 /// Each type parameter has an implicit region bound that
230 /// indicates it must outlive at least the function body (the user
231 /// may specify stronger requirements). This field indicates the
232 /// region of the callee. If it is `None`, then the parameter
233 /// environment is for an item or something where the "callee" is
235 implicit_region_bound: Option<ty::Region<'tcx>>,
237 body_id: Option<hir::BodyId>,
240 impl<'a, 'gcx, 'tcx> Deref for Inherited<'a, 'gcx, 'tcx> {
241 type Target = InferCtxt<'a, 'gcx, 'tcx>;
242 fn deref(&self) -> &Self::Target {
247 /// When type-checking an expression, we propagate downward
248 /// whatever type hint we are able in the form of an `Expectation`.
249 #[derive(Copy, Clone, Debug)]
250 pub enum Expectation<'tcx> {
251 /// We know nothing about what type this expression should have.
254 /// This expression should have the type given (or some subtype).
255 ExpectHasType(Ty<'tcx>),
257 /// This expression will be cast to the `Ty`.
258 ExpectCastableToType(Ty<'tcx>),
260 /// This rvalue expression will be wrapped in `&` or `Box` and coerced
261 /// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
262 ExpectRvalueLikeUnsized(Ty<'tcx>),
265 impl<'a, 'gcx, 'tcx> Expectation<'tcx> {
266 // Disregard "castable to" expectations because they
267 // can lead us astray. Consider for example `if cond
268 // {22} else {c} as u8` -- if we propagate the
269 // "castable to u8" constraint to 22, it will pick the
270 // type 22u8, which is overly constrained (c might not
271 // be a u8). In effect, the problem is that the
272 // "castable to" expectation is not the tightest thing
273 // we can say, so we want to drop it in this case.
274 // The tightest thing we can say is "must unify with
275 // else branch". Note that in the case of a "has type"
276 // constraint, this limitation does not hold.
278 // If the expected type is just a type variable, then don't use
279 // an expected type. Otherwise, we might write parts of the type
280 // when checking the 'then' block which are incompatible with the
282 fn adjust_for_branches(&self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
284 ExpectHasType(ety) => {
285 let ety = fcx.shallow_resolve(ety);
286 if !ety.is_ty_var() {
292 ExpectRvalueLikeUnsized(ety) => {
293 ExpectRvalueLikeUnsized(ety)
299 /// Provides an expectation for an rvalue expression given an *optional*
300 /// hint, which is not required for type safety (the resulting type might
301 /// be checked higher up, as is the case with `&expr` and `box expr`), but
302 /// is useful in determining the concrete type.
304 /// The primary use case is where the expected type is a fat pointer,
305 /// like `&[isize]`. For example, consider the following statement:
307 /// let x: &[isize] = &[1, 2, 3];
309 /// In this case, the expected type for the `&[1, 2, 3]` expression is
310 /// `&[isize]`. If however we were to say that `[1, 2, 3]` has the
311 /// expectation `ExpectHasType([isize])`, that would be too strong --
312 /// `[1, 2, 3]` does not have the type `[isize]` but rather `[isize; 3]`.
313 /// It is only the `&[1, 2, 3]` expression as a whole that can be coerced
314 /// to the type `&[isize]`. Therefore, we propagate this more limited hint,
315 /// which still is useful, because it informs integer literals and the like.
316 /// See the test case `test/run-pass/coerce-expect-unsized.rs` and #20169
317 /// for examples of where this comes up,.
318 fn rvalue_hint(fcx: &FnCtxt<'a, 'gcx, 'tcx>, ty: Ty<'tcx>) -> Expectation<'tcx> {
319 match fcx.tcx.struct_tail(ty).sty {
320 ty::Slice(_) | ty::Str | ty::Dynamic(..) => {
321 ExpectRvalueLikeUnsized(ty)
323 _ => ExpectHasType(ty)
327 // Resolves `expected` by a single level if it is a variable. If
328 // there is no expected type or resolution is not possible (e.g.,
329 // no constraints yet present), just returns `None`.
330 fn resolve(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
332 NoExpectation => NoExpectation,
333 ExpectCastableToType(t) => {
334 ExpectCastableToType(fcx.resolve_vars_if_possible(&t))
336 ExpectHasType(t) => {
337 ExpectHasType(fcx.resolve_vars_if_possible(&t))
339 ExpectRvalueLikeUnsized(t) => {
340 ExpectRvalueLikeUnsized(fcx.resolve_vars_if_possible(&t))
345 fn to_option(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Option<Ty<'tcx>> {
346 match self.resolve(fcx) {
347 NoExpectation => None,
348 ExpectCastableToType(ty) |
350 ExpectRvalueLikeUnsized(ty) => Some(ty),
354 /// It sometimes happens that we want to turn an expectation into
355 /// a **hard constraint** (i.e., something that must be satisfied
356 /// for the program to type-check). `only_has_type` will return
357 /// such a constraint, if it exists.
358 fn only_has_type(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Option<Ty<'tcx>> {
359 match self.resolve(fcx) {
360 ExpectHasType(ty) => Some(ty),
361 NoExpectation | ExpectCastableToType(_) | ExpectRvalueLikeUnsized(_) => None,
365 /// Like `only_has_type`, but instead of returning `None` if no
366 /// hard constraint exists, creates a fresh type variable.
367 fn coercion_target_type(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>, span: Span) -> Ty<'tcx> {
368 self.only_has_type(fcx)
370 fcx.next_ty_var(TypeVariableOrigin {
371 kind: TypeVariableOriginKind::MiscVariable,
378 #[derive(Copy, Clone, Debug, PartialEq, Eq)]
385 fn maybe_mut_place(m: hir::Mutability) -> Self {
387 hir::MutMutable => Needs::MutPlace,
388 hir::MutImmutable => Needs::None,
393 #[derive(Copy, Clone)]
394 pub struct UnsafetyState {
396 pub unsafety: hir::Unsafety,
397 pub unsafe_push_count: u32,
402 pub fn function(unsafety: hir::Unsafety, def: hir::HirId) -> UnsafetyState {
403 UnsafetyState { def: def, unsafety: unsafety, unsafe_push_count: 0, from_fn: true }
406 pub fn recurse(&mut self, blk: &hir::Block) -> UnsafetyState {
407 match self.unsafety {
408 // If this unsafe, then if the outer function was already marked as
409 // unsafe we shouldn't attribute the unsafe'ness to the block. This
410 // way the block can be warned about instead of ignoring this
411 // extraneous block (functions are never warned about).
412 hir::Unsafety::Unsafe if self.from_fn => *self,
415 let (unsafety, def, count) = match blk.rules {
416 hir::PushUnsafeBlock(..) =>
417 (unsafety, blk.hir_id, self.unsafe_push_count.checked_add(1).unwrap()),
418 hir::PopUnsafeBlock(..) =>
419 (unsafety, blk.hir_id, self.unsafe_push_count.checked_sub(1).unwrap()),
420 hir::UnsafeBlock(..) =>
421 (hir::Unsafety::Unsafe, blk.hir_id, self.unsafe_push_count),
423 (unsafety, self.def, self.unsafe_push_count),
427 unsafe_push_count: count,
434 #[derive(Debug, Copy, Clone)]
440 /// Tracks whether executing a node may exit normally (versus
441 /// return/break/panic, which "diverge", leaving dead code in their
442 /// wake). Tracked semi-automatically (through type variables marked
443 /// as diverging), with some manual adjustments for control-flow
444 /// primitives (approximating a CFG).
445 #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)]
447 /// Potentially unknown, some cases converge,
448 /// others require a CFG to determine them.
451 /// Definitely known to diverge and therefore
452 /// not reach the next sibling or its parent.
455 /// Same as `Always` but with a reachability
456 /// warning already emitted.
460 // Convenience impls for combinig `Diverges`.
462 impl ops::BitAnd for Diverges {
464 fn bitand(self, other: Self) -> Self {
465 cmp::min(self, other)
469 impl ops::BitOr for Diverges {
471 fn bitor(self, other: Self) -> Self {
472 cmp::max(self, other)
476 impl ops::BitAndAssign for Diverges {
477 fn bitand_assign(&mut self, other: Self) {
478 *self = *self & other;
482 impl ops::BitOrAssign for Diverges {
483 fn bitor_assign(&mut self, other: Self) {
484 *self = *self | other;
489 fn always(self) -> bool {
490 self >= Diverges::Always
494 pub struct BreakableCtxt<'gcx: 'tcx, 'tcx> {
497 // this is `null` for loops where break with a value is illegal,
498 // such as `while`, `for`, and `while let`
499 coerce: Option<DynamicCoerceMany<'gcx, 'tcx>>,
502 pub struct EnclosingBreakables<'gcx: 'tcx, 'tcx> {
503 stack: Vec<BreakableCtxt<'gcx, 'tcx>>,
504 by_id: HirIdMap<usize>,
507 impl<'gcx, 'tcx> EnclosingBreakables<'gcx, 'tcx> {
508 fn find_breakable(&mut self, target_id: hir::HirId) -> &mut BreakableCtxt<'gcx, 'tcx> {
509 let ix = *self.by_id.get(&target_id).unwrap_or_else(|| {
510 bug!("could not find enclosing breakable with id {}", target_id);
516 pub struct FnCtxt<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
519 /// The parameter environment used for proving trait obligations
520 /// in this function. This can change when we descend into
521 /// closures (as they bring new things into scope), hence it is
522 /// not part of `Inherited` (as of the time of this writing,
523 /// closures do not yet change the environment, but they will
525 param_env: ty::ParamEnv<'tcx>,
527 /// Number of errors that had been reported when we started
528 /// checking this function. On exit, if we find that *more* errors
529 /// have been reported, we will skip regionck and other work that
530 /// expects the types within the function to be consistent.
531 err_count_on_creation: usize,
533 ret_coercion: Option<RefCell<DynamicCoerceMany<'gcx, 'tcx>>>,
534 ret_coercion_span: RefCell<Option<Span>>,
536 yield_ty: Option<Ty<'tcx>>,
538 ps: RefCell<UnsafetyState>,
540 /// Whether the last checked node generates a divergence (e.g.,
541 /// `return` will set this to `Always`). In general, when entering
542 /// an expression or other node in the tree, the initial value
543 /// indicates whether prior parts of the containing expression may
544 /// have diverged. It is then typically set to `Maybe` (and the
545 /// old value remembered) for processing the subparts of the
546 /// current expression. As each subpart is processed, they may set
547 /// the flag to `Always`, etc. Finally, at the end, we take the
548 /// result and "union" it with the original value, so that when we
549 /// return the flag indicates if any subpart of the parent
550 /// expression (up to and including this part) has diverged. So,
551 /// if you read it after evaluating a subexpression `X`, the value
552 /// you get indicates whether any subexpression that was
553 /// evaluating up to and including `X` diverged.
555 /// We currently use this flag only for diagnostic purposes:
557 /// - To warn about unreachable code: if, after processing a
558 /// sub-expression but before we have applied the effects of the
559 /// current node, we see that the flag is set to `Always`, we
560 /// can issue a warning. This corresponds to something like
561 /// `foo(return)`; we warn on the `foo()` expression. (We then
562 /// update the flag to `WarnedAlways` to suppress duplicate
563 /// reports.) Similarly, if we traverse to a fresh statement (or
564 /// tail expression) from a `Always` setting, we will issue a
565 /// warning. This corresponds to something like `{return;
566 /// foo();}` or `{return; 22}`, where we would warn on the
569 /// An expression represents dead code if, after checking it,
570 /// the diverges flag is set to something other than `Maybe`.
571 diverges: Cell<Diverges>,
573 /// Whether any child nodes have any type errors.
574 has_errors: Cell<bool>,
576 enclosing_breakables: RefCell<EnclosingBreakables<'gcx, 'tcx>>,
578 inh: &'a Inherited<'a, 'gcx, 'tcx>,
581 impl<'a, 'gcx, 'tcx> Deref for FnCtxt<'a, 'gcx, 'tcx> {
582 type Target = Inherited<'a, 'gcx, 'tcx>;
583 fn deref(&self) -> &Self::Target {
588 /// Helper type of a temporary returned by `Inherited::build(...)`.
589 /// Necessary because we can't write the following bound:
590 /// `F: for<'b, 'tcx> where 'gcx: 'tcx FnOnce(Inherited<'b, 'gcx, 'tcx>)`.
591 pub struct InheritedBuilder<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
592 infcx: infer::InferCtxtBuilder<'a, 'gcx, 'tcx>,
596 impl<'a, 'gcx, 'tcx> Inherited<'a, 'gcx, 'tcx> {
597 pub fn build(tcx: TyCtxt<'a, 'gcx, 'gcx>, def_id: DefId)
598 -> InheritedBuilder<'a, 'gcx, 'tcx> {
599 let hir_id_root = if def_id.is_local() {
600 let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
601 DefId::local(hir_id.owner)
607 infcx: tcx.infer_ctxt().with_fresh_in_progress_tables(hir_id_root),
613 impl<'a, 'gcx, 'tcx> InheritedBuilder<'a, 'gcx, 'tcx> {
614 fn enter<F, R>(&'tcx mut self, f: F) -> R
615 where F: for<'b> FnOnce(Inherited<'b, 'gcx, 'tcx>) -> R
617 let def_id = self.def_id;
618 self.infcx.enter(|infcx| f(Inherited::new(infcx, def_id)))
622 impl<'a, 'gcx, 'tcx> Inherited<'a, 'gcx, 'tcx> {
623 fn new(infcx: InferCtxt<'a, 'gcx, 'tcx>, def_id: DefId) -> Self {
625 let item_id = tcx.hir().as_local_hir_id(def_id);
626 let body_id = item_id.and_then(|id| tcx.hir().maybe_body_owned_by_by_hir_id(id));
627 let implicit_region_bound = body_id.map(|body_id| {
628 let body = tcx.hir().body(body_id);
629 tcx.mk_region(ty::ReScope(region::Scope {
630 id: body.value.hir_id.local_id,
631 data: region::ScopeData::CallSite
636 tables: MaybeInProgressTables {
637 maybe_tables: infcx.in_progress_tables,
640 fulfillment_cx: RefCell::new(TraitEngine::new(tcx)),
641 locals: RefCell::new(Default::default()),
642 deferred_sized_obligations: RefCell::new(Vec::new()),
643 deferred_call_resolutions: RefCell::new(Default::default()),
644 deferred_cast_checks: RefCell::new(Vec::new()),
645 deferred_generator_interiors: RefCell::new(Vec::new()),
646 opaque_types: RefCell::new(Default::default()),
647 implicit_region_bound,
652 fn register_predicate(&self, obligation: traits::PredicateObligation<'tcx>) {
653 debug!("register_predicate({:?})", obligation);
654 if obligation.has_escaping_bound_vars() {
655 span_bug!(obligation.cause.span, "escaping bound vars in predicate {:?}",
660 .register_predicate_obligation(self, obligation);
663 fn register_predicates<I>(&self, obligations: I)
664 where I: IntoIterator<Item = traits::PredicateObligation<'tcx>>
666 for obligation in obligations {
667 self.register_predicate(obligation);
671 fn register_infer_ok_obligations<T>(&self, infer_ok: InferOk<'tcx, T>) -> T {
672 self.register_predicates(infer_ok.obligations);
676 fn normalize_associated_types_in<T>(&self,
679 param_env: ty::ParamEnv<'tcx>,
681 where T : TypeFoldable<'tcx>
683 let ok = self.partially_normalize_associated_types_in(span, body_id, param_env, value);
684 self.register_infer_ok_obligations(ok)
688 struct CheckItemTypesVisitor<'a, 'tcx: 'a> { tcx: TyCtxt<'a, 'tcx, 'tcx> }
690 impl<'a, 'tcx> ItemLikeVisitor<'tcx> for CheckItemTypesVisitor<'a, 'tcx> {
691 fn visit_item(&mut self, i: &'tcx hir::Item) {
692 check_item_type(self.tcx, i);
694 fn visit_trait_item(&mut self, _: &'tcx hir::TraitItem) { }
695 fn visit_impl_item(&mut self, _: &'tcx hir::ImplItem) { }
698 pub fn check_wf_new<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Result<(), ErrorReported> {
699 tcx.sess.track_errors(|| {
700 let mut visit = wfcheck::CheckTypeWellFormedVisitor::new(tcx);
701 tcx.hir().krate().par_visit_all_item_likes(&mut visit);
705 fn check_mod_item_types<'tcx>(tcx: TyCtxt<'_, 'tcx, 'tcx>, module_def_id: DefId) {
706 tcx.hir().visit_item_likes_in_module(module_def_id, &mut CheckItemTypesVisitor { tcx });
709 fn typeck_item_bodies<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, crate_num: CrateNum) {
710 debug_assert!(crate_num == LOCAL_CRATE);
711 tcx.par_body_owners(|body_owner_def_id| {
712 tcx.ensure().typeck_tables_of(body_owner_def_id);
716 fn check_item_well_formed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) {
717 wfcheck::check_item_well_formed(tcx, def_id);
720 fn check_trait_item_well_formed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) {
721 wfcheck::check_trait_item(tcx, def_id);
724 fn check_impl_item_well_formed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) {
725 wfcheck::check_impl_item(tcx, def_id);
728 pub fn provide(providers: &mut Providers<'_>) {
729 method::provide(providers);
730 *providers = Providers {
736 check_item_well_formed,
737 check_trait_item_well_formed,
738 check_impl_item_well_formed,
739 check_mod_item_types,
744 fn adt_destructor<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
746 -> Option<ty::Destructor> {
747 tcx.calculate_dtor(def_id, &mut dropck::check_drop_impl)
750 /// If this `DefId` is a "primary tables entry", returns `Some((body_id, decl))`
751 /// with information about it's body-id and fn-decl (if any). Otherwise,
754 /// If this function returns "some", then `typeck_tables(def_id)` will
755 /// succeed; if it returns `None`, then `typeck_tables(def_id)` may or
756 /// may not succeed. In some cases where this function returns `None`
757 /// (notably closures), `typeck_tables(def_id)` would wind up
758 /// redirecting to the owning function.
759 fn primary_body_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
761 -> Option<(hir::BodyId, Option<&'tcx hir::FnDecl>)>
763 match tcx.hir().get_by_hir_id(id) {
764 Node::Item(item) => {
766 hir::ItemKind::Const(_, body) |
767 hir::ItemKind::Static(_, _, body) =>
769 hir::ItemKind::Fn(ref decl, .., body) =>
770 Some((body, Some(decl))),
775 Node::TraitItem(item) => {
777 hir::TraitItemKind::Const(_, Some(body)) =>
779 hir::TraitItemKind::Method(ref sig, hir::TraitMethod::Provided(body)) =>
780 Some((body, Some(&sig.decl))),
785 Node::ImplItem(item) => {
787 hir::ImplItemKind::Const(_, body) =>
789 hir::ImplItemKind::Method(ref sig, body) =>
790 Some((body, Some(&sig.decl))),
795 Node::AnonConst(constant) => Some((constant.body, None)),
800 fn has_typeck_tables<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
803 // Closures' tables come from their outermost function,
804 // as they are part of the same "inference environment".
805 let outer_def_id = tcx.closure_base_def_id(def_id);
806 if outer_def_id != def_id {
807 return tcx.has_typeck_tables(outer_def_id);
810 let id = tcx.hir().as_local_hir_id(def_id).unwrap();
811 primary_body_of(tcx, id).is_some()
814 fn used_trait_imports<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
817 &*tcx.typeck_tables_of(def_id).used_trait_imports
820 fn typeck_tables_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
822 -> &'tcx ty::TypeckTables<'tcx> {
823 // Closures' tables come from their outermost function,
824 // as they are part of the same "inference environment".
825 let outer_def_id = tcx.closure_base_def_id(def_id);
826 if outer_def_id != def_id {
827 return tcx.typeck_tables_of(outer_def_id);
830 let id = tcx.hir().as_local_hir_id(def_id).unwrap();
831 let span = tcx.hir().span_by_hir_id(id);
833 // Figure out what primary body this item has.
834 let (body_id, fn_decl) = primary_body_of(tcx, id).unwrap_or_else(|| {
835 span_bug!(span, "can't type-check body of {:?}", def_id);
837 let body = tcx.hir().body(body_id);
839 let tables = Inherited::build(tcx, def_id).enter(|inh| {
840 let param_env = tcx.param_env(def_id);
841 let fcx = if let Some(decl) = fn_decl {
842 let fn_sig = tcx.fn_sig(def_id);
844 check_abi(tcx, span, fn_sig.abi());
846 // Compute the fty from point of view of inside the fn.
848 tcx.liberate_late_bound_regions(def_id, &fn_sig);
850 inh.normalize_associated_types_in(body.value.span,
855 let fcx = check_fn(&inh, param_env, fn_sig, decl, id, body, None).0;
858 let fcx = FnCtxt::new(&inh, param_env, body.value.hir_id);
859 let expected_type = tcx.type_of(def_id);
860 let expected_type = fcx.normalize_associated_types_in(body.value.span, &expected_type);
861 fcx.require_type_is_sized(expected_type, body.value.span, traits::ConstSized);
863 let revealed_ty = if tcx.features().impl_trait_in_bindings {
864 fcx.instantiate_opaque_types_from_value(
872 // Gather locals in statics (because of block expressions).
873 GatherLocalsVisitor { fcx: &fcx, parent_id: id, }.visit_body(body);
875 fcx.check_expr_coercable_to_type(&body.value, revealed_ty);
877 fcx.write_ty(id, revealed_ty);
882 // All type checking constraints were added, try to fallback unsolved variables.
883 fcx.select_obligations_where_possible(false);
884 let mut fallback_has_occurred = false;
885 for ty in &fcx.unsolved_variables() {
886 fallback_has_occurred |= fcx.fallback_if_possible(ty);
888 fcx.select_obligations_where_possible(fallback_has_occurred);
890 // Even though coercion casts provide type hints, we check casts after fallback for
891 // backwards compatibility. This makes fallback a stronger type hint than a cast coercion.
894 // Closure and generator analysis may run after fallback
895 // because they don't constrain other type variables.
896 fcx.closure_analyze(body);
897 assert!(fcx.deferred_call_resolutions.borrow().is_empty());
898 fcx.resolve_generator_interiors(def_id);
900 for (ty, span, code) in fcx.deferred_sized_obligations.borrow_mut().drain(..) {
901 let ty = fcx.normalize_ty(span, ty);
902 fcx.require_type_is_sized(ty, span, code);
904 fcx.select_all_obligations_or_error();
906 if fn_decl.is_some() {
907 fcx.regionck_fn(id, body);
909 fcx.regionck_expr(body);
912 fcx.resolve_type_vars_in_body(body)
915 // Consistency check our TypeckTables instance can hold all ItemLocalIds
916 // it will need to hold.
917 assert_eq!(tables.local_id_root, Some(DefId::local(id.owner)));
922 fn check_abi<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, span: Span, abi: Abi) {
923 if !tcx.sess.target.target.is_abi_supported(abi) {
924 struct_span_err!(tcx.sess, span, E0570,
925 "The ABI `{}` is not supported for the current target", abi).emit()
929 struct GatherLocalsVisitor<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
930 fcx: &'a FnCtxt<'a, 'gcx, 'tcx>,
931 parent_id: hir::HirId,
934 impl<'a, 'gcx, 'tcx> GatherLocalsVisitor<'a, 'gcx, 'tcx> {
935 fn assign(&mut self, span: Span, nid: hir::HirId, ty_opt: Option<LocalTy<'tcx>>) -> Ty<'tcx> {
938 // infer the variable's type
939 let var_ty = self.fcx.next_ty_var(TypeVariableOrigin {
940 kind: TypeVariableOriginKind::TypeInference,
943 self.fcx.locals.borrow_mut().insert(nid, LocalTy {
950 // take type that the user specified
951 self.fcx.locals.borrow_mut().insert(nid, typ);
958 impl<'a, 'gcx, 'tcx> Visitor<'gcx> for GatherLocalsVisitor<'a, 'gcx, 'tcx> {
959 fn nested_visit_map<'this>(&'this mut self) -> NestedVisitorMap<'this, 'gcx> {
960 NestedVisitorMap::None
963 // Add explicitly-declared locals.
964 fn visit_local(&mut self, local: &'gcx hir::Local) {
965 let local_ty = match local.ty {
967 let o_ty = self.fcx.to_ty(&ty);
969 let revealed_ty = if self.fcx.tcx.features().impl_trait_in_bindings {
970 self.fcx.instantiate_opaque_types_from_value(
978 let c_ty = self.fcx.inh.infcx.canonicalize_user_type_annotation(
979 &UserType::Ty(revealed_ty)
981 debug!("visit_local: ty.hir_id={:?} o_ty={:?} revealed_ty={:?} c_ty={:?}",
982 ty.hir_id, o_ty, revealed_ty, c_ty);
983 self.fcx.tables.borrow_mut().user_provided_types_mut().insert(ty.hir_id, c_ty);
985 Some(LocalTy { decl_ty: o_ty, revealed_ty })
989 self.assign(local.span, local.hir_id, local_ty);
991 debug!("Local variable {:?} is assigned type {}",
993 self.fcx.ty_to_string(
994 self.fcx.locals.borrow().get(&local.hir_id).unwrap().clone().decl_ty));
995 intravisit::walk_local(self, local);
998 // Add pattern bindings.
999 fn visit_pat(&mut self, p: &'gcx hir::Pat) {
1000 if let PatKind::Binding(_, _, ident, _) = p.node {
1001 let var_ty = self.assign(p.span, p.hir_id, None);
1003 let node_id = self.fcx.tcx.hir().hir_to_node_id(p.hir_id);
1004 if !self.fcx.tcx.features().unsized_locals {
1005 self.fcx.require_type_is_sized(var_ty, p.span,
1006 traits::VariableType(node_id));
1009 debug!("Pattern binding {} is assigned to {} with type {:?}",
1011 self.fcx.ty_to_string(
1012 self.fcx.locals.borrow().get(&p.hir_id).unwrap().clone().decl_ty),
1015 intravisit::walk_pat(self, p);
1018 // Don't descend into the bodies of nested closures
1019 fn visit_fn(&mut self, _: intravisit::FnKind<'gcx>, _: &'gcx hir::FnDecl,
1020 _: hir::BodyId, _: Span, _: hir::HirId) { }
1023 /// When `check_fn` is invoked on a generator (i.e., a body that
1024 /// includes yield), it returns back some information about the yield
1026 struct GeneratorTypes<'tcx> {
1027 /// Type of value that is yielded.
1030 /// Types that are captured (see `GeneratorInterior` for more).
1033 /// Indicates if the generator is movable or static (immovable).
1034 movability: hir::GeneratorMovability,
1037 /// Helper used for fns and closures. Does the grungy work of checking a function
1038 /// body and returns the function context used for that purpose, since in the case of a fn item
1039 /// there is still a bit more to do.
1042 /// * inherited: other fields inherited from the enclosing fn (if any)
1043 fn check_fn<'a, 'gcx, 'tcx>(inherited: &'a Inherited<'a, 'gcx, 'tcx>,
1044 param_env: ty::ParamEnv<'tcx>,
1045 fn_sig: ty::FnSig<'tcx>,
1046 decl: &'gcx hir::FnDecl,
1048 body: &'gcx hir::Body,
1049 can_be_generator: Option<hir::GeneratorMovability>)
1050 -> (FnCtxt<'a, 'gcx, 'tcx>, Option<GeneratorTypes<'tcx>>)
1052 let mut fn_sig = fn_sig.clone();
1054 debug!("check_fn(sig={:?}, fn_id={}, param_env={:?})", fn_sig, fn_id, param_env);
1056 // Create the function context. This is either derived from scratch or,
1057 // in the case of closures, based on the outer context.
1058 let mut fcx = FnCtxt::new(inherited, param_env, body.value.hir_id);
1059 *fcx.ps.borrow_mut() = UnsafetyState::function(fn_sig.unsafety, fn_id);
1061 let declared_ret_ty = fn_sig.output();
1062 fcx.require_type_is_sized(declared_ret_ty, decl.output.span(), traits::SizedReturnType);
1063 let revealed_ret_ty = fcx.instantiate_opaque_types_from_value(fn_id, &declared_ret_ty);
1064 fcx.ret_coercion = Some(RefCell::new(CoerceMany::new(revealed_ret_ty)));
1065 fn_sig = fcx.tcx.mk_fn_sig(
1066 fn_sig.inputs().iter().cloned(),
1073 let span = body.value.span;
1075 if body.is_generator && can_be_generator.is_some() {
1076 let yield_ty = fcx.next_ty_var(TypeVariableOrigin {
1077 kind: TypeVariableOriginKind::TypeInference,
1080 fcx.require_type_is_sized(yield_ty, span, traits::SizedYieldType);
1081 fcx.yield_ty = Some(yield_ty);
1084 let outer_def_id = fcx.tcx.closure_base_def_id(fcx.tcx.hir().local_def_id_from_hir_id(fn_id));
1085 let outer_hir_id = fcx.tcx.hir().as_local_hir_id(outer_def_id).unwrap();
1086 GatherLocalsVisitor { fcx: &fcx, parent_id: outer_hir_id, }.visit_body(body);
1088 // Add formal parameters.
1089 for (arg_ty, arg) in fn_sig.inputs().iter().zip(&body.arguments) {
1090 // Check the pattern.
1091 let binding_mode = ty::BindingMode::BindByValue(hir::Mutability::MutImmutable);
1092 fcx.check_pat_walk(&arg.pat, arg_ty, binding_mode, None);
1094 // Check that argument is Sized.
1095 // The check for a non-trivial pattern is a hack to avoid duplicate warnings
1096 // for simple cases like `fn foo(x: Trait)`,
1097 // where we would error once on the parameter as a whole, and once on the binding `x`.
1098 if arg.pat.simple_ident().is_none() && !fcx.tcx.features().unsized_locals {
1099 fcx.require_type_is_sized(arg_ty, decl.output.span(), traits::SizedArgumentType);
1102 fcx.write_ty(arg.hir_id, arg_ty);
1105 inherited.tables.borrow_mut().liberated_fn_sigs_mut().insert(fn_id, fn_sig);
1107 fcx.check_return_expr(&body.value);
1109 // We insert the deferred_generator_interiors entry after visiting the body.
1110 // This ensures that all nested generators appear before the entry of this generator.
1111 // resolve_generator_interiors relies on this property.
1112 let gen_ty = if can_be_generator.is_some() && body.is_generator {
1113 let interior = fcx.next_ty_var(TypeVariableOrigin {
1114 kind: TypeVariableOriginKind::MiscVariable,
1117 fcx.deferred_generator_interiors.borrow_mut().push((body.id(), interior));
1118 Some(GeneratorTypes {
1119 yield_ty: fcx.yield_ty.unwrap(),
1121 movability: can_be_generator.unwrap(),
1127 // Finalize the return check by taking the LUB of the return types
1128 // we saw and assigning it to the expected return type. This isn't
1129 // really expected to fail, since the coercions would have failed
1130 // earlier when trying to find a LUB.
1132 // However, the behavior around `!` is sort of complex. In the
1133 // event that the `actual_return_ty` comes back as `!`, that
1134 // indicates that the fn either does not return or "returns" only
1135 // values of type `!`. In this case, if there is an expected
1136 // return type that is *not* `!`, that should be ok. But if the
1137 // return type is being inferred, we want to "fallback" to `!`:
1139 // let x = move || panic!();
1141 // To allow for that, I am creating a type variable with diverging
1142 // fallback. This was deemed ever so slightly better than unifying
1143 // the return value with `!` because it allows for the caller to
1144 // make more assumptions about the return type (e.g., they could do
1146 // let y: Option<u32> = Some(x());
1148 // which would then cause this return type to become `u32`, not
1150 let coercion = fcx.ret_coercion.take().unwrap().into_inner();
1151 let mut actual_return_ty = coercion.complete(&fcx);
1152 if actual_return_ty.is_never() {
1153 actual_return_ty = fcx.next_diverging_ty_var(
1154 TypeVariableOrigin {
1155 kind: TypeVariableOriginKind::DivergingFn,
1160 fcx.demand_suptype(span, revealed_ret_ty, actual_return_ty);
1162 // Check that the main return type implements the termination trait.
1163 if let Some(term_id) = fcx.tcx.lang_items().termination() {
1164 if let Some((def_id, EntryFnType::Main)) = fcx.tcx.entry_fn(LOCAL_CRATE) {
1165 let main_id = fcx.tcx.hir().as_local_hir_id(def_id).unwrap();
1166 if main_id == fn_id {
1167 let substs = fcx.tcx.mk_substs_trait(declared_ret_ty, &[]);
1168 let trait_ref = ty::TraitRef::new(term_id, substs);
1169 let return_ty_span = decl.output.span();
1170 let cause = traits::ObligationCause::new(
1171 return_ty_span, fn_id, ObligationCauseCode::MainFunctionType);
1173 inherited.register_predicate(
1174 traits::Obligation::new(
1175 cause, param_env, trait_ref.to_predicate()));
1180 // Check that a function marked as `#[panic_handler]` has signature `fn(&PanicInfo) -> !`
1181 if let Some(panic_impl_did) = fcx.tcx.lang_items().panic_impl() {
1182 if panic_impl_did == fcx.tcx.hir().local_def_id_from_hir_id(fn_id) {
1183 if let Some(panic_info_did) = fcx.tcx.lang_items().panic_info() {
1184 // at this point we don't care if there are duplicate handlers or if the handler has
1185 // the wrong signature as this value we'll be used when writing metadata and that
1186 // only happens if compilation succeeded
1187 fcx.tcx.sess.has_panic_handler.try_set_same(true);
1189 if declared_ret_ty.sty != ty::Never {
1190 fcx.tcx.sess.span_err(
1192 "return type should be `!`",
1196 let inputs = fn_sig.inputs();
1197 let span = fcx.tcx.hir().span_by_hir_id(fn_id);
1198 if inputs.len() == 1 {
1199 let arg_is_panic_info = match inputs[0].sty {
1200 ty::Ref(region, ty, mutbl) => match ty.sty {
1201 ty::Adt(ref adt, _) => {
1202 adt.did == panic_info_did &&
1203 mutbl == hir::Mutability::MutImmutable &&
1204 *region != RegionKind::ReStatic
1211 if !arg_is_panic_info {
1212 fcx.tcx.sess.span_err(
1213 decl.inputs[0].span,
1214 "argument should be `&PanicInfo`",
1218 if let Node::Item(item) = fcx.tcx.hir().get_by_hir_id(fn_id) {
1219 if let ItemKind::Fn(_, _, ref generics, _) = item.node {
1220 if !generics.params.is_empty() {
1221 fcx.tcx.sess.span_err(
1223 "should have no type parameters",
1229 let span = fcx.tcx.sess.source_map().def_span(span);
1230 fcx.tcx.sess.span_err(span, "function should have one argument");
1233 fcx.tcx.sess.err("language item required, but not found: `panic_info`");
1238 // Check that a function marked as `#[alloc_error_handler]` has signature `fn(Layout) -> !`
1239 if let Some(alloc_error_handler_did) = fcx.tcx.lang_items().oom() {
1240 if alloc_error_handler_did == fcx.tcx.hir().local_def_id_from_hir_id(fn_id) {
1241 if let Some(alloc_layout_did) = fcx.tcx.lang_items().alloc_layout() {
1242 if declared_ret_ty.sty != ty::Never {
1243 fcx.tcx.sess.span_err(
1245 "return type should be `!`",
1249 let inputs = fn_sig.inputs();
1250 let span = fcx.tcx.hir().span_by_hir_id(fn_id);
1251 if inputs.len() == 1 {
1252 let arg_is_alloc_layout = match inputs[0].sty {
1253 ty::Adt(ref adt, _) => {
1254 adt.did == alloc_layout_did
1259 if !arg_is_alloc_layout {
1260 fcx.tcx.sess.span_err(
1261 decl.inputs[0].span,
1262 "argument should be `Layout`",
1266 if let Node::Item(item) = fcx.tcx.hir().get_by_hir_id(fn_id) {
1267 if let ItemKind::Fn(_, _, ref generics, _) = item.node {
1268 if !generics.params.is_empty() {
1269 fcx.tcx.sess.span_err(
1271 "`#[alloc_error_handler]` function should have no type \
1278 let span = fcx.tcx.sess.source_map().def_span(span);
1279 fcx.tcx.sess.span_err(span, "function should have one argument");
1282 fcx.tcx.sess.err("language item required, but not found: `alloc_layout`");
1290 fn check_struct<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1293 let def_id = tcx.hir().local_def_id_from_hir_id(id);
1294 let def = tcx.adt_def(def_id);
1295 def.destructor(tcx); // force the destructor to be evaluated
1296 check_representable(tcx, span, def_id);
1298 if def.repr.simd() {
1299 check_simd(tcx, span, def_id);
1302 check_transparent(tcx, span, def_id);
1303 check_packed(tcx, span, def_id);
1306 fn check_union<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1309 let def_id = tcx.hir().local_def_id_from_hir_id(id);
1310 let def = tcx.adt_def(def_id);
1311 def.destructor(tcx); // force the destructor to be evaluated
1312 check_representable(tcx, span, def_id);
1313 check_transparent(tcx, span, def_id);
1314 check_packed(tcx, span, def_id);
1317 fn check_opaque<'a, 'tcx>(
1318 tcx: TyCtxt<'a, 'tcx, 'tcx>,
1320 substs: SubstsRef<'tcx>,
1323 if let Err(partially_expanded_type) = tcx.try_expand_impl_trait_type(def_id, substs) {
1324 let mut err = struct_span_err!(
1325 tcx.sess, span, E0720,
1326 "opaque type expands to a recursive type",
1328 err.span_label(span, "expands to self-referential type");
1329 if let ty::Opaque(..) = partially_expanded_type.sty {
1330 err.note("type resolves to itself");
1332 err.note(&format!("expanded type is `{}`", partially_expanded_type));
1338 pub fn check_item_type<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item) {
1340 "check_item_type(it.hir_id={}, it.name={})",
1342 tcx.def_path_str(tcx.hir().local_def_id_from_hir_id(it.hir_id))
1344 let _indenter = indenter();
1346 // Consts can play a role in type-checking, so they are included here.
1347 hir::ItemKind::Static(..) => {
1348 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1349 tcx.typeck_tables_of(def_id);
1350 maybe_check_static_with_link_section(tcx, def_id, it.span);
1352 hir::ItemKind::Const(..) => {
1353 tcx.typeck_tables_of(tcx.hir().local_def_id_from_hir_id(it.hir_id));
1355 hir::ItemKind::Enum(ref enum_definition, _) => {
1356 check_enum(tcx, it.span, &enum_definition.variants, it.hir_id);
1358 hir::ItemKind::Fn(..) => {} // entirely within check_item_body
1359 hir::ItemKind::Impl(.., ref impl_item_refs) => {
1360 debug!("ItemKind::Impl {} with id {}", it.ident, it.hir_id);
1361 let impl_def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1362 if let Some(impl_trait_ref) = tcx.impl_trait_ref(impl_def_id) {
1363 check_impl_items_against_trait(
1370 let trait_def_id = impl_trait_ref.def_id;
1371 check_on_unimplemented(tcx, trait_def_id, it);
1374 hir::ItemKind::Trait(..) => {
1375 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1376 check_on_unimplemented(tcx, def_id, it);
1378 hir::ItemKind::Struct(..) => {
1379 check_struct(tcx, it.hir_id, it.span);
1381 hir::ItemKind::Union(..) => {
1382 check_union(tcx, it.hir_id, it.span);
1384 hir::ItemKind::Existential(..) => {
1385 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1387 let substs = InternalSubsts::identity_for_item(tcx, def_id);
1388 check_opaque(tcx, def_id, substs, it.span);
1390 hir::ItemKind::Ty(..) => {
1391 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1392 let pty_ty = tcx.type_of(def_id);
1393 let generics = tcx.generics_of(def_id);
1394 check_bounds_are_used(tcx, &generics, pty_ty);
1396 hir::ItemKind::ForeignMod(ref m) => {
1397 check_abi(tcx, it.span, m.abi);
1399 if m.abi == Abi::RustIntrinsic {
1400 for item in &m.items {
1401 intrinsic::check_intrinsic_type(tcx, item);
1403 } else if m.abi == Abi::PlatformIntrinsic {
1404 for item in &m.items {
1405 intrinsic::check_platform_intrinsic_type(tcx, item);
1408 for item in &m.items {
1409 let generics = tcx.generics_of(tcx.hir().local_def_id_from_hir_id(item.hir_id));
1410 if generics.params.len() - generics.own_counts().lifetimes != 0 {
1411 let mut err = struct_span_err!(
1415 "foreign items may not have type parameters"
1417 err.span_label(item.span, "can't have type parameters");
1418 // FIXME: once we start storing spans for type arguments, turn this into a
1421 "use specialization instead of type parameters by replacing them \
1422 with concrete types like `u32`",
1427 if let hir::ForeignItemKind::Fn(ref fn_decl, _, _) = item.node {
1428 require_c_abi_if_c_variadic(tcx, fn_decl, m.abi, item.span);
1433 _ => { /* nothing to do */ }
1437 fn maybe_check_static_with_link_section(tcx: TyCtxt<'_, '_, '_>, id: DefId, span: Span) {
1438 // Only restricted on wasm32 target for now
1439 if !tcx.sess.opts.target_triple.triple().starts_with("wasm32") {
1443 // If `#[link_section]` is missing, then nothing to verify
1444 let attrs = tcx.codegen_fn_attrs(id);
1445 if attrs.link_section.is_none() {
1449 // For the wasm32 target statics with #[link_section] are placed into custom
1450 // sections of the final output file, but this isn't link custom sections of
1451 // other executable formats. Namely we can only embed a list of bytes,
1452 // nothing with pointers to anything else or relocations. If any relocation
1453 // show up, reject them here.
1454 let instance = ty::Instance::mono(tcx, id);
1455 let cid = GlobalId {
1459 let param_env = ty::ParamEnv::reveal_all();
1460 if let Ok(static_) = tcx.const_eval(param_env.and(cid)) {
1461 let alloc = if let ConstValue::ByRef(_, allocation) = static_.val {
1464 bug!("Matching on non-ByRef static")
1466 if alloc.relocations.len() != 0 {
1467 let msg = "statics with a custom `#[link_section]` must be a \
1468 simple list of bytes on the wasm target with no \
1469 extra levels of indirection such as references";
1470 tcx.sess.span_err(span, msg);
1475 fn check_on_unimplemented<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1476 trait_def_id: DefId,
1478 let item_def_id = tcx.hir().local_def_id_from_hir_id(item.hir_id);
1479 // an error would be reported if this fails.
1480 let _ = traits::OnUnimplementedDirective::of_item(tcx, trait_def_id, item_def_id);
1483 fn report_forbidden_specialization<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1484 impl_item: &hir::ImplItem,
1487 let mut err = struct_span_err!(
1488 tcx.sess, impl_item.span, E0520,
1489 "`{}` specializes an item from a parent `impl`, but \
1490 that item is not marked `default`",
1492 err.span_label(impl_item.span, format!("cannot specialize default item `{}`",
1495 match tcx.span_of_impl(parent_impl) {
1497 err.span_label(span, "parent `impl` is here");
1498 err.note(&format!("to specialize, `{}` in the parent `impl` must be marked `default`",
1502 err.note(&format!("parent implementation is in crate `{}`", cname));
1509 fn check_specialization_validity<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1510 trait_def: &ty::TraitDef,
1511 trait_item: &ty::AssocItem,
1513 impl_item: &hir::ImplItem)
1515 let ancestors = trait_def.ancestors(tcx, impl_id);
1517 let kind = match impl_item.node {
1518 hir::ImplItemKind::Const(..) => ty::AssocKind::Const,
1519 hir::ImplItemKind::Method(..) => ty::AssocKind::Method,
1520 hir::ImplItemKind::Existential(..) => ty::AssocKind::Existential,
1521 hir::ImplItemKind::Type(_) => ty::AssocKind::Type
1524 let parent = ancestors.defs(tcx, trait_item.ident, kind, trait_def.def_id).nth(1)
1525 .map(|node_item| node_item.map(|parent| parent.defaultness));
1527 if let Some(parent) = parent {
1528 if tcx.impl_item_is_final(&parent) {
1529 report_forbidden_specialization(tcx, impl_item, parent.node.def_id());
1535 fn check_impl_items_against_trait<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1538 impl_trait_ref: ty::TraitRef<'tcx>,
1539 impl_item_refs: &[hir::ImplItemRef]) {
1540 let impl_span = tcx.sess.source_map().def_span(impl_span);
1542 // If the trait reference itself is erroneous (so the compilation is going
1543 // to fail), skip checking the items here -- the `impl_item` table in `tcx`
1544 // isn't populated for such impls.
1545 if impl_trait_ref.references_error() { return; }
1547 // Locate trait definition and items
1548 let trait_def = tcx.trait_def(impl_trait_ref.def_id);
1549 let mut overridden_associated_type = None;
1551 let impl_items = || impl_item_refs.iter().map(|iiref| tcx.hir().impl_item(iiref.id));
1553 // Check existing impl methods to see if they are both present in trait
1554 // and compatible with trait signature
1555 for impl_item in impl_items() {
1556 let ty_impl_item = tcx.associated_item(
1557 tcx.hir().local_def_id_from_hir_id(impl_item.hir_id));
1558 let ty_trait_item = tcx.associated_items(impl_trait_ref.def_id)
1559 .find(|ac| Namespace::from(&impl_item.node) == Namespace::from(ac.kind) &&
1560 tcx.hygienic_eq(ty_impl_item.ident, ac.ident, impl_trait_ref.def_id))
1562 // Not compatible, but needed for the error message
1563 tcx.associated_items(impl_trait_ref.def_id)
1564 .find(|ac| tcx.hygienic_eq(ty_impl_item.ident, ac.ident, impl_trait_ref.def_id))
1567 // Check that impl definition matches trait definition
1568 if let Some(ty_trait_item) = ty_trait_item {
1569 match impl_item.node {
1570 hir::ImplItemKind::Const(..) => {
1571 // Find associated const definition.
1572 if ty_trait_item.kind == ty::AssocKind::Const {
1573 compare_const_impl(tcx,
1579 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0323,
1580 "item `{}` is an associated const, \
1581 which doesn't match its trait `{}`",
1584 err.span_label(impl_item.span, "does not match trait");
1585 // We can only get the spans from local trait definition
1586 // Same for E0324 and E0325
1587 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
1588 err.span_label(trait_span, "item in trait");
1593 hir::ImplItemKind::Method(..) => {
1594 let trait_span = tcx.hir().span_if_local(ty_trait_item.def_id);
1595 if ty_trait_item.kind == ty::AssocKind::Method {
1596 compare_impl_method(tcx,
1603 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0324,
1604 "item `{}` is an associated method, \
1605 which doesn't match its trait `{}`",
1608 err.span_label(impl_item.span, "does not match trait");
1609 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
1610 err.span_label(trait_span, "item in trait");
1615 hir::ImplItemKind::Existential(..) |
1616 hir::ImplItemKind::Type(_) => {
1617 if ty_trait_item.kind == ty::AssocKind::Type {
1618 if ty_trait_item.defaultness.has_value() {
1619 overridden_associated_type = Some(impl_item);
1622 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0325,
1623 "item `{}` is an associated type, \
1624 which doesn't match its trait `{}`",
1627 err.span_label(impl_item.span, "does not match trait");
1628 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
1629 err.span_label(trait_span, "item in trait");
1636 check_specialization_validity(tcx, trait_def, &ty_trait_item, impl_id, impl_item);
1640 // Check for missing items from trait
1641 let mut missing_items = Vec::new();
1642 let mut invalidated_items = Vec::new();
1643 let associated_type_overridden = overridden_associated_type.is_some();
1644 for trait_item in tcx.associated_items(impl_trait_ref.def_id) {
1645 let is_implemented = trait_def.ancestors(tcx, impl_id)
1646 .defs(tcx, trait_item.ident, trait_item.kind, impl_trait_ref.def_id)
1648 .map(|node_item| !node_item.node.is_from_trait())
1651 if !is_implemented && !tcx.impl_is_default(impl_id) {
1652 if !trait_item.defaultness.has_value() {
1653 missing_items.push(trait_item);
1654 } else if associated_type_overridden {
1655 invalidated_items.push(trait_item.ident);
1660 if !missing_items.is_empty() {
1661 let mut err = struct_span_err!(tcx.sess, impl_span, E0046,
1662 "not all trait items implemented, missing: `{}`",
1663 missing_items.iter()
1664 .map(|trait_item| trait_item.ident.to_string())
1665 .collect::<Vec<_>>().join("`, `"));
1666 err.span_label(impl_span, format!("missing `{}` in implementation",
1667 missing_items.iter()
1668 .map(|trait_item| trait_item.ident.to_string())
1669 .collect::<Vec<_>>().join("`, `")));
1670 for trait_item in missing_items {
1671 if let Some(span) = tcx.hir().span_if_local(trait_item.def_id) {
1672 err.span_label(span, format!("`{}` from trait", trait_item.ident));
1674 err.note_trait_signature(trait_item.ident.to_string(),
1675 trait_item.signature(tcx));
1681 if !invalidated_items.is_empty() {
1682 let invalidator = overridden_associated_type.unwrap();
1683 span_err!(tcx.sess, invalidator.span, E0399,
1684 "the following trait items need to be reimplemented \
1685 as `{}` was overridden: `{}`",
1687 invalidated_items.iter()
1688 .map(|name| name.to_string())
1689 .collect::<Vec<_>>().join("`, `"))
1693 /// Checks whether a type can be represented in memory. In particular, it
1694 /// identifies types that contain themselves without indirection through a
1695 /// pointer, which would mean their size is unbounded.
1696 fn check_representable<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1700 let rty = tcx.type_of(item_def_id);
1702 // Check that it is possible to represent this type. This call identifies
1703 // (1) types that contain themselves and (2) types that contain a different
1704 // recursive type. It is only necessary to throw an error on those that
1705 // contain themselves. For case 2, there must be an inner type that will be
1706 // caught by case 1.
1707 match rty.is_representable(tcx, sp) {
1708 Representability::SelfRecursive(spans) => {
1709 let mut err = tcx.recursive_type_with_infinite_size_error(item_def_id);
1711 err.span_label(span, "recursive without indirection");
1716 Representability::Representable | Representability::ContainsRecursive => (),
1721 pub fn check_simd<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, sp: Span, def_id: DefId) {
1722 let t = tcx.type_of(def_id);
1723 if let ty::Adt(def, substs) = t.sty {
1724 if def.is_struct() {
1725 let fields = &def.non_enum_variant().fields;
1726 if fields.is_empty() {
1727 span_err!(tcx.sess, sp, E0075, "SIMD vector cannot be empty");
1730 let e = fields[0].ty(tcx, substs);
1731 if !fields.iter().all(|f| f.ty(tcx, substs) == e) {
1732 struct_span_err!(tcx.sess, sp, E0076, "SIMD vector should be homogeneous")
1733 .span_label(sp, "SIMD elements must have the same type")
1738 ty::Param(_) => { /* struct<T>(T, T, T, T) is ok */ }
1739 _ if e.is_machine() => { /* struct(u8, u8, u8, u8) is ok */ }
1741 span_err!(tcx.sess, sp, E0077,
1742 "SIMD vector element type should be machine type");
1750 fn check_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, sp: Span, def_id: DefId) {
1751 let repr = tcx.adt_def(def_id).repr;
1753 for attr in tcx.get_attrs(def_id).iter() {
1754 for r in attr::find_repr_attrs(&tcx.sess.parse_sess, attr) {
1755 if let attr::ReprPacked(pack) = r {
1756 if pack != repr.pack {
1757 struct_span_err!(tcx.sess, sp, E0634,
1758 "type has conflicting packed representation hints").emit();
1764 struct_span_err!(tcx.sess, sp, E0587,
1765 "type has conflicting packed and align representation hints").emit();
1767 else if check_packed_inner(tcx, def_id, &mut Vec::new()) {
1768 struct_span_err!(tcx.sess, sp, E0588,
1769 "packed type cannot transitively contain a `[repr(align)]` type").emit();
1774 fn check_packed_inner<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1776 stack: &mut Vec<DefId>) -> bool {
1777 let t = tcx.type_of(def_id);
1778 if stack.contains(&def_id) {
1779 debug!("check_packed_inner: {:?} is recursive", t);
1782 if let ty::Adt(def, substs) = t.sty {
1783 if def.is_struct() || def.is_union() {
1784 if tcx.adt_def(def.did).repr.align > 0 {
1787 // push struct def_id before checking fields
1789 for field in &def.non_enum_variant().fields {
1790 let f = field.ty(tcx, substs);
1791 if let ty::Adt(def, _) = f.sty {
1792 if check_packed_inner(tcx, def.did, stack) {
1797 // only need to pop if not early out
1804 fn check_transparent<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, sp: Span, def_id: DefId) {
1805 let adt = tcx.adt_def(def_id);
1806 if !adt.repr.transparent() {
1811 if !tcx.features().transparent_enums {
1812 emit_feature_err(&tcx.sess.parse_sess,
1813 sym::transparent_enums,
1815 GateIssue::Language,
1816 "transparent enums are unstable");
1818 if adt.variants.len() != 1 {
1819 let variant_spans: Vec<_> = adt.variants.iter().map(|variant| {
1820 tcx.hir().span_if_local(variant.def_id).unwrap()
1822 let mut err = struct_span_err!(tcx.sess, sp, E0731,
1823 "transparent enum needs exactly one variant, but has {}",
1824 adt.variants.len());
1825 if !variant_spans.is_empty() {
1826 err.span_note(variant_spans, &format!("the following variants exist on `{}`",
1827 tcx.def_path_str(def_id)));
1830 if adt.variants.is_empty() {
1831 // Don't bother checking the fields. No variants (and thus no fields) exist.
1837 if adt.is_union() && !tcx.features().transparent_unions {
1838 emit_feature_err(&tcx.sess.parse_sess,
1839 sym::transparent_unions,
1841 GateIssue::Language,
1842 "transparent unions are unstable");
1845 // For each field, figure out if it's known to be a ZST and align(1)
1846 let field_infos = adt.all_fields().map(|field| {
1847 let ty = field.ty(tcx, InternalSubsts::identity_for_item(tcx, field.did));
1848 let param_env = tcx.param_env(field.did);
1849 let layout = tcx.layout_of(param_env.and(ty));
1850 // We are currently checking the type this field came from, so it must be local
1851 let span = tcx.hir().span_if_local(field.did).unwrap();
1852 let zst = layout.map(|layout| layout.is_zst()).unwrap_or(false);
1853 let align1 = layout.map(|layout| layout.align.abi.bytes() == 1).unwrap_or(false);
1857 let non_zst_fields = field_infos.clone().filter(|(_span, zst, _align1)| !*zst);
1858 let non_zst_count = non_zst_fields.clone().count();
1859 if non_zst_count != 1 {
1860 let field_spans: Vec<_> = non_zst_fields.map(|(span, _zst, _align1)| span).collect();
1862 let mut err = struct_span_err!(tcx.sess, sp, E0690,
1863 "{}transparent {} needs exactly one non-zero-sized field, but has {}",
1864 if adt.is_enum() { "the variant of a " } else { "" },
1867 if !field_spans.is_empty() {
1868 err.span_note(field_spans,
1869 &format!("the following non-zero-sized fields exist on `{}`:",
1870 tcx.def_path_str(def_id)));
1874 for (span, zst, align1) in field_infos {
1876 span_err!(tcx.sess, span, E0691,
1877 "zero-sized field in transparent {} has alignment larger than 1",
1883 #[allow(trivial_numeric_casts)]
1884 pub fn check_enum<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1886 vs: &'tcx [hir::Variant],
1888 let def_id = tcx.hir().local_def_id_from_hir_id(id);
1889 let def = tcx.adt_def(def_id);
1890 def.destructor(tcx); // force the destructor to be evaluated
1893 let attributes = tcx.get_attrs(def_id);
1894 if let Some(attr) = attr::find_by_name(&attributes, sym::repr) {
1896 tcx.sess, attr.span, E0084,
1897 "unsupported representation for zero-variant enum")
1898 .span_label(sp, "zero-variant enum")
1903 let repr_type_ty = def.repr.discr_type().to_ty(tcx);
1904 if repr_type_ty == tcx.types.i128 || repr_type_ty == tcx.types.u128 {
1905 if !tcx.features().repr128 {
1906 emit_feature_err(&tcx.sess.parse_sess,
1909 GateIssue::Language,
1910 "repr with 128-bit type is unstable");
1915 if let Some(ref e) = v.node.disr_expr {
1916 tcx.typeck_tables_of(tcx.hir().local_def_id_from_hir_id(e.hir_id));
1920 let mut disr_vals: Vec<Discr<'tcx>> = Vec::with_capacity(vs.len());
1921 for ((_, discr), v) in def.discriminants(tcx).zip(vs) {
1922 // Check for duplicate discriminant values
1923 if let Some(i) = disr_vals.iter().position(|&x| x.val == discr.val) {
1924 let variant_did = def.variants[VariantIdx::new(i)].def_id;
1925 let variant_i_hir_id = tcx.hir().as_local_hir_id(variant_did).unwrap();
1926 let variant_i = tcx.hir().expect_variant(variant_i_hir_id);
1927 let i_span = match variant_i.node.disr_expr {
1928 Some(ref expr) => tcx.hir().span_by_hir_id(expr.hir_id),
1929 None => tcx.hir().span_by_hir_id(variant_i_hir_id)
1931 let span = match v.node.disr_expr {
1932 Some(ref expr) => tcx.hir().span_by_hir_id(expr.hir_id),
1935 struct_span_err!(tcx.sess, span, E0081,
1936 "discriminant value `{}` already exists", disr_vals[i])
1937 .span_label(i_span, format!("first use of `{}`", disr_vals[i]))
1938 .span_label(span , format!("enum already has `{}`", disr_vals[i]))
1941 disr_vals.push(discr);
1944 check_representable(tcx, sp, def_id);
1945 check_transparent(tcx, sp, def_id);
1948 fn report_unexpected_variant_res<'a, 'gcx, 'tcx>(tcx: TyCtxt<'a, 'gcx, 'tcx>,
1952 span_err!(tcx.sess, span, E0533,
1953 "expected unit struct/variant or constant, found {} `{}`",
1955 hir::print::to_string(tcx.hir(), |s| s.print_qpath(qpath, false)));
1958 impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> {
1959 fn tcx<'b>(&'b self) -> TyCtxt<'b, 'gcx, 'tcx> { self.tcx }
1961 fn get_type_parameter_bounds(&self, _: Span, def_id: DefId)
1962 -> &'tcx ty::GenericPredicates<'tcx>
1965 let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
1966 let item_id = tcx.hir().ty_param_owner(hir_id);
1967 let item_def_id = tcx.hir().local_def_id_from_hir_id(item_id);
1968 let generics = tcx.generics_of(item_def_id);
1969 let index = generics.param_def_id_to_index[&def_id];
1970 tcx.arena.alloc(ty::GenericPredicates {
1972 predicates: self.param_env.caller_bounds.iter().filter_map(|&predicate| {
1974 ty::Predicate::Trait(ref data)
1975 if data.skip_binder().self_ty().is_param(index) => {
1976 // HACK(eddyb) should get the original `Span`.
1977 let span = tcx.def_span(def_id);
1978 Some((predicate, span))
1988 def: Option<&ty::GenericParamDef>,
1990 ) -> Option<ty::Region<'tcx>> {
1992 Some(def) => infer::EarlyBoundRegion(span, def.name),
1993 None => infer::MiscVariable(span)
1995 Some(self.next_region_var(v))
1998 fn ty_infer(&self, param: Option<&ty::GenericParamDef>, span: Span) -> Ty<'tcx> {
1999 if let Some(param) = param {
2000 if let UnpackedKind::Type(ty) = self.var_for_def(span, param).unpack() {
2005 self.next_ty_var(TypeVariableOrigin {
2006 kind: TypeVariableOriginKind::TypeInference,
2015 param: Option<&ty::GenericParamDef>,
2017 ) -> &'tcx Const<'tcx> {
2018 if let Some(param) = param {
2019 if let UnpackedKind::Const(ct) = self.var_for_def(span, param).unpack() {
2024 self.next_const_var(ty, ConstVariableOrigin {
2025 kind: ConstVariableOriginKind::ConstInference,
2031 fn projected_ty_from_poly_trait_ref(&self,
2034 poly_trait_ref: ty::PolyTraitRef<'tcx>)
2037 let (trait_ref, _) = self.replace_bound_vars_with_fresh_vars(
2039 infer::LateBoundRegionConversionTime::AssocTypeProjection(item_def_id),
2043 self.tcx().mk_projection(item_def_id, trait_ref.substs)
2046 fn normalize_ty(&self, span: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
2047 if ty.has_escaping_bound_vars() {
2048 ty // FIXME: normalization and escaping regions
2050 self.normalize_associated_types_in(span, &ty)
2054 fn set_tainted_by_errors(&self) {
2055 self.infcx.set_tainted_by_errors()
2058 fn record_ty(&self, hir_id: hir::HirId, ty: Ty<'tcx>, _span: Span) {
2059 self.write_ty(hir_id, ty)
2063 /// Controls whether the arguments are tupled. This is used for the call
2066 /// Tupling means that all call-side arguments are packed into a tuple and
2067 /// passed as a single parameter. For example, if tupling is enabled, this
2070 /// fn f(x: (isize, isize))
2072 /// Can be called as:
2079 #[derive(Clone, Eq, PartialEq)]
2080 enum TupleArgumentsFlag {
2085 impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
2086 pub fn new(inh: &'a Inherited<'a, 'gcx, 'tcx>,
2087 param_env: ty::ParamEnv<'tcx>,
2088 body_id: hir::HirId)
2089 -> FnCtxt<'a, 'gcx, 'tcx> {
2093 err_count_on_creation: inh.tcx.sess.err_count(),
2095 ret_coercion_span: RefCell::new(None),
2097 ps: RefCell::new(UnsafetyState::function(hir::Unsafety::Normal,
2098 hir::CRATE_HIR_ID)),
2099 diverges: Cell::new(Diverges::Maybe),
2100 has_errors: Cell::new(false),
2101 enclosing_breakables: RefCell::new(EnclosingBreakables {
2103 by_id: Default::default(),
2109 pub fn sess(&self) -> &Session {
2113 pub fn err_count_since_creation(&self) -> usize {
2114 self.tcx.sess.err_count() - self.err_count_on_creation
2117 /// Produces warning on the given node, if the current point in the
2118 /// function is unreachable, and there hasn't been another warning.
2119 fn warn_if_unreachable(&self, id: hir::HirId, span: Span, kind: &str) {
2120 if self.diverges.get() == Diverges::Always &&
2121 // If span arose from a desugaring of `if` then it is the condition itself,
2122 // which diverges, that we are about to lint on. This gives suboptimal diagnostics
2123 // and so we stop here and allow the block of the `if`-expression to be linted instead.
2124 !span.is_compiler_desugaring(CompilerDesugaringKind::IfTemporary) {
2125 self.diverges.set(Diverges::WarnedAlways);
2127 debug!("warn_if_unreachable: id={:?} span={:?} kind={}", id, span, kind);
2129 let msg = format!("unreachable {}", kind);
2130 self.tcx().lint_hir(lint::builtin::UNREACHABLE_CODE, id, span, &msg);
2136 code: ObligationCauseCode<'tcx>)
2137 -> ObligationCause<'tcx> {
2138 ObligationCause::new(span, self.body_id, code)
2141 pub fn misc(&self, span: Span) -> ObligationCause<'tcx> {
2142 self.cause(span, ObligationCauseCode::MiscObligation)
2145 /// Resolves type variables in `ty` if possible. Unlike the infcx
2146 /// version (resolve_vars_if_possible), this version will
2147 /// also select obligations if it seems useful, in an effort
2148 /// to get more type information.
2149 fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
2150 debug!("resolve_type_vars_with_obligations(ty={:?})", ty);
2152 // No Infer()? Nothing needs doing.
2153 if !ty.has_infer_types() {
2154 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
2158 // If `ty` is a type variable, see whether we already know what it is.
2159 ty = self.resolve_vars_if_possible(&ty);
2160 if !ty.has_infer_types() {
2161 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
2165 // If not, try resolving pending obligations as much as
2166 // possible. This can help substantially when there are
2167 // indirect dependencies that don't seem worth tracking
2169 self.select_obligations_where_possible(false);
2170 ty = self.resolve_vars_if_possible(&ty);
2172 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
2176 fn record_deferred_call_resolution(&self,
2177 closure_def_id: DefId,
2178 r: DeferredCallResolution<'gcx, 'tcx>) {
2179 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
2180 deferred_call_resolutions.entry(closure_def_id).or_default().push(r);
2183 fn remove_deferred_call_resolutions(&self,
2184 closure_def_id: DefId)
2185 -> Vec<DeferredCallResolution<'gcx, 'tcx>>
2187 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
2188 deferred_call_resolutions.remove(&closure_def_id).unwrap_or(vec![])
2191 pub fn tag(&self) -> String {
2192 let self_ptr: *const FnCtxt<'_, '_, '_> = self;
2193 format!("{:?}", self_ptr)
2196 pub fn local_ty(&self, span: Span, nid: hir::HirId) -> LocalTy<'tcx> {
2197 self.locals.borrow().get(&nid).cloned().unwrap_or_else(||
2198 span_bug!(span, "no type for local variable {}",
2199 self.tcx.hir().hir_to_string(nid))
2204 pub fn write_ty(&self, id: hir::HirId, ty: Ty<'tcx>) {
2205 debug!("write_ty({:?}, {:?}) in fcx {}",
2206 id, self.resolve_vars_if_possible(&ty), self.tag());
2207 self.tables.borrow_mut().node_types_mut().insert(id, ty);
2209 if ty.references_error() {
2210 self.has_errors.set(true);
2211 self.set_tainted_by_errors();
2215 pub fn write_field_index(&self, hir_id: hir::HirId, index: usize) {
2216 self.tables.borrow_mut().field_indices_mut().insert(hir_id, index);
2219 pub fn write_method_call(&self,
2221 method: MethodCallee<'tcx>) {
2222 debug!("write_method_call(hir_id={:?}, method={:?})", hir_id, method);
2225 .type_dependent_defs_mut()
2226 .insert(hir_id, Ok((DefKind::Method, method.def_id)));
2228 self.write_substs(hir_id, method.substs);
2230 // When the method is confirmed, the `method.substs` includes
2231 // parameters from not just the method, but also the impl of
2232 // the method -- in particular, the `Self` type will be fully
2233 // resolved. However, those are not something that the "user
2234 // specified" -- i.e., those types come from the inferred type
2235 // of the receiver, not something the user wrote. So when we
2236 // create the user-substs, we want to replace those earlier
2237 // types with just the types that the user actually wrote --
2238 // that is, those that appear on the *method itself*.
2240 // As an example, if the user wrote something like
2241 // `foo.bar::<u32>(...)` -- the `Self` type here will be the
2242 // type of `foo` (possibly adjusted), but we don't want to
2243 // include that. We want just the `[_, u32]` part.
2244 if !method.substs.is_noop() {
2245 let method_generics = self.tcx.generics_of(method.def_id);
2246 if !method_generics.params.is_empty() {
2247 let user_type_annotation = self.infcx.probe(|_| {
2248 let user_substs = UserSubsts {
2249 substs: InternalSubsts::for_item(self.tcx, method.def_id, |param, _| {
2250 let i = param.index as usize;
2251 if i < method_generics.parent_count {
2252 self.infcx.var_for_def(DUMMY_SP, param)
2257 user_self_ty: None, // not relevant here
2260 self.infcx.canonicalize_user_type_annotation(&UserType::TypeOf(
2266 debug!("write_method_call: user_type_annotation={:?}", user_type_annotation);
2267 self.write_user_type_annotation(hir_id, user_type_annotation);
2272 pub fn write_substs(&self, node_id: hir::HirId, substs: SubstsRef<'tcx>) {
2273 if !substs.is_noop() {
2274 debug!("write_substs({:?}, {:?}) in fcx {}",
2279 self.tables.borrow_mut().node_substs_mut().insert(node_id, substs);
2283 /// Given the substs that we just converted from the HIR, try to
2284 /// canonicalize them and store them as user-given substitutions
2285 /// (i.e., substitutions that must be respected by the NLL check).
2287 /// This should be invoked **before any unifications have
2288 /// occurred**, so that annotations like `Vec<_>` are preserved
2290 pub fn write_user_type_annotation_from_substs(
2294 substs: SubstsRef<'tcx>,
2295 user_self_ty: Option<UserSelfTy<'tcx>>,
2298 "write_user_type_annotation_from_substs: hir_id={:?} def_id={:?} substs={:?} \
2299 user_self_ty={:?} in fcx {}",
2300 hir_id, def_id, substs, user_self_ty, self.tag(),
2303 if Self::can_contain_user_lifetime_bounds((substs, user_self_ty)) {
2304 let canonicalized = self.infcx.canonicalize_user_type_annotation(
2305 &UserType::TypeOf(def_id, UserSubsts {
2310 debug!("write_user_type_annotation_from_substs: canonicalized={:?}", canonicalized);
2311 self.write_user_type_annotation(hir_id, canonicalized);
2315 pub fn write_user_type_annotation(
2318 canonical_user_type_annotation: CanonicalUserType<'tcx>,
2321 "write_user_type_annotation: hir_id={:?} canonical_user_type_annotation={:?} tag={}",
2322 hir_id, canonical_user_type_annotation, self.tag(),
2325 if !canonical_user_type_annotation.is_identity() {
2326 self.tables.borrow_mut().user_provided_types_mut().insert(
2327 hir_id, canonical_user_type_annotation
2330 debug!("write_user_type_annotation: skipping identity substs");
2334 pub fn apply_adjustments(&self, expr: &hir::Expr, adj: Vec<Adjustment<'tcx>>) {
2335 debug!("apply_adjustments(expr={:?}, adj={:?})", expr, adj);
2341 match self.tables.borrow_mut().adjustments_mut().entry(expr.hir_id) {
2342 Entry::Vacant(entry) => { entry.insert(adj); },
2343 Entry::Occupied(mut entry) => {
2344 debug!(" - composing on top of {:?}", entry.get());
2345 match (&entry.get()[..], &adj[..]) {
2346 // Applying any adjustment on top of a NeverToAny
2347 // is a valid NeverToAny adjustment, because it can't
2349 (&[Adjustment { kind: Adjust::NeverToAny, .. }], _) => return,
2351 Adjustment { kind: Adjust::Deref(_), .. },
2352 Adjustment { kind: Adjust::Borrow(AutoBorrow::Ref(..)), .. },
2354 Adjustment { kind: Adjust::Deref(_), .. },
2355 .. // Any following adjustments are allowed.
2357 // A reborrow has no effect before a dereference.
2359 // FIXME: currently we never try to compose autoderefs
2360 // and ReifyFnPointer/UnsafeFnPointer, but we could.
2362 bug!("while adjusting {:?}, can't compose {:?} and {:?}",
2363 expr, entry.get(), adj)
2365 *entry.get_mut() = adj;
2370 /// Basically whenever we are converting from a type scheme into
2371 /// the fn body space, we always want to normalize associated
2372 /// types as well. This function combines the two.
2373 fn instantiate_type_scheme<T>(&self,
2375 substs: SubstsRef<'tcx>,
2378 where T : TypeFoldable<'tcx>
2380 let value = value.subst(self.tcx, substs);
2381 let result = self.normalize_associated_types_in(span, &value);
2382 debug!("instantiate_type_scheme(value={:?}, substs={:?}) = {:?}",
2389 /// As `instantiate_type_scheme`, but for the bounds found in a
2390 /// generic type scheme.
2391 fn instantiate_bounds(&self, span: Span, def_id: DefId, substs: SubstsRef<'tcx>)
2392 -> ty::InstantiatedPredicates<'tcx> {
2393 let bounds = self.tcx.predicates_of(def_id);
2394 let result = bounds.instantiate(self.tcx, substs);
2395 let result = self.normalize_associated_types_in(span, &result);
2396 debug!("instantiate_bounds(bounds={:?}, substs={:?}) = {:?}",
2403 /// Replaces the opaque types from the given value with type variables,
2404 /// and records the `OpaqueTypeMap` for later use during writeback. See
2405 /// `InferCtxt::instantiate_opaque_types` for more details.
2406 fn instantiate_opaque_types_from_value<T: TypeFoldable<'tcx>>(
2408 parent_id: hir::HirId,
2411 let parent_def_id = self.tcx.hir().local_def_id_from_hir_id(parent_id);
2412 debug!("instantiate_opaque_types_from_value(parent_def_id={:?}, value={:?})",
2416 let (value, opaque_type_map) = self.register_infer_ok_obligations(
2417 self.instantiate_opaque_types(
2425 let mut opaque_types = self.opaque_types.borrow_mut();
2426 for (ty, decl) in opaque_type_map {
2427 let old_value = opaque_types.insert(ty, decl);
2428 assert!(old_value.is_none(), "instantiated twice: {:?}/{:?}", ty, decl);
2434 fn normalize_associated_types_in<T>(&self, span: Span, value: &T) -> T
2435 where T : TypeFoldable<'tcx>
2437 self.inh.normalize_associated_types_in(span, self.body_id, self.param_env, value)
2440 fn normalize_associated_types_in_as_infer_ok<T>(&self, span: Span, value: &T)
2442 where T : TypeFoldable<'tcx>
2444 self.inh.partially_normalize_associated_types_in(span,
2450 pub fn require_type_meets(&self,
2453 code: traits::ObligationCauseCode<'tcx>,
2456 self.register_bound(
2459 traits::ObligationCause::new(span, self.body_id, code));
2462 pub fn require_type_is_sized(&self,
2465 code: traits::ObligationCauseCode<'tcx>)
2467 let lang_item = self.tcx.require_lang_item(lang_items::SizedTraitLangItem);
2468 self.require_type_meets(ty, span, code, lang_item);
2471 pub fn require_type_is_sized_deferred(&self,
2474 code: traits::ObligationCauseCode<'tcx>)
2476 self.deferred_sized_obligations.borrow_mut().push((ty, span, code));
2479 pub fn register_bound(&self,
2482 cause: traits::ObligationCause<'tcx>)
2484 self.fulfillment_cx.borrow_mut()
2485 .register_bound(self, self.param_env, ty, def_id, cause);
2488 pub fn to_ty(&self, ast_t: &hir::Ty) -> Ty<'tcx> {
2489 let t = AstConv::ast_ty_to_ty(self, ast_t);
2490 self.register_wf_obligation(t, ast_t.span, traits::MiscObligation);
2494 pub fn to_ty_saving_user_provided_ty(&self, ast_ty: &hir::Ty) -> Ty<'tcx> {
2495 let ty = self.to_ty(ast_ty);
2496 debug!("to_ty_saving_user_provided_ty: ty={:?}", ty);
2498 if Self::can_contain_user_lifetime_bounds(ty) {
2499 let c_ty = self.infcx.canonicalize_response(&UserType::Ty(ty));
2500 debug!("to_ty_saving_user_provided_ty: c_ty={:?}", c_ty);
2501 self.tables.borrow_mut().user_provided_types_mut().insert(ast_ty.hir_id, c_ty);
2507 pub fn to_const(&self, ast_c: &hir::AnonConst, ty: Ty<'tcx>) -> &'tcx ty::Const<'tcx> {
2508 AstConv::ast_const_to_const(self, ast_c, ty)
2511 // If the type given by the user has free regions, save it for later, since
2512 // NLL would like to enforce those. Also pass in types that involve
2513 // projections, since those can resolve to `'static` bounds (modulo #54940,
2514 // which hopefully will be fixed by the time you see this comment, dear
2515 // reader, although I have my doubts). Also pass in types with inference
2516 // types, because they may be repeated. Other sorts of things are already
2517 // sufficiently enforced with erased regions. =)
2518 fn can_contain_user_lifetime_bounds<T>(t: T) -> bool
2520 T: TypeFoldable<'tcx>
2522 t.has_free_regions() || t.has_projections() || t.has_infer_types()
2525 pub fn node_ty(&self, id: hir::HirId) -> Ty<'tcx> {
2526 match self.tables.borrow().node_types().get(id) {
2528 None if self.is_tainted_by_errors() => self.tcx.types.err,
2530 let node_id = self.tcx.hir().hir_to_node_id(id);
2531 bug!("no type for node {}: {} in fcx {}",
2532 node_id, self.tcx.hir().node_to_string(node_id),
2538 /// Registers an obligation for checking later, during regionck, that the type `ty` must
2539 /// outlive the region `r`.
2540 pub fn register_wf_obligation(&self,
2543 code: traits::ObligationCauseCode<'tcx>)
2545 // WF obligations never themselves fail, so no real need to give a detailed cause:
2546 let cause = traits::ObligationCause::new(span, self.body_id, code);
2547 self.register_predicate(traits::Obligation::new(cause,
2549 ty::Predicate::WellFormed(ty)));
2552 /// Registers obligations that all types appearing in `substs` are well-formed.
2553 pub fn add_wf_bounds(&self, substs: SubstsRef<'tcx>, expr: &hir::Expr) {
2554 for ty in substs.types() {
2555 self.register_wf_obligation(ty, expr.span, traits::MiscObligation);
2559 /// Given a fully substituted set of bounds (`generic_bounds`), and the values with which each
2560 /// type/region parameter was instantiated (`substs`), creates and registers suitable
2561 /// trait/region obligations.
2563 /// For example, if there is a function:
2566 /// fn foo<'a,T:'a>(...)
2569 /// and a reference:
2575 /// Then we will create a fresh region variable `'$0` and a fresh type variable `$1` for `'a`
2576 /// and `T`. This routine will add a region obligation `$1:'$0` and register it locally.
2577 pub fn add_obligations_for_parameters(&self,
2578 cause: traits::ObligationCause<'tcx>,
2579 predicates: &ty::InstantiatedPredicates<'tcx>)
2581 assert!(!predicates.has_escaping_bound_vars());
2583 debug!("add_obligations_for_parameters(predicates={:?})",
2586 for obligation in traits::predicates_for_generics(cause, self.param_env, predicates) {
2587 self.register_predicate(obligation);
2591 // FIXME(arielb1): use this instead of field.ty everywhere
2592 // Only for fields! Returns <none> for methods>
2593 // Indifferent to privacy flags
2594 pub fn field_ty(&self,
2596 field: &'tcx ty::FieldDef,
2597 substs: SubstsRef<'tcx>)
2600 self.normalize_associated_types_in(span, &field.ty(self.tcx, substs))
2603 fn check_casts(&self) {
2604 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
2605 for cast in deferred_cast_checks.drain(..) {
2610 fn resolve_generator_interiors(&self, def_id: DefId) {
2611 let mut generators = self.deferred_generator_interiors.borrow_mut();
2612 for (body_id, interior) in generators.drain(..) {
2613 self.select_obligations_where_possible(false);
2614 generator_interior::resolve_interior(self, def_id, body_id, interior);
2618 // Tries to apply a fallback to `ty` if it is an unsolved variable.
2619 // Non-numerics get replaced with ! or () (depending on whether
2620 // feature(never_type) is enabled, unconstrained ints with i32,
2621 // unconstrained floats with f64.
2622 // Fallback becomes very dubious if we have encountered type-checking errors.
2623 // In that case, fallback to Error.
2624 // The return value indicates whether fallback has occurred.
2625 fn fallback_if_possible(&self, ty: Ty<'tcx>) -> bool {
2626 use rustc::ty::error::UnconstrainedNumeric::Neither;
2627 use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedInt, UnconstrainedFloat};
2629 assert!(ty.is_ty_infer());
2630 let fallback = match self.type_is_unconstrained_numeric(ty) {
2631 _ if self.is_tainted_by_errors() => self.tcx().types.err,
2632 UnconstrainedInt => self.tcx.types.i32,
2633 UnconstrainedFloat => self.tcx.types.f64,
2634 Neither if self.type_var_diverges(ty) => self.tcx.mk_diverging_default(),
2635 Neither => return false,
2637 debug!("fallback_if_possible: defaulting `{:?}` to `{:?}`", ty, fallback);
2638 self.demand_eqtype(syntax_pos::DUMMY_SP, ty, fallback);
2642 fn select_all_obligations_or_error(&self) {
2643 debug!("select_all_obligations_or_error");
2644 if let Err(errors) = self.fulfillment_cx.borrow_mut().select_all_or_error(&self) {
2645 self.report_fulfillment_errors(&errors, self.inh.body_id, false);
2649 /// Select as many obligations as we can at present.
2650 fn select_obligations_where_possible(&self, fallback_has_occurred: bool) {
2651 if let Err(errors) = self.fulfillment_cx.borrow_mut().select_where_possible(self) {
2652 self.report_fulfillment_errors(&errors, self.inh.body_id, fallback_has_occurred);
2656 /// For the overloaded place expressions (`*x`, `x[3]`), the trait
2657 /// returns a type of `&T`, but the actual type we assign to the
2658 /// *expression* is `T`. So this function just peels off the return
2659 /// type by one layer to yield `T`.
2660 fn make_overloaded_place_return_type(&self,
2661 method: MethodCallee<'tcx>)
2662 -> ty::TypeAndMut<'tcx>
2664 // extract method return type, which will be &T;
2665 let ret_ty = method.sig.output();
2667 // method returns &T, but the type as visible to user is T, so deref
2668 ret_ty.builtin_deref(true).unwrap()
2671 fn lookup_indexing(&self,
2673 base_expr: &'gcx hir::Expr,
2677 -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)>
2679 // FIXME(#18741) -- this is almost but not quite the same as the
2680 // autoderef that normal method probing does. They could likely be
2683 let mut autoderef = self.autoderef(base_expr.span, base_ty);
2684 let mut result = None;
2685 while result.is_none() && autoderef.next().is_some() {
2686 result = self.try_index_step(expr, base_expr, &autoderef, needs, idx_ty);
2688 autoderef.finalize(self);
2692 /// To type-check `base_expr[index_expr]`, we progressively autoderef
2693 /// (and otherwise adjust) `base_expr`, looking for a type which either
2694 /// supports builtin indexing or overloaded indexing.
2695 /// This loop implements one step in that search; the autoderef loop
2696 /// is implemented by `lookup_indexing`.
2697 fn try_index_step(&self,
2699 base_expr: &hir::Expr,
2700 autoderef: &Autoderef<'a, 'gcx, 'tcx>,
2703 -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)>
2705 let adjusted_ty = autoderef.unambiguous_final_ty(self);
2706 debug!("try_index_step(expr={:?}, base_expr={:?}, adjusted_ty={:?}, \
2713 for &unsize in &[false, true] {
2714 let mut self_ty = adjusted_ty;
2716 // We only unsize arrays here.
2717 if let ty::Array(element_ty, _) = adjusted_ty.sty {
2718 self_ty = self.tcx.mk_slice(element_ty);
2724 // If some lookup succeeds, write callee into table and extract index/element
2725 // type from the method signature.
2726 // If some lookup succeeded, install method in table
2727 let input_ty = self.next_ty_var(TypeVariableOrigin {
2728 kind: TypeVariableOriginKind::AutoDeref,
2729 span: base_expr.span,
2731 let method = self.try_overloaded_place_op(
2732 expr.span, self_ty, &[input_ty], needs, PlaceOp::Index);
2734 let result = method.map(|ok| {
2735 debug!("try_index_step: success, using overloaded indexing");
2736 let method = self.register_infer_ok_obligations(ok);
2738 let mut adjustments = autoderef.adjust_steps(self, needs);
2739 if let ty::Ref(region, _, r_mutbl) = method.sig.inputs()[0].sty {
2740 let mutbl = match r_mutbl {
2741 hir::MutImmutable => AutoBorrowMutability::Immutable,
2742 hir::MutMutable => AutoBorrowMutability::Mutable {
2743 // Indexing can be desugared to a method call,
2744 // so maybe we could use two-phase here.
2745 // See the documentation of AllowTwoPhase for why that's
2746 // not the case today.
2747 allow_two_phase_borrow: AllowTwoPhase::No,
2750 adjustments.push(Adjustment {
2751 kind: Adjust::Borrow(AutoBorrow::Ref(region, mutbl)),
2752 target: self.tcx.mk_ref(region, ty::TypeAndMut {
2759 adjustments.push(Adjustment {
2760 kind: Adjust::Pointer(PointerCast::Unsize),
2761 target: method.sig.inputs()[0]
2764 self.apply_adjustments(base_expr, adjustments);
2766 self.write_method_call(expr.hir_id, method);
2767 (input_ty, self.make_overloaded_place_return_type(method).ty)
2769 if result.is_some() {
2777 fn resolve_place_op(&self, op: PlaceOp, is_mut: bool) -> (Option<DefId>, ast::Ident) {
2778 let (tr, name) = match (op, is_mut) {
2779 (PlaceOp::Deref, false) => (self.tcx.lang_items().deref_trait(), sym::deref),
2780 (PlaceOp::Deref, true) => (self.tcx.lang_items().deref_mut_trait(), sym::deref_mut),
2781 (PlaceOp::Index, false) => (self.tcx.lang_items().index_trait(), sym::index),
2782 (PlaceOp::Index, true) => (self.tcx.lang_items().index_mut_trait(), sym::index_mut),
2784 (tr, ast::Ident::with_empty_ctxt(name))
2787 fn try_overloaded_place_op(&self,
2790 arg_tys: &[Ty<'tcx>],
2793 -> Option<InferOk<'tcx, MethodCallee<'tcx>>>
2795 debug!("try_overloaded_place_op({:?},{:?},{:?},{:?})",
2801 // Try Mut first, if needed.
2802 let (mut_tr, mut_op) = self.resolve_place_op(op, true);
2803 let method = match (needs, mut_tr) {
2804 (Needs::MutPlace, Some(trait_did)) => {
2805 self.lookup_method_in_trait(span, mut_op, trait_did, base_ty, Some(arg_tys))
2810 // Otherwise, fall back to the immutable version.
2811 let (imm_tr, imm_op) = self.resolve_place_op(op, false);
2812 let method = match (method, imm_tr) {
2813 (None, Some(trait_did)) => {
2814 self.lookup_method_in_trait(span, imm_op, trait_did, base_ty, Some(arg_tys))
2816 (method, _) => method,
2822 fn check_method_argument_types(&self,
2825 method: Result<MethodCallee<'tcx>, ()>,
2826 args_no_rcvr: &'gcx [hir::Expr],
2827 tuple_arguments: TupleArgumentsFlag,
2828 expected: Expectation<'tcx>)
2830 let has_error = match method {
2832 method.substs.references_error() || method.sig.references_error()
2837 let err_inputs = self.err_args(args_no_rcvr.len());
2839 let err_inputs = match tuple_arguments {
2840 DontTupleArguments => err_inputs,
2841 TupleArguments => vec![self.tcx.intern_tup(&err_inputs[..])],
2844 self.check_argument_types(sp, expr_sp, &err_inputs[..], &[], args_no_rcvr,
2845 false, tuple_arguments, None);
2846 return self.tcx.types.err;
2849 let method = method.unwrap();
2850 // HACK(eddyb) ignore self in the definition (see above).
2851 let expected_arg_tys = self.expected_inputs_for_expected_output(
2854 method.sig.output(),
2855 &method.sig.inputs()[1..]
2857 self.check_argument_types(sp, expr_sp, &method.sig.inputs()[1..], &expected_arg_tys[..],
2858 args_no_rcvr, method.sig.c_variadic, tuple_arguments,
2859 self.tcx.hir().span_if_local(method.def_id));
2863 fn self_type_matches_expected_vid(
2865 trait_ref: ty::PolyTraitRef<'tcx>,
2866 expected_vid: ty::TyVid,
2868 let self_ty = self.shallow_resolve(trait_ref.self_ty());
2870 "self_type_matches_expected_vid(trait_ref={:?}, self_ty={:?}, expected_vid={:?})",
2871 trait_ref, self_ty, expected_vid
2874 ty::Infer(ty::TyVar(found_vid)) => {
2875 // FIXME: consider using `sub_root_var` here so we
2876 // can see through subtyping.
2877 let found_vid = self.root_var(found_vid);
2878 debug!("self_type_matches_expected_vid - found_vid={:?}", found_vid);
2879 expected_vid == found_vid
2885 fn obligations_for_self_ty<'b>(&'b self, self_ty: ty::TyVid)
2886 -> impl Iterator<Item=(ty::PolyTraitRef<'tcx>, traits::PredicateObligation<'tcx>)>
2887 + Captures<'gcx> + 'b
2889 // FIXME: consider using `sub_root_var` here so we
2890 // can see through subtyping.
2891 let ty_var_root = self.root_var(self_ty);
2892 debug!("obligations_for_self_ty: self_ty={:?} ty_var_root={:?} pending_obligations={:?}",
2893 self_ty, ty_var_root,
2894 self.fulfillment_cx.borrow().pending_obligations());
2898 .pending_obligations()
2900 .filter_map(move |obligation| match obligation.predicate {
2901 ty::Predicate::Projection(ref data) =>
2902 Some((data.to_poly_trait_ref(self.tcx), obligation)),
2903 ty::Predicate::Trait(ref data) =>
2904 Some((data.to_poly_trait_ref(), obligation)),
2905 ty::Predicate::Subtype(..) => None,
2906 ty::Predicate::RegionOutlives(..) => None,
2907 ty::Predicate::TypeOutlives(..) => None,
2908 ty::Predicate::WellFormed(..) => None,
2909 ty::Predicate::ObjectSafe(..) => None,
2910 ty::Predicate::ConstEvaluatable(..) => None,
2911 // N.B., this predicate is created by breaking down a
2912 // `ClosureType: FnFoo()` predicate, where
2913 // `ClosureType` represents some `Closure`. It can't
2914 // possibly be referring to the current closure,
2915 // because we haven't produced the `Closure` for
2916 // this closure yet; this is exactly why the other
2917 // code is looking for a self type of a unresolved
2918 // inference variable.
2919 ty::Predicate::ClosureKind(..) => None,
2920 }).filter(move |(tr, _)| self.self_type_matches_expected_vid(*tr, ty_var_root))
2923 fn type_var_is_sized(&self, self_ty: ty::TyVid) -> bool {
2924 self.obligations_for_self_ty(self_ty).any(|(tr, _)| {
2925 Some(tr.def_id()) == self.tcx.lang_items().sized_trait()
2929 /// Generic function that factors out common logic from function calls,
2930 /// method calls and overloaded operators.
2931 fn check_argument_types(&self,
2934 fn_inputs: &[Ty<'tcx>],
2935 expected_arg_tys: &[Ty<'tcx>],
2936 args: &'gcx [hir::Expr],
2938 tuple_arguments: TupleArgumentsFlag,
2939 def_span: Option<Span>) {
2942 // Grab the argument types, supplying fresh type variables
2943 // if the wrong number of arguments were supplied
2944 let supplied_arg_count = if tuple_arguments == DontTupleArguments {
2950 // All the input types from the fn signature must outlive the call
2951 // so as to validate implied bounds.
2952 for &fn_input_ty in fn_inputs {
2953 self.register_wf_obligation(fn_input_ty, sp, traits::MiscObligation);
2956 let expected_arg_count = fn_inputs.len();
2958 let param_count_error = |expected_count: usize,
2963 let mut err = tcx.sess.struct_span_err_with_code(sp,
2964 &format!("this function takes {}{} but {} {} supplied",
2965 if c_variadic { "at least " } else { "" },
2966 potentially_plural_count(expected_count, "parameter"),
2967 potentially_plural_count(arg_count, "parameter"),
2968 if arg_count == 1 {"was"} else {"were"}),
2969 DiagnosticId::Error(error_code.to_owned()));
2971 if let Some(def_s) = def_span.map(|sp| tcx.sess.source_map().def_span(sp)) {
2972 err.span_label(def_s, "defined here");
2975 let sugg_span = tcx.sess.source_map().end_point(expr_sp);
2976 // remove closing `)` from the span
2977 let sugg_span = sugg_span.shrink_to_lo();
2978 err.span_suggestion(
2980 "expected the unit value `()`; create it with empty parentheses",
2982 Applicability::MachineApplicable);
2984 err.span_label(sp, format!("expected {}{}",
2985 if c_variadic { "at least " } else { "" },
2986 potentially_plural_count(expected_count, "parameter")));
2991 let mut expected_arg_tys = expected_arg_tys.to_vec();
2993 let formal_tys = if tuple_arguments == TupleArguments {
2994 let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
2995 match tuple_type.sty {
2996 ty::Tuple(arg_types) if arg_types.len() != args.len() => {
2997 param_count_error(arg_types.len(), args.len(), "E0057", false, false);
2998 expected_arg_tys = vec![];
2999 self.err_args(args.len())
3001 ty::Tuple(arg_types) => {
3002 expected_arg_tys = match expected_arg_tys.get(0) {
3003 Some(&ty) => match ty.sty {
3004 ty::Tuple(ref tys) => tys.iter().map(|k| k.expect_ty()).collect(),
3009 arg_types.iter().map(|k| k.expect_ty()).collect()
3012 span_err!(tcx.sess, sp, E0059,
3013 "cannot use call notation; the first type parameter \
3014 for the function trait is neither a tuple nor unit");
3015 expected_arg_tys = vec![];
3016 self.err_args(args.len())
3019 } else if expected_arg_count == supplied_arg_count {
3021 } else if c_variadic {
3022 if supplied_arg_count >= expected_arg_count {
3025 param_count_error(expected_arg_count, supplied_arg_count, "E0060", true, false);
3026 expected_arg_tys = vec![];
3027 self.err_args(supplied_arg_count)
3030 // is the missing argument of type `()`?
3031 let sugg_unit = if expected_arg_tys.len() == 1 && supplied_arg_count == 0 {
3032 self.resolve_vars_if_possible(&expected_arg_tys[0]).is_unit()
3033 } else if fn_inputs.len() == 1 && supplied_arg_count == 0 {
3034 self.resolve_vars_if_possible(&fn_inputs[0]).is_unit()
3038 param_count_error(expected_arg_count, supplied_arg_count, "E0061", false, sugg_unit);
3040 expected_arg_tys = vec![];
3041 self.err_args(supplied_arg_count)
3044 debug!("check_argument_types: formal_tys={:?}",
3045 formal_tys.iter().map(|t| self.ty_to_string(*t)).collect::<Vec<String>>());
3047 // If there is no expectation, expect formal_tys.
3048 let expected_arg_tys = if !expected_arg_tys.is_empty() {
3054 // Check the arguments.
3055 // We do this in a pretty awful way: first we type-check any arguments
3056 // that are not closures, then we type-check the closures. This is so
3057 // that we have more information about the types of arguments when we
3058 // type-check the functions. This isn't really the right way to do this.
3059 for &check_closures in &[false, true] {
3060 debug!("check_closures={}", check_closures);
3062 // More awful hacks: before we check argument types, try to do
3063 // an "opportunistic" vtable resolution of any trait bounds on
3064 // the call. This helps coercions.
3066 self.select_obligations_where_possible(false);
3069 // For C-variadic functions, we don't have a declared type for all of
3070 // the arguments hence we only do our usual type checking with
3071 // the arguments who's types we do know.
3072 let t = if c_variadic {
3074 } else if tuple_arguments == TupleArguments {
3079 for (i, arg) in args.iter().take(t).enumerate() {
3080 // Warn only for the first loop (the "no closures" one).
3081 // Closure arguments themselves can't be diverging, but
3082 // a previous argument can, e.g., `foo(panic!(), || {})`.
3083 if !check_closures {
3084 self.warn_if_unreachable(arg.hir_id, arg.span, "expression");
3087 let is_closure = match arg.node {
3088 ExprKind::Closure(..) => true,
3092 if is_closure != check_closures {
3096 debug!("checking the argument");
3097 let formal_ty = formal_tys[i];
3099 // The special-cased logic below has three functions:
3100 // 1. Provide as good of an expected type as possible.
3101 let expected = Expectation::rvalue_hint(self, expected_arg_tys[i]);
3103 let checked_ty = self.check_expr_with_expectation(&arg, expected);
3105 // 2. Coerce to the most detailed type that could be coerced
3106 // to, which is `expected_ty` if `rvalue_hint` returns an
3107 // `ExpectHasType(expected_ty)`, or the `formal_ty` otherwise.
3108 let coerce_ty = expected.only_has_type(self).unwrap_or(formal_ty);
3109 // We're processing function arguments so we definitely want to use
3110 // two-phase borrows.
3111 self.demand_coerce(&arg, checked_ty, coerce_ty, AllowTwoPhase::Yes);
3113 // 3. Relate the expected type and the formal one,
3114 // if the expected type was used for the coercion.
3115 self.demand_suptype(arg.span, formal_ty, coerce_ty);
3119 // We also need to make sure we at least write the ty of the other
3120 // arguments which we skipped above.
3122 fn variadic_error<'tcx>(s: &Session, span: Span, t: Ty<'tcx>, cast_ty: &str) {
3123 use crate::structured_errors::{VariadicError, StructuredDiagnostic};
3124 VariadicError::new(s, span, t, cast_ty).diagnostic().emit();
3127 for arg in args.iter().skip(expected_arg_count) {
3128 let arg_ty = self.check_expr(&arg);
3130 // There are a few types which get autopromoted when passed via varargs
3131 // in C but we just error out instead and require explicit casts.
3132 let arg_ty = self.structurally_resolved_type(arg.span, arg_ty);
3134 ty::Float(ast::FloatTy::F32) => {
3135 variadic_error(tcx.sess, arg.span, arg_ty, "c_double");
3137 ty::Int(ast::IntTy::I8) | ty::Int(ast::IntTy::I16) | ty::Bool => {
3138 variadic_error(tcx.sess, arg.span, arg_ty, "c_int");
3140 ty::Uint(ast::UintTy::U8) | ty::Uint(ast::UintTy::U16) => {
3141 variadic_error(tcx.sess, arg.span, arg_ty, "c_uint");
3144 let ptr_ty = self.tcx.mk_fn_ptr(arg_ty.fn_sig(self.tcx));
3145 let ptr_ty = self.resolve_vars_if_possible(&ptr_ty);
3146 variadic_error(tcx.sess, arg.span, arg_ty, &ptr_ty.to_string());
3154 fn err_args(&self, len: usize) -> Vec<Ty<'tcx>> {
3155 vec![self.tcx.types.err; len]
3158 // AST fragment checking
3161 expected: Expectation<'tcx>)
3167 ast::LitKind::Str(..) => tcx.mk_static_str(),
3168 ast::LitKind::ByteStr(ref v) => {
3169 tcx.mk_imm_ref(tcx.lifetimes.re_static,
3170 tcx.mk_array(tcx.types.u8, v.len() as u64))
3172 ast::LitKind::Byte(_) => tcx.types.u8,
3173 ast::LitKind::Char(_) => tcx.types.char,
3174 ast::LitKind::Int(_, ast::LitIntType::Signed(t)) => tcx.mk_mach_int(t),
3175 ast::LitKind::Int(_, ast::LitIntType::Unsigned(t)) => tcx.mk_mach_uint(t),
3176 ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
3177 let opt_ty = expected.to_option(self).and_then(|ty| {
3179 ty::Int(_) | ty::Uint(_) => Some(ty),
3180 ty::Char => Some(tcx.types.u8),
3181 ty::RawPtr(..) => Some(tcx.types.usize),
3182 ty::FnDef(..) | ty::FnPtr(_) => Some(tcx.types.usize),
3186 opt_ty.unwrap_or_else(|| self.next_int_var())
3188 ast::LitKind::Float(_, t) => tcx.mk_mach_float(t),
3189 ast::LitKind::FloatUnsuffixed(_) => {
3190 let opt_ty = expected.to_option(self).and_then(|ty| {
3192 ty::Float(_) => Some(ty),
3196 opt_ty.unwrap_or_else(|| self.next_float_var())
3198 ast::LitKind::Bool(_) => tcx.types.bool,
3199 ast::LitKind::Err(_) => tcx.types.err,
3203 fn check_expr_eq_type(&self,
3204 expr: &'gcx hir::Expr,
3205 expected: Ty<'tcx>) {
3206 let ty = self.check_expr_with_hint(expr, expected);
3207 self.demand_eqtype(expr.span, expected, ty);
3210 pub fn check_expr_has_type_or_error(&self,
3211 expr: &'gcx hir::Expr,
3212 expected: Ty<'tcx>) -> Ty<'tcx> {
3213 self.check_expr_meets_expectation_or_error(expr, ExpectHasType(expected))
3216 fn check_expr_meets_expectation_or_error(&self,
3217 expr: &'gcx hir::Expr,
3218 expected: Expectation<'tcx>) -> Ty<'tcx> {
3219 let expected_ty = expected.to_option(&self).unwrap_or(self.tcx.types.bool);
3220 let mut ty = self.check_expr_with_expectation(expr, expected);
3222 // While we don't allow *arbitrary* coercions here, we *do* allow
3223 // coercions from ! to `expected`.
3225 assert!(!self.tables.borrow().adjustments().contains_key(expr.hir_id),
3226 "expression with never type wound up being adjusted");
3227 let adj_ty = self.next_diverging_ty_var(
3228 TypeVariableOrigin {
3229 kind: TypeVariableOriginKind::AdjustmentType,
3233 self.apply_adjustments(expr, vec![Adjustment {
3234 kind: Adjust::NeverToAny,
3240 if let Some(mut err) = self.demand_suptype_diag(expr.span, expected_ty, ty) {
3241 let expr = match &expr.node {
3242 ExprKind::DropTemps(expr) => expr,
3245 // Error possibly reported in `check_assign` so avoid emitting error again.
3246 err.emit_unless(self.is_assign_to_bool(expr, expected_ty));
3251 fn check_expr_coercable_to_type(&self,
3252 expr: &'gcx hir::Expr,
3253 expected: Ty<'tcx>) -> Ty<'tcx> {
3254 let ty = self.check_expr_with_hint(expr, expected);
3255 // checks don't need two phase
3256 self.demand_coerce(expr, ty, expected, AllowTwoPhase::No)
3259 fn check_expr_with_hint(&self,
3260 expr: &'gcx hir::Expr,
3261 expected: Ty<'tcx>) -> Ty<'tcx> {
3262 self.check_expr_with_expectation(expr, ExpectHasType(expected))
3265 fn check_expr_with_expectation(&self,
3266 expr: &'gcx hir::Expr,
3267 expected: Expectation<'tcx>) -> Ty<'tcx> {
3268 self.check_expr_with_expectation_and_needs(expr, expected, Needs::None)
3271 fn check_expr(&self, expr: &'gcx hir::Expr) -> Ty<'tcx> {
3272 self.check_expr_with_expectation(expr, NoExpectation)
3275 fn check_expr_with_needs(&self, expr: &'gcx hir::Expr, needs: Needs) -> Ty<'tcx> {
3276 self.check_expr_with_expectation_and_needs(expr, NoExpectation, needs)
3279 // Determine the `Self` type, using fresh variables for all variables
3280 // declared on the impl declaration e.g., `impl<A,B> for Vec<(A,B)>`
3281 // would return `($0, $1)` where `$0` and `$1` are freshly instantiated type
3283 pub fn impl_self_ty(&self,
3284 span: Span, // (potential) receiver for this impl
3286 -> TypeAndSubsts<'tcx> {
3287 let ity = self.tcx.type_of(did);
3288 debug!("impl_self_ty: ity={:?}", ity);
3290 let substs = self.fresh_substs_for_item(span, did);
3291 let substd_ty = self.instantiate_type_scheme(span, &substs, &ity);
3293 TypeAndSubsts { substs: substs, ty: substd_ty }
3296 /// Unifies the output type with the expected type early, for more coercions
3297 /// and forward type information on the input expressions.
3298 fn expected_inputs_for_expected_output(&self,
3300 expected_ret: Expectation<'tcx>,
3301 formal_ret: Ty<'tcx>,
3302 formal_args: &[Ty<'tcx>])
3304 let formal_ret = self.resolve_type_vars_with_obligations(formal_ret);
3305 let ret_ty = match expected_ret.only_has_type(self) {
3307 None => return Vec::new()
3309 let expect_args = self.fudge_inference_if_ok(|| {
3310 // Attempt to apply a subtyping relationship between the formal
3311 // return type (likely containing type variables if the function
3312 // is polymorphic) and the expected return type.
3313 // No argument expectations are produced if unification fails.
3314 let origin = self.misc(call_span);
3315 let ures = self.at(&origin, self.param_env).sup(ret_ty, &formal_ret);
3317 // FIXME(#27336) can't use ? here, Try::from_error doesn't default
3318 // to identity so the resulting type is not constrained.
3321 // Process any obligations locally as much as
3322 // we can. We don't care if some things turn
3323 // out unconstrained or ambiguous, as we're
3324 // just trying to get hints here.
3325 self.save_and_restore_in_snapshot_flag(|_| {
3326 let mut fulfill = TraitEngine::new(self.tcx);
3327 for obligation in ok.obligations {
3328 fulfill.register_predicate_obligation(self, obligation);
3330 fulfill.select_where_possible(self)
3331 }).map_err(|_| ())?;
3333 Err(_) => return Err(()),
3336 // Record all the argument types, with the substitutions
3337 // produced from the above subtyping unification.
3338 Ok(formal_args.iter().map(|ty| {
3339 self.resolve_vars_if_possible(ty)
3341 }).unwrap_or_default();
3342 debug!("expected_inputs_for_expected_output(formal={:?} -> {:?}, expected={:?} -> {:?})",
3343 formal_args, formal_ret,
3344 expect_args, expected_ret);
3348 // Checks a method call.
3349 fn check_method_call(&self,
3350 expr: &'gcx hir::Expr,
3351 segment: &hir::PathSegment,
3353 args: &'gcx [hir::Expr],
3354 expected: Expectation<'tcx>,
3355 needs: Needs) -> Ty<'tcx> {
3356 let rcvr = &args[0];
3357 let rcvr_t = self.check_expr_with_needs(&rcvr, needs);
3358 // no need to check for bot/err -- callee does that
3359 let rcvr_t = self.structurally_resolved_type(args[0].span, rcvr_t);
3361 let method = match self.lookup_method(rcvr_t,
3367 self.write_method_call(expr.hir_id, method);
3371 if segment.ident.name != kw::Invalid {
3372 self.report_method_error(span,
3375 SelfSource::MethodCall(rcvr),
3383 // Call the generic checker.
3384 self.check_method_argument_types(span,
3392 fn check_return_expr(&self, return_expr: &'gcx hir::Expr) {
3396 .unwrap_or_else(|| span_bug!(return_expr.span,
3397 "check_return_expr called outside fn body"));
3399 let ret_ty = ret_coercion.borrow().expected_ty();
3400 let return_expr_ty = self.check_expr_with_hint(return_expr, ret_ty.clone());
3401 ret_coercion.borrow_mut()
3403 &self.cause(return_expr.span,
3404 ObligationCauseCode::ReturnType(return_expr.hir_id)),
3409 // Check field access expressions
3410 fn check_field(&self,
3411 expr: &'gcx hir::Expr,
3413 base: &'gcx hir::Expr,
3414 field: ast::Ident) -> Ty<'tcx> {
3415 let expr_t = self.check_expr_with_needs(base, needs);
3416 let expr_t = self.structurally_resolved_type(base.span,
3418 let mut private_candidate = None;
3419 let mut autoderef = self.autoderef(expr.span, expr_t);
3420 while let Some((base_t, _)) = autoderef.next() {
3422 ty::Adt(base_def, substs) if !base_def.is_enum() => {
3423 debug!("struct named {:?}", base_t);
3424 let (ident, def_scope) =
3425 self.tcx.adjust_ident_and_get_scope(field, base_def.did, self.body_id);
3426 let fields = &base_def.non_enum_variant().fields;
3427 if let Some(index) = fields.iter().position(|f| f.ident.modern() == ident) {
3428 let field = &fields[index];
3429 let field_ty = self.field_ty(expr.span, field, substs);
3430 // Save the index of all fields regardless of their visibility in case
3431 // of error recovery.
3432 self.write_field_index(expr.hir_id, index);
3433 if field.vis.is_accessible_from(def_scope, self.tcx) {
3434 let adjustments = autoderef.adjust_steps(self, needs);
3435 self.apply_adjustments(base, adjustments);
3436 autoderef.finalize(self);
3438 self.tcx.check_stability(field.did, Some(expr.hir_id), expr.span);
3441 private_candidate = Some((base_def.did, field_ty));
3444 ty::Tuple(ref tys) => {
3445 let fstr = field.as_str();
3446 if let Ok(index) = fstr.parse::<usize>() {
3447 if fstr == index.to_string() {
3448 if let Some(field_ty) = tys.get(index) {
3449 let adjustments = autoderef.adjust_steps(self, needs);
3450 self.apply_adjustments(base, adjustments);
3451 autoderef.finalize(self);
3453 self.write_field_index(expr.hir_id, index);
3454 return field_ty.expect_ty();
3462 autoderef.unambiguous_final_ty(self);
3464 if let Some((did, field_ty)) = private_candidate {
3465 let struct_path = self.tcx().def_path_str(did);
3466 let mut err = struct_span_err!(self.tcx().sess, expr.span, E0616,
3467 "field `{}` of struct `{}` is private",
3468 field, struct_path);
3469 // Also check if an accessible method exists, which is often what is meant.
3470 if self.method_exists(field, expr_t, expr.hir_id, false)
3471 && !self.expr_in_place(expr.hir_id)
3473 self.suggest_method_call(
3475 &format!("a method `{}` also exists, call it with parentheses", field),
3483 } else if field.name == kw::Invalid {
3484 self.tcx().types.err
3485 } else if self.method_exists(field, expr_t, expr.hir_id, true) {
3486 let mut err = type_error_struct!(self.tcx().sess, field.span, expr_t, E0615,
3487 "attempted to take value of method `{}` on type `{}`",
3490 if !self.expr_in_place(expr.hir_id) {
3491 self.suggest_method_call(
3493 "use parentheses to call the method",
3499 err.help("methods are immutable and cannot be assigned to");
3503 self.tcx().types.err
3505 if !expr_t.is_primitive_ty() {
3506 let mut err = self.no_such_field_err(field.span, field, expr_t);
3509 ty::Adt(def, _) if !def.is_enum() => {
3510 if let Some(suggested_field_name) =
3511 Self::suggest_field_name(def.non_enum_variant(),
3512 &field.as_str(), vec![]) {
3513 err.span_suggestion(
3515 "a field with a similar name exists",
3516 suggested_field_name.to_string(),
3517 Applicability::MaybeIncorrect,
3520 err.span_label(field.span, "unknown field");
3521 let struct_variant_def = def.non_enum_variant();
3522 let field_names = self.available_field_names(struct_variant_def);
3523 if !field_names.is_empty() {
3524 err.note(&format!("available fields are: {}",
3525 self.name_series_display(field_names)));
3529 ty::Array(_, len) => {
3530 if let (Some(len), Ok(user_index)) = (
3531 len.assert_usize(self.tcx),
3532 field.as_str().parse::<u64>()
3534 let base = self.tcx.sess.source_map()
3535 .span_to_snippet(base.span)
3537 self.tcx.hir().hir_to_pretty_string(base.hir_id));
3538 let help = "instead of using tuple indexing, use array indexing";
3539 let suggestion = format!("{}[{}]", base, field);
3540 let applicability = if len < user_index {
3541 Applicability::MachineApplicable
3543 Applicability::MaybeIncorrect
3545 err.span_suggestion(
3546 expr.span, help, suggestion, applicability
3551 let base = self.tcx.sess.source_map()
3552 .span_to_snippet(base.span)
3553 .unwrap_or_else(|_| self.tcx.hir().hir_to_pretty_string(base.hir_id));
3554 let msg = format!("`{}` is a raw pointer; try dereferencing it", base);
3555 let suggestion = format!("(*{}).{}", base, field);
3556 err.span_suggestion(
3560 Applicability::MaybeIncorrect,
3567 type_error_struct!(self.tcx().sess, field.span, expr_t, E0610,
3568 "`{}` is a primitive type and therefore doesn't have fields",
3571 self.tcx().types.err
3575 // Return an hint about the closest match in field names
3576 fn suggest_field_name(variant: &'tcx ty::VariantDef,
3578 skip: Vec<LocalInternedString>)
3580 let names = variant.fields.iter().filter_map(|field| {
3581 // ignore already set fields and private fields from non-local crates
3582 if skip.iter().any(|x| *x == field.ident.as_str()) ||
3583 (!variant.def_id.is_local() && field.vis != Visibility::Public)
3587 Some(&field.ident.name)
3591 find_best_match_for_name(names, field, None)
3594 fn available_field_names(&self, variant: &'tcx ty::VariantDef) -> Vec<ast::Name> {
3595 variant.fields.iter().filter(|field| {
3597 self.tcx.adjust_ident_and_get_scope(field.ident, variant.def_id, self.body_id).1;
3598 field.vis.is_accessible_from(def_scope, self.tcx)
3600 .map(|field| field.ident.name)
3604 fn name_series_display(&self, names: Vec<ast::Name>) -> String {
3605 // dynamic limit, to never omit just one field
3606 let limit = if names.len() == 6 { 6 } else { 5 };
3607 let mut display = names.iter().take(limit)
3608 .map(|n| format!("`{}`", n)).collect::<Vec<_>>().join(", ");
3609 if names.len() > limit {
3610 display = format!("{} ... and {} others", display, names.len() - limit);
3615 fn no_such_field_err<T: Display>(&self, span: Span, field: T, expr_t: &ty::TyS<'_>)
3616 -> DiagnosticBuilder<'_> {
3617 type_error_struct!(self.tcx().sess, span, expr_t, E0609,
3618 "no field `{}` on type `{}`",
3622 fn report_unknown_field(
3625 variant: &'tcx ty::VariantDef,
3627 skip_fields: &[hir::Field],
3630 if variant.recovered {
3633 let mut err = self.type_error_struct_with_diag(
3635 |actual| match ty.sty {
3636 ty::Adt(adt, ..) if adt.is_enum() => {
3637 struct_span_err!(self.tcx.sess, field.ident.span, E0559,
3638 "{} `{}::{}` has no field named `{}`",
3639 kind_name, actual, variant.ident, field.ident)
3642 struct_span_err!(self.tcx.sess, field.ident.span, E0560,
3643 "{} `{}` has no field named `{}`",
3644 kind_name, actual, field.ident)
3648 // prevent all specified fields from being suggested
3649 let skip_fields = skip_fields.iter().map(|ref x| x.ident.as_str());
3650 if let Some(field_name) = Self::suggest_field_name(variant,
3651 &field.ident.as_str(),
3652 skip_fields.collect()) {
3653 err.span_suggestion(
3655 "a field with a similar name exists",
3656 field_name.to_string(),
3657 Applicability::MaybeIncorrect,
3661 ty::Adt(adt, ..) => {
3663 err.span_label(field.ident.span,
3664 format!("`{}::{}` does not have this field",
3665 ty, variant.ident));
3667 err.span_label(field.ident.span,
3668 format!("`{}` does not have this field", ty));
3670 let available_field_names = self.available_field_names(variant);
3671 if !available_field_names.is_empty() {
3672 err.note(&format!("available fields are: {}",
3673 self.name_series_display(available_field_names)));
3676 _ => bug!("non-ADT passed to report_unknown_field")
3682 fn check_expr_struct_fields(&self,
3684 expected: Expectation<'tcx>,
3685 expr_id: hir::HirId,
3687 variant: &'tcx ty::VariantDef,
3688 ast_fields: &'gcx [hir::Field],
3689 check_completeness: bool) -> bool {
3693 self.expected_inputs_for_expected_output(span, expected, adt_ty, &[adt_ty])
3694 .get(0).cloned().unwrap_or(adt_ty);
3695 // re-link the regions that EIfEO can erase.
3696 self.demand_eqtype(span, adt_ty_hint, adt_ty);
3698 let (substs, adt_kind, kind_name) = match &adt_ty.sty {
3699 &ty::Adt(adt, substs) => {
3700 (substs, adt.adt_kind(), adt.variant_descr())
3702 _ => span_bug!(span, "non-ADT passed to check_expr_struct_fields")
3705 let mut remaining_fields = variant.fields.iter().enumerate().map(|(i, field)|
3706 (field.ident.modern(), (i, field))
3707 ).collect::<FxHashMap<_, _>>();
3709 let mut seen_fields = FxHashMap::default();
3711 let mut error_happened = false;
3713 // Type-check each field.
3714 for field in ast_fields {
3715 let ident = tcx.adjust_ident(field.ident, variant.def_id);
3716 let field_type = if let Some((i, v_field)) = remaining_fields.remove(&ident) {
3717 seen_fields.insert(ident, field.span);
3718 self.write_field_index(field.hir_id, i);
3720 // We don't look at stability attributes on
3721 // struct-like enums (yet...), but it's definitely not
3722 // a bug to have constructed one.
3723 if adt_kind != AdtKind::Enum {
3724 tcx.check_stability(v_field.did, Some(expr_id), field.span);
3727 self.field_ty(field.span, v_field, substs)
3729 error_happened = true;
3730 if let Some(prev_span) = seen_fields.get(&ident) {
3731 let mut err = struct_span_err!(self.tcx.sess,
3734 "field `{}` specified more than once",
3737 err.span_label(field.ident.span, "used more than once");
3738 err.span_label(*prev_span, format!("first use of `{}`", ident));
3742 self.report_unknown_field(adt_ty, variant, field, ast_fields, kind_name);
3748 // Make sure to give a type to the field even if there's
3749 // an error, so we can continue type-checking.
3750 self.check_expr_coercable_to_type(&field.expr, field_type);
3753 // Make sure the programmer specified correct number of fields.
3754 if kind_name == "union" {
3755 if ast_fields.len() != 1 {
3756 tcx.sess.span_err(span, "union expressions should have exactly one field");
3758 } else if check_completeness && !error_happened && !remaining_fields.is_empty() {
3759 let len = remaining_fields.len();
3761 let mut displayable_field_names = remaining_fields
3763 .map(|ident| ident.as_str())
3764 .collect::<Vec<_>>();
3766 displayable_field_names.sort();
3768 let truncated_fields_error = if len <= 3 {
3771 format!(" and {} other field{}", (len - 3), if len - 3 == 1 {""} else {"s"})
3774 let remaining_fields_names = displayable_field_names.iter().take(3)
3775 .map(|n| format!("`{}`", n))
3776 .collect::<Vec<_>>()
3779 struct_span_err!(tcx.sess, span, E0063,
3780 "missing field{} {}{} in initializer of `{}`",
3781 if remaining_fields.len() == 1 { "" } else { "s" },
3782 remaining_fields_names,
3783 truncated_fields_error,
3785 .span_label(span, format!("missing {}{}",
3786 remaining_fields_names,
3787 truncated_fields_error))
3793 fn check_struct_fields_on_error(&self,
3794 fields: &'gcx [hir::Field],
3795 base_expr: &'gcx Option<P<hir::Expr>>) {
3796 for field in fields {
3797 self.check_expr(&field.expr);
3799 if let Some(ref base) = *base_expr {
3800 self.check_expr(&base);
3804 pub fn check_struct_path(&self,
3807 -> Option<(&'tcx ty::VariantDef, Ty<'tcx>)> {
3808 let path_span = match *qpath {
3809 QPath::Resolved(_, ref path) => path.span,
3810 QPath::TypeRelative(ref qself, _) => qself.span
3812 let (def, ty) = self.finish_resolving_struct_path(qpath, path_span, hir_id);
3813 let variant = match def {
3815 self.set_tainted_by_errors();
3818 Res::Def(DefKind::Variant, _) => {
3820 ty::Adt(adt, substs) => {
3821 Some((adt.variant_of_res(def), adt.did, substs))
3823 _ => bug!("unexpected type: {:?}", ty)
3826 Res::Def(DefKind::Struct, _)
3827 | Res::Def(DefKind::Union, _)
3828 | Res::Def(DefKind::TyAlias, _)
3829 | Res::Def(DefKind::AssocTy, _)
3830 | Res::SelfTy(..) => {
3832 ty::Adt(adt, substs) if !adt.is_enum() => {
3833 Some((adt.non_enum_variant(), adt.did, substs))
3838 _ => bug!("unexpected definition: {:?}", def)
3841 if let Some((variant, did, substs)) = variant {
3842 debug!("check_struct_path: did={:?} substs={:?}", did, substs);
3843 self.write_user_type_annotation_from_substs(hir_id, did, substs, None);
3845 // Check bounds on type arguments used in the path.
3846 let bounds = self.instantiate_bounds(path_span, did, substs);
3847 let cause = traits::ObligationCause::new(path_span, self.body_id,
3848 traits::ItemObligation(did));
3849 self.add_obligations_for_parameters(cause, &bounds);
3853 struct_span_err!(self.tcx.sess, path_span, E0071,
3854 "expected struct, variant or union type, found {}",
3855 ty.sort_string(self.tcx))
3856 .span_label(path_span, "not a struct")
3862 fn check_expr_struct(&self,
3864 expected: Expectation<'tcx>,
3866 fields: &'gcx [hir::Field],
3867 base_expr: &'gcx Option<P<hir::Expr>>) -> Ty<'tcx>
3869 // Find the relevant variant
3870 let (variant, adt_ty) =
3871 if let Some(variant_ty) = self.check_struct_path(qpath, expr.hir_id) {
3874 self.check_struct_fields_on_error(fields, base_expr);
3875 return self.tcx.types.err;
3878 let path_span = match *qpath {
3879 QPath::Resolved(_, ref path) => path.span,
3880 QPath::TypeRelative(ref qself, _) => qself.span
3883 // Prohibit struct expressions when non-exhaustive flag is set.
3884 let adt = adt_ty.ty_adt_def().expect("`check_struct_path` returned non-ADT type");
3885 if !adt.did.is_local() && variant.is_field_list_non_exhaustive() {
3886 span_err!(self.tcx.sess, expr.span, E0639,
3887 "cannot create non-exhaustive {} using struct expression",
3888 adt.variant_descr());
3891 let error_happened = self.check_expr_struct_fields(adt_ty, expected, expr.hir_id, path_span,
3892 variant, fields, base_expr.is_none());
3893 if let &Some(ref base_expr) = base_expr {
3894 // If check_expr_struct_fields hit an error, do not attempt to populate
3895 // the fields with the base_expr. This could cause us to hit errors later
3896 // when certain fields are assumed to exist that in fact do not.
3897 if !error_happened {
3898 self.check_expr_has_type_or_error(base_expr, adt_ty);
3900 ty::Adt(adt, substs) if adt.is_struct() => {
3901 let fru_field_types = adt.non_enum_variant().fields.iter().map(|f| {
3902 self.normalize_associated_types_in(expr.span, &f.ty(self.tcx, substs))
3907 .fru_field_types_mut()
3908 .insert(expr.hir_id, fru_field_types);
3911 span_err!(self.tcx.sess, base_expr.span, E0436,
3912 "functional record update syntax requires a struct");
3917 self.require_type_is_sized(adt_ty, expr.span, traits::StructInitializerSized);
3923 /// If an expression has any sub-expressions that result in a type error,
3924 /// inspecting that expression's type with `ty.references_error()` will return
3925 /// true. Likewise, if an expression is known to diverge, inspecting its
3926 /// type with `ty::type_is_bot` will return true (n.b.: since Rust is
3927 /// strict, _|_ can appear in the type of an expression that does not,
3928 /// itself, diverge: for example, fn() -> _|_.)
3929 /// Note that inspecting a type's structure *directly* may expose the fact
3930 /// that there are actually multiple representations for `Error`, so avoid
3931 /// that when err needs to be handled differently.
3932 fn check_expr_with_expectation_and_needs(&self,
3933 expr: &'gcx hir::Expr,
3934 expected: Expectation<'tcx>,
3935 needs: Needs) -> Ty<'tcx> {
3936 debug!(">> type-checking: expr={:?} expected={:?}",
3939 // Warn for expressions after diverging siblings.
3940 self.warn_if_unreachable(expr.hir_id, expr.span, "expression");
3942 // Hide the outer diverging and has_errors flags.
3943 let old_diverges = self.diverges.get();
3944 let old_has_errors = self.has_errors.get();
3945 self.diverges.set(Diverges::Maybe);
3946 self.has_errors.set(false);
3948 let ty = self.check_expr_kind(expr, expected, needs);
3950 // Warn for non-block expressions with diverging children.
3952 ExprKind::Block(..) |
3953 ExprKind::Loop(..) | ExprKind::While(..) |
3954 ExprKind::Match(..) => {}
3956 _ => self.warn_if_unreachable(expr.hir_id, expr.span, "expression")
3959 // Any expression that produces a value of type `!` must have diverged
3961 self.diverges.set(self.diverges.get() | Diverges::Always);
3964 // Record the type, which applies it effects.
3965 // We need to do this after the warning above, so that
3966 // we don't warn for the diverging expression itself.
3967 self.write_ty(expr.hir_id, ty);
3969 // Combine the diverging and has_error flags.
3970 self.diverges.set(self.diverges.get() | old_diverges);
3971 self.has_errors.set(self.has_errors.get() | old_has_errors);
3973 debug!("type of {} is...", self.tcx.hir().hir_to_string(expr.hir_id));
3974 debug!("... {:?}, expected is {:?}", ty, expected);
3981 expr: &'gcx hir::Expr,
3982 expected: Expectation<'tcx>,
3986 "check_expr_kind(expr={:?}, expected={:?}, needs={:?})",
3993 let id = expr.hir_id;
3995 ExprKind::Box(ref subexpr) => {
3996 let expected_inner = expected.to_option(self).map_or(NoExpectation, |ty| {
3998 ty::Adt(def, _) if def.is_box()
3999 => Expectation::rvalue_hint(self, ty.boxed_ty()),
4003 let referent_ty = self.check_expr_with_expectation(subexpr, expected_inner);
4004 tcx.mk_box(referent_ty)
4007 ExprKind::Lit(ref lit) => {
4008 self.check_lit(&lit, expected)
4010 ExprKind::Binary(op, ref lhs, ref rhs) => {
4011 self.check_binop(expr, op, lhs, rhs)
4013 ExprKind::AssignOp(op, ref lhs, ref rhs) => {
4014 self.check_binop_assign(expr, op, lhs, rhs)
4016 ExprKind::Unary(unop, ref oprnd) => {
4017 let expected_inner = match unop {
4018 hir::UnNot | hir::UnNeg => {
4025 let needs = match unop {
4026 hir::UnDeref => needs,
4029 let mut oprnd_t = self.check_expr_with_expectation_and_needs(&oprnd,
4033 if !oprnd_t.references_error() {
4034 oprnd_t = self.structurally_resolved_type(expr.span, oprnd_t);
4037 if let Some(mt) = oprnd_t.builtin_deref(true) {
4039 } else if let Some(ok) = self.try_overloaded_deref(
4040 expr.span, oprnd_t, needs) {
4041 let method = self.register_infer_ok_obligations(ok);
4042 if let ty::Ref(region, _, mutbl) = method.sig.inputs()[0].sty {
4043 let mutbl = match mutbl {
4044 hir::MutImmutable => AutoBorrowMutability::Immutable,
4045 hir::MutMutable => AutoBorrowMutability::Mutable {
4046 // (It shouldn't actually matter for unary ops whether
4047 // we enable two-phase borrows or not, since a unary
4048 // op has no additional operands.)
4049 allow_two_phase_borrow: AllowTwoPhase::No,
4052 self.apply_adjustments(oprnd, vec![Adjustment {
4053 kind: Adjust::Borrow(AutoBorrow::Ref(region, mutbl)),
4054 target: method.sig.inputs()[0]
4057 oprnd_t = self.make_overloaded_place_return_type(method).ty;
4058 self.write_method_call(expr.hir_id, method);
4060 let mut err = type_error_struct!(
4065 "type `{}` cannot be dereferenced",
4068 let sp = tcx.sess.source_map().start_point(expr.span);
4069 if let Some(sp) = tcx.sess.parse_sess.ambiguous_block_expr_parse
4072 tcx.sess.parse_sess.expr_parentheses_needed(
4079 oprnd_t = tcx.types.err;
4083 let result = self.check_user_unop(expr, oprnd_t, unop);
4084 // If it's builtin, we can reuse the type, this helps inference.
4085 if !(oprnd_t.is_integral() || oprnd_t.sty == ty::Bool) {
4090 let result = self.check_user_unop(expr, oprnd_t, unop);
4091 // If it's builtin, we can reuse the type, this helps inference.
4092 if !(oprnd_t.is_integral() || oprnd_t.is_fp()) {
4100 ExprKind::AddrOf(mutbl, ref oprnd) => {
4101 let hint = expected.only_has_type(self).map_or(NoExpectation, |ty| {
4103 ty::Ref(_, ty, _) | ty::RawPtr(ty::TypeAndMut { ty, .. }) => {
4104 if oprnd.is_place_expr() {
4105 // Places may legitimately have unsized types.
4106 // For example, dereferences of a fat pointer and
4107 // the last field of a struct can be unsized.
4110 Expectation::rvalue_hint(self, ty)
4116 let needs = Needs::maybe_mut_place(mutbl);
4117 let ty = self.check_expr_with_expectation_and_needs(&oprnd, hint, needs);
4119 let tm = ty::TypeAndMut { ty: ty, mutbl: mutbl };
4120 if tm.ty.references_error() {
4123 // Note: at this point, we cannot say what the best lifetime
4124 // is to use for resulting pointer. We want to use the
4125 // shortest lifetime possible so as to avoid spurious borrowck
4126 // errors. Moreover, the longest lifetime will depend on the
4127 // precise details of the value whose address is being taken
4128 // (and how long it is valid), which we don't know yet until type
4129 // inference is complete.
4131 // Therefore, here we simply generate a region variable. The
4132 // region inferencer will then select the ultimate value.
4133 // Finally, borrowck is charged with guaranteeing that the
4134 // value whose address was taken can actually be made to live
4135 // as long as it needs to live.
4136 let region = self.next_region_var(infer::AddrOfRegion(expr.span));
4137 tcx.mk_ref(region, tm)
4140 ExprKind::Path(ref qpath) => {
4141 let (res, opt_ty, segs) = self.resolve_ty_and_res_ufcs(qpath, expr.hir_id,
4143 let ty = match res {
4145 self.set_tainted_by_errors();
4148 Res::Def(DefKind::Ctor(_, CtorKind::Fictive), _) => {
4149 report_unexpected_variant_res(tcx, res, expr.span, qpath);
4152 _ => self.instantiate_value_path(segs, opt_ty, res, expr.span, id).0,
4155 if let ty::FnDef(..) = ty.sty {
4156 let fn_sig = ty.fn_sig(tcx);
4157 if !tcx.features().unsized_locals {
4158 // We want to remove some Sized bounds from std functions,
4159 // but don't want to expose the removal to stable Rust.
4160 // i.e., we don't want to allow
4166 // to work in stable even if the Sized bound on `drop` is relaxed.
4167 for i in 0..fn_sig.inputs().skip_binder().len() {
4168 // We just want to check sizedness, so instead of introducing
4169 // placeholder lifetimes with probing, we just replace higher lifetimes
4171 let input = self.replace_bound_vars_with_fresh_vars(
4173 infer::LateBoundRegionConversionTime::FnCall,
4174 &fn_sig.input(i)).0;
4175 self.require_type_is_sized_deferred(input, expr.span,
4176 traits::SizedArgumentType);
4179 // Here we want to prevent struct constructors from returning unsized types.
4180 // There were two cases this happened: fn pointer coercion in stable
4181 // and usual function call in presense of unsized_locals.
4182 // Also, as we just want to check sizedness, instead of introducing
4183 // placeholder lifetimes with probing, we just replace higher lifetimes
4185 let output = self.replace_bound_vars_with_fresh_vars(
4187 infer::LateBoundRegionConversionTime::FnCall,
4188 &fn_sig.output()).0;
4189 self.require_type_is_sized_deferred(output, expr.span, traits::SizedReturnType);
4192 // We always require that the type provided as the value for
4193 // a type parameter outlives the moment of instantiation.
4194 let substs = self.tables.borrow().node_substs(expr.hir_id);
4195 self.add_wf_bounds(substs, expr);
4199 ExprKind::InlineAsm(_, ref outputs, ref inputs) => {
4200 for expr in outputs.iter().chain(inputs.iter()) {
4201 self.check_expr(expr);
4205 ExprKind::Break(destination, ref expr_opt) => {
4206 if let Ok(target_id) = destination.target_id {
4208 if let Some(ref e) = *expr_opt {
4209 // If this is a break with a value, we need to type-check
4210 // the expression. Get an expected type from the loop context.
4211 let opt_coerce_to = {
4212 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4213 enclosing_breakables.find_breakable(target_id)
4216 .map(|coerce| coerce.expected_ty())
4219 // If the loop context is not a `loop { }`, then break with
4220 // a value is illegal, and `opt_coerce_to` will be `None`.
4221 // Just set expectation to error in that case.
4222 let coerce_to = opt_coerce_to.unwrap_or(tcx.types.err);
4224 // Recurse without `enclosing_breakables` borrowed.
4225 e_ty = self.check_expr_with_hint(e, coerce_to);
4226 cause = self.misc(e.span);
4228 // Otherwise, this is a break *without* a value. That's
4229 // always legal, and is equivalent to `break ()`.
4230 e_ty = tcx.mk_unit();
4231 cause = self.misc(expr.span);
4234 // Now that we have type-checked `expr_opt`, borrow
4235 // the `enclosing_loops` field and let's coerce the
4236 // type of `expr_opt` into what is expected.
4237 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4238 let ctxt = enclosing_breakables.find_breakable(target_id);
4239 if let Some(ref mut coerce) = ctxt.coerce {
4240 if let Some(ref e) = *expr_opt {
4241 coerce.coerce(self, &cause, e, e_ty);
4243 assert!(e_ty.is_unit());
4244 coerce.coerce_forced_unit(self, &cause, &mut |_| (), true);
4247 // If `ctxt.coerce` is `None`, we can just ignore
4248 // the type of the expresison. This is because
4249 // either this was a break *without* a value, in
4250 // which case it is always a legal type (`()`), or
4251 // else an error would have been flagged by the
4252 // `loops` pass for using break with an expression
4253 // where you are not supposed to.
4254 assert!(expr_opt.is_none() || self.tcx.sess.err_count() > 0);
4257 ctxt.may_break = true;
4259 // the type of a `break` is always `!`, since it diverges
4262 // Otherwise, we failed to find the enclosing loop;
4263 // this can only happen if the `break` was not
4264 // inside a loop at all, which is caught by the
4265 // loop-checking pass.
4266 if self.tcx.sess.err_count() == 0 {
4267 self.tcx.sess.delay_span_bug(expr.span,
4268 "break was outside loop, but no error was emitted");
4271 // We still need to assign a type to the inner expression to
4272 // prevent the ICE in #43162.
4273 if let Some(ref e) = *expr_opt {
4274 self.check_expr_with_hint(e, tcx.types.err);
4276 // ... except when we try to 'break rust;'.
4277 // ICE this expression in particular (see #43162).
4278 if let ExprKind::Path(QPath::Resolved(_, ref path)) = e.node {
4279 if path.segments.len() == 1 &&
4280 path.segments[0].ident.name == sym::rust {
4281 fatally_break_rust(self.tcx.sess);
4285 // There was an error; make type-check fail.
4290 ExprKind::Continue(destination) => {
4291 if destination.target_id.is_ok() {
4294 // There was an error; make type-check fail.
4298 ExprKind::Ret(ref expr_opt) => {
4299 if self.ret_coercion.is_none() {
4300 struct_span_err!(self.tcx.sess, expr.span, E0572,
4301 "return statement outside of function body").emit();
4302 } else if let Some(ref e) = *expr_opt {
4303 if self.ret_coercion_span.borrow().is_none() {
4304 *self.ret_coercion_span.borrow_mut() = Some(e.span);
4306 self.check_return_expr(e);
4308 let mut coercion = self.ret_coercion.as_ref().unwrap().borrow_mut();
4309 if self.ret_coercion_span.borrow().is_none() {
4310 *self.ret_coercion_span.borrow_mut() = Some(expr.span);
4312 let cause = self.cause(expr.span, ObligationCauseCode::ReturnNoExpression);
4313 if let Some((fn_decl, _)) = self.get_fn_decl(expr.hir_id) {
4314 coercion.coerce_forced_unit(
4319 fn_decl.output.span(),
4321 "expected `{}` because of this return type",
4329 coercion.coerce_forced_unit(self, &cause, &mut |_| (), true);
4334 ExprKind::Assign(ref lhs, ref rhs) => {
4335 self.check_assign(expr, expected, lhs, rhs)
4337 ExprKind::While(ref cond, ref body, _) => {
4338 let ctxt = BreakableCtxt {
4339 // cannot use break with a value from a while loop
4341 may_break: false, // Will get updated if/when we find a `break`.
4344 let (ctxt, ()) = self.with_breakable_ctxt(expr.hir_id, ctxt, || {
4345 self.check_expr_has_type_or_error(&cond, tcx.types.bool);
4346 let cond_diverging = self.diverges.get();
4347 self.check_block_no_value(&body);
4349 // We may never reach the body so it diverging means nothing.
4350 self.diverges.set(cond_diverging);
4354 // No way to know whether it's diverging because
4355 // of a `break` or an outer `break` or `return`.
4356 self.diverges.set(Diverges::Maybe);
4361 ExprKind::Loop(ref body, _, source) => {
4362 let coerce = match source {
4363 // you can only use break with a value from a normal `loop { }`
4364 hir::LoopSource::Loop => {
4365 let coerce_to = expected.coercion_target_type(self, body.span);
4366 Some(CoerceMany::new(coerce_to))
4369 hir::LoopSource::WhileLet |
4370 hir::LoopSource::ForLoop => {
4375 let ctxt = BreakableCtxt {
4377 may_break: false, // Will get updated if/when we find a `break`.
4380 let (ctxt, ()) = self.with_breakable_ctxt(expr.hir_id, ctxt, || {
4381 self.check_block_no_value(&body);
4385 // No way to know whether it's diverging because
4386 // of a `break` or an outer `break` or `return`.
4387 self.diverges.set(Diverges::Maybe);
4390 // If we permit break with a value, then result type is
4391 // the LUB of the breaks (possibly ! if none); else, it
4392 // is nil. This makes sense because infinite loops
4393 // (which would have type !) are only possible iff we
4394 // permit break with a value [1].
4395 if ctxt.coerce.is_none() && !ctxt.may_break {
4397 self.tcx.sess.delay_span_bug(body.span, "no coercion, but loop may not break");
4399 ctxt.coerce.map(|c| c.complete(self)).unwrap_or_else(|| self.tcx.mk_unit())
4401 ExprKind::Match(ref discrim, ref arms, match_src) => {
4402 self.check_match(expr, &discrim, arms, expected, match_src)
4404 ExprKind::Closure(capture, ref decl, body_id, _, gen) => {
4405 self.check_expr_closure(expr, capture, &decl, body_id, gen, expected)
4407 ExprKind::Block(ref body, _) => {
4408 self.check_block_with_expected(&body, expected)
4410 ExprKind::Call(ref callee, ref args) => {
4411 self.check_call(expr, &callee, args, expected)
4413 ExprKind::MethodCall(ref segment, span, ref args) => {
4414 self.check_method_call(expr, segment, span, args, expected, needs)
4416 ExprKind::Cast(ref e, ref t) => {
4417 // Find the type of `e`. Supply hints based on the type we are casting to,
4419 let t_cast = self.to_ty_saving_user_provided_ty(t);
4420 let t_cast = self.resolve_vars_if_possible(&t_cast);
4421 let t_expr = self.check_expr_with_expectation(e, ExpectCastableToType(t_cast));
4422 let t_cast = self.resolve_vars_if_possible(&t_cast);
4424 // Eagerly check for some obvious errors.
4425 if t_expr.references_error() || t_cast.references_error() {
4428 // Defer other checks until we're done type checking.
4429 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
4430 match cast::CastCheck::new(self, e, t_expr, t_cast, t.span, expr.span) {
4432 deferred_cast_checks.push(cast_check);
4435 Err(ErrorReported) => {
4441 ExprKind::Type(ref e, ref t) => {
4442 let ty = self.to_ty_saving_user_provided_ty(&t);
4443 self.check_expr_eq_type(&e, ty);
4446 ExprKind::DropTemps(ref e) => {
4447 self.check_expr_with_expectation(e, expected)
4449 ExprKind::Array(ref args) => {
4450 let uty = expected.to_option(self).and_then(|uty| {
4452 ty::Array(ty, _) | ty::Slice(ty) => Some(ty),
4457 let element_ty = if !args.is_empty() {
4458 let coerce_to = uty.unwrap_or_else(|| {
4459 self.next_ty_var(TypeVariableOrigin {
4460 kind: TypeVariableOriginKind::TypeInference,
4464 let mut coerce = CoerceMany::with_coercion_sites(coerce_to, args);
4465 assert_eq!(self.diverges.get(), Diverges::Maybe);
4467 let e_ty = self.check_expr_with_hint(e, coerce_to);
4468 let cause = self.misc(e.span);
4469 coerce.coerce(self, &cause, e, e_ty);
4471 coerce.complete(self)
4473 self.next_ty_var(TypeVariableOrigin {
4474 kind: TypeVariableOriginKind::TypeInference,
4478 tcx.mk_array(element_ty, args.len() as u64)
4480 ExprKind::Repeat(ref element, ref count) => {
4481 let count_def_id = tcx.hir().local_def_id_from_hir_id(count.hir_id);
4482 let param_env = ty::ParamEnv::empty();
4483 let substs = InternalSubsts::identity_for_item(tcx.global_tcx(), count_def_id);
4484 let instance = ty::Instance::resolve(
4490 let global_id = GlobalId {
4494 let count = tcx.const_eval(param_env.and(global_id));
4496 let uty = match expected {
4497 ExpectHasType(uty) => {
4499 ty::Array(ty, _) | ty::Slice(ty) => Some(ty),
4506 let (element_ty, t) = match uty {
4508 self.check_expr_coercable_to_type(&element, uty);
4512 let ty = self.next_ty_var(TypeVariableOrigin {
4513 kind: TypeVariableOriginKind::MiscVariable,
4516 let element_ty = self.check_expr_has_type_or_error(&element, ty);
4521 if let Ok(count) = count {
4522 let zero_or_one = count.assert_usize(tcx).map_or(false, |count| count <= 1);
4524 // For [foo, ..n] where n > 1, `foo` must have
4526 let lang_item = self.tcx.require_lang_item(lang_items::CopyTraitLangItem);
4527 self.require_type_meets(t, expr.span, traits::RepeatVec, lang_item);
4531 if element_ty.references_error() {
4533 } else if let Ok(count) = count {
4534 tcx.mk_ty(ty::Array(t, count))
4539 ExprKind::Tup(ref elts) => {
4540 let flds = expected.only_has_type(self).and_then(|ty| {
4541 let ty = self.resolve_type_vars_with_obligations(ty);
4543 ty::Tuple(ref flds) => Some(&flds[..]),
4548 let elt_ts_iter = elts.iter().enumerate().map(|(i, e)| {
4549 let t = match flds {
4550 Some(ref fs) if i < fs.len() => {
4551 let ety = fs[i].expect_ty();
4552 self.check_expr_coercable_to_type(&e, ety);
4556 self.check_expr_with_expectation(&e, NoExpectation)
4561 let tuple = tcx.mk_tup(elt_ts_iter);
4562 if tuple.references_error() {
4565 self.require_type_is_sized(tuple, expr.span, traits::TupleInitializerSized);
4569 ExprKind::Struct(ref qpath, ref fields, ref base_expr) => {
4570 self.check_expr_struct(expr, expected, qpath, fields, base_expr)
4572 ExprKind::Field(ref base, field) => {
4573 self.check_field(expr, needs, &base, field)
4575 ExprKind::Index(ref base, ref idx) => {
4576 let base_t = self.check_expr_with_needs(&base, needs);
4577 let idx_t = self.check_expr(&idx);
4579 if base_t.references_error() {
4581 } else if idx_t.references_error() {
4584 let base_t = self.structurally_resolved_type(base.span, base_t);
4585 match self.lookup_indexing(expr, base, base_t, idx_t, needs) {
4586 Some((index_ty, element_ty)) => {
4587 // two-phase not needed because index_ty is never mutable
4588 self.demand_coerce(idx, idx_t, index_ty, AllowTwoPhase::No);
4593 type_error_struct!(tcx.sess, expr.span, base_t, E0608,
4594 "cannot index into a value of type `{}`",
4596 // Try to give some advice about indexing tuples.
4597 if let ty::Tuple(..) = base_t.sty {
4598 let mut needs_note = true;
4599 // If the index is an integer, we can show the actual
4600 // fixed expression:
4601 if let ExprKind::Lit(ref lit) = idx.node {
4602 if let ast::LitKind::Int(i,
4603 ast::LitIntType::Unsuffixed) = lit.node {
4604 let snip = tcx.sess.source_map().span_to_snippet(base.span);
4605 if let Ok(snip) = snip {
4606 err.span_suggestion(
4608 "to access tuple elements, use",
4609 format!("{}.{}", snip, i),
4610 Applicability::MachineApplicable,
4617 err.help("to access tuple elements, use tuple indexing \
4618 syntax (e.g., `tuple.0`)");
4627 ExprKind::Yield(ref value) => {
4628 match self.yield_ty {
4630 self.check_expr_coercable_to_type(&value, ty);
4633 struct_span_err!(self.tcx.sess, expr.span, E0627,
4634 "yield statement outside of generator literal").emit();
4639 hir::ExprKind::Err => {
4645 /// Type check assignment expression `expr` of form `lhs = rhs`.
4646 /// The expected type is `()` and is passsed to the function for the purposes of diagnostics.
4649 expr: &'gcx hir::Expr,
4650 expected: Expectation<'tcx>,
4651 lhs: &'gcx hir::Expr,
4652 rhs: &'gcx hir::Expr,
4654 let lhs_ty = self.check_expr_with_needs(&lhs, Needs::MutPlace);
4655 let rhs_ty = self.check_expr_coercable_to_type(&rhs, lhs_ty);
4657 let expected_ty = expected.coercion_target_type(self, expr.span);
4658 if expected_ty == self.tcx.types.bool {
4659 // The expected type is `bool` but this will result in `()` so we can reasonably
4660 // say that the user intended to write `lhs == rhs` instead of `lhs = rhs`.
4661 // The likely cause of this is `if foo = bar { .. }`.
4662 let actual_ty = self.tcx.mk_unit();
4663 let mut err = self.demand_suptype_diag(expr.span, expected_ty, actual_ty).unwrap();
4664 let msg = "try comparing for equality";
4665 let left = self.tcx.sess.source_map().span_to_snippet(lhs.span);
4666 let right = self.tcx.sess.source_map().span_to_snippet(rhs.span);
4667 if let (Ok(left), Ok(right)) = (left, right) {
4668 let help = format!("{} == {}", left, right);
4669 err.span_suggestion(expr.span, msg, help, Applicability::MaybeIncorrect);
4674 } else if !lhs.is_place_expr() {
4675 struct_span_err!(self.tcx.sess, expr.span, E0070,
4676 "invalid left-hand side expression")
4677 .span_label(expr.span, "left-hand of expression not valid")
4681 self.require_type_is_sized(lhs_ty, lhs.span, traits::AssignmentLhsSized);
4683 if lhs_ty.references_error() || rhs_ty.references_error() {
4690 // Finish resolving a path in a struct expression or pattern `S::A { .. }` if necessary.
4691 // The newly resolved definition is written into `type_dependent_defs`.
4692 fn finish_resolving_struct_path(&self,
4699 QPath::Resolved(ref maybe_qself, ref path) => {
4700 let self_ty = maybe_qself.as_ref().map(|qself| self.to_ty(qself));
4701 let ty = AstConv::res_to_ty(self, self_ty, path, true);
4704 QPath::TypeRelative(ref qself, ref segment) => {
4705 let ty = self.to_ty(qself);
4707 let res = if let hir::TyKind::Path(QPath::Resolved(_, ref path)) = qself.node {
4712 let result = AstConv::associated_path_to_ty(
4721 let ty = result.map(|(ty, _, _)| ty).unwrap_or(self.tcx().types.err);
4722 let result = result.map(|(_, kind, def_id)| (kind, def_id));
4724 // Write back the new resolution.
4725 self.tables.borrow_mut().type_dependent_defs_mut().insert(hir_id, result);
4727 (result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err), ty)
4732 /// Resolves associated value path into a base type and associated constant or method
4733 /// resolution. The newly resolved definition is written into `type_dependent_defs`.
4734 pub fn resolve_ty_and_res_ufcs<'b>(&self,
4738 -> (Res, Option<Ty<'tcx>>, &'b [hir::PathSegment])
4740 debug!("resolve_ty_and_res_ufcs: qpath={:?} hir_id={:?} span={:?}", qpath, hir_id, span);
4741 let (ty, qself, item_segment) = match *qpath {
4742 QPath::Resolved(ref opt_qself, ref path) => {
4744 opt_qself.as_ref().map(|qself| self.to_ty(qself)),
4745 &path.segments[..]);
4747 QPath::TypeRelative(ref qself, ref segment) => {
4748 (self.to_ty(qself), qself, segment)
4751 if let Some(&cached_result) = self.tables.borrow().type_dependent_defs().get(hir_id) {
4752 // Return directly on cache hit. This is useful to avoid doubly reporting
4753 // errors with default match binding modes. See #44614.
4754 let def = cached_result.map(|(kind, def_id)| Res::Def(kind, def_id))
4755 .unwrap_or(Res::Err);
4756 return (def, Some(ty), slice::from_ref(&**item_segment));
4758 let item_name = item_segment.ident;
4759 let result = self.resolve_ufcs(span, item_name, ty, hir_id).or_else(|error| {
4760 let result = match error {
4761 method::MethodError::PrivateMatch(kind, def_id, _) => Ok((kind, def_id)),
4762 _ => Err(ErrorReported),
4764 if item_name.name != kw::Invalid {
4765 self.report_method_error(
4769 SelfSource::QPath(qself),
4777 // Write back the new resolution.
4778 self.tables.borrow_mut().type_dependent_defs_mut().insert(hir_id, result);
4780 result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err),
4782 slice::from_ref(&**item_segment),
4786 pub fn check_decl_initializer(&self,
4787 local: &'gcx hir::Local,
4788 init: &'gcx hir::Expr) -> Ty<'tcx>
4790 // FIXME(tschottdorf): `contains_explicit_ref_binding()` must be removed
4791 // for #42640 (default match binding modes).
4794 let ref_bindings = local.pat.contains_explicit_ref_binding();
4796 let local_ty = self.local_ty(init.span, local.hir_id).revealed_ty;
4797 if let Some(m) = ref_bindings {
4798 // Somewhat subtle: if we have a `ref` binding in the pattern,
4799 // we want to avoid introducing coercions for the RHS. This is
4800 // both because it helps preserve sanity and, in the case of
4801 // ref mut, for soundness (issue #23116). In particular, in
4802 // the latter case, we need to be clear that the type of the
4803 // referent for the reference that results is *equal to* the
4804 // type of the place it is referencing, and not some
4805 // supertype thereof.
4806 let init_ty = self.check_expr_with_needs(init, Needs::maybe_mut_place(m));
4807 self.demand_eqtype(init.span, local_ty, init_ty);
4810 self.check_expr_coercable_to_type(init, local_ty)
4814 pub fn check_decl_local(&self, local: &'gcx hir::Local) {
4815 let t = self.local_ty(local.span, local.hir_id).decl_ty;
4816 self.write_ty(local.hir_id, t);
4818 if let Some(ref init) = local.init {
4819 let init_ty = self.check_decl_initializer(local, &init);
4820 if init_ty.references_error() {
4821 self.write_ty(local.hir_id, init_ty);
4825 self.check_pat_walk(
4828 ty::BindingMode::BindByValue(hir::Mutability::MutImmutable),
4831 let pat_ty = self.node_ty(local.pat.hir_id);
4832 if pat_ty.references_error() {
4833 self.write_ty(local.hir_id, pat_ty);
4837 pub fn check_stmt(&self, stmt: &'gcx hir::Stmt) {
4838 // Don't do all the complex logic below for `DeclItem`.
4840 hir::StmtKind::Item(..) => return,
4841 hir::StmtKind::Local(..) | hir::StmtKind::Expr(..) | hir::StmtKind::Semi(..) => {}
4844 self.warn_if_unreachable(stmt.hir_id, stmt.span, "statement");
4846 // Hide the outer diverging and `has_errors` flags.
4847 let old_diverges = self.diverges.get();
4848 let old_has_errors = self.has_errors.get();
4849 self.diverges.set(Diverges::Maybe);
4850 self.has_errors.set(false);
4853 hir::StmtKind::Local(ref l) => {
4854 self.check_decl_local(&l);
4857 hir::StmtKind::Item(_) => {}
4858 hir::StmtKind::Expr(ref expr) => {
4859 // Check with expected type of `()`.
4860 self.check_expr_has_type_or_error(&expr, self.tcx.mk_unit());
4862 hir::StmtKind::Semi(ref expr) => {
4863 self.check_expr(&expr);
4867 // Combine the diverging and `has_error` flags.
4868 self.diverges.set(self.diverges.get() | old_diverges);
4869 self.has_errors.set(self.has_errors.get() | old_has_errors);
4872 pub fn check_block_no_value(&self, blk: &'gcx hir::Block) {
4873 let unit = self.tcx.mk_unit();
4874 let ty = self.check_block_with_expected(blk, ExpectHasType(unit));
4876 // if the block produces a `!` value, that can always be
4877 // (effectively) coerced to unit.
4879 self.demand_suptype(blk.span, unit, ty);
4883 fn check_block_with_expected(&self,
4884 blk: &'gcx hir::Block,
4885 expected: Expectation<'tcx>) -> Ty<'tcx> {
4887 let mut fcx_ps = self.ps.borrow_mut();
4888 let unsafety_state = fcx_ps.recurse(blk);
4889 replace(&mut *fcx_ps, unsafety_state)
4892 // In some cases, blocks have just one exit, but other blocks
4893 // can be targeted by multiple breaks. This can happen both
4894 // with labeled blocks as well as when we desugar
4895 // a `try { ... }` expression.
4899 // 'a: { if true { break 'a Err(()); } Ok(()) }
4901 // Here we would wind up with two coercions, one from
4902 // `Err(())` and the other from the tail expression
4903 // `Ok(())`. If the tail expression is omitted, that's a
4904 // "forced unit" -- unless the block diverges, in which
4905 // case we can ignore the tail expression (e.g., `'a: {
4906 // break 'a 22; }` would not force the type of the block
4908 let tail_expr = blk.expr.as_ref();
4909 let coerce_to_ty = expected.coercion_target_type(self, blk.span);
4910 let coerce = if blk.targeted_by_break {
4911 CoerceMany::new(coerce_to_ty)
4913 let tail_expr: &[P<hir::Expr>] = match tail_expr {
4914 Some(e) => slice::from_ref(e),
4917 CoerceMany::with_coercion_sites(coerce_to_ty, tail_expr)
4920 let prev_diverges = self.diverges.get();
4921 let ctxt = BreakableCtxt {
4922 coerce: Some(coerce),
4926 let (ctxt, ()) = self.with_breakable_ctxt(blk.hir_id, ctxt, || {
4927 for s in &blk.stmts {
4931 // check the tail expression **without** holding the
4932 // `enclosing_breakables` lock below.
4933 let tail_expr_ty = tail_expr.map(|t| self.check_expr_with_expectation(t, expected));
4935 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4936 let ctxt = enclosing_breakables.find_breakable(blk.hir_id);
4937 let coerce = ctxt.coerce.as_mut().unwrap();
4938 if let Some(tail_expr_ty) = tail_expr_ty {
4939 let tail_expr = tail_expr.unwrap();
4940 let cause = self.cause(tail_expr.span,
4941 ObligationCauseCode::BlockTailExpression(blk.hir_id));
4947 // Subtle: if there is no explicit tail expression,
4948 // that is typically equivalent to a tail expression
4949 // of `()` -- except if the block diverges. In that
4950 // case, there is no value supplied from the tail
4951 // expression (assuming there are no other breaks,
4952 // this implies that the type of the block will be
4955 // #41425 -- label the implicit `()` as being the
4956 // "found type" here, rather than the "expected type".
4957 if !self.diverges.get().always() {
4958 // #50009 -- Do not point at the entire fn block span, point at the return type
4959 // span, as it is the cause of the requirement, and
4960 // `consider_hint_about_removing_semicolon` will point at the last expression
4961 // if it were a relevant part of the error. This improves usability in editors
4962 // that highlight errors inline.
4963 let mut sp = blk.span;
4964 let mut fn_span = None;
4965 if let Some((decl, ident)) = self.get_parent_fn_decl(blk.hir_id) {
4966 let ret_sp = decl.output.span();
4967 if let Some(block_sp) = self.parent_item_span(blk.hir_id) {
4968 // HACK: on some cases (`ui/liveness/liveness-issue-2163.rs`) the
4969 // output would otherwise be incorrect and even misleading. Make sure
4970 // the span we're aiming at correspond to a `fn` body.
4971 if block_sp == blk.span {
4973 fn_span = Some(ident.span);
4977 coerce.coerce_forced_unit(self, &self.misc(sp), &mut |err| {
4978 if let Some(expected_ty) = expected.only_has_type(self) {
4979 self.consider_hint_about_removing_semicolon(blk, expected_ty, err);
4981 if let Some(fn_span) = fn_span {
4982 err.span_label(fn_span, "this function's body doesn't return");
4990 // If we can break from the block, then the block's exit is always reachable
4991 // (... as long as the entry is reachable) - regardless of the tail of the block.
4992 self.diverges.set(prev_diverges);
4995 let mut ty = ctxt.coerce.unwrap().complete(self);
4997 if self.has_errors.get() || ty.references_error() {
4998 ty = self.tcx.types.err
5001 self.write_ty(blk.hir_id, ty);
5003 *self.ps.borrow_mut() = prev;
5007 fn parent_item_span(&self, id: hir::HirId) -> Option<Span> {
5008 let node = self.tcx.hir().get_by_hir_id(self.tcx.hir().get_parent_item(id));
5010 Node::Item(&hir::Item {
5011 node: hir::ItemKind::Fn(_, _, _, body_id), ..
5013 Node::ImplItem(&hir::ImplItem {
5014 node: hir::ImplItemKind::Method(_, body_id), ..
5016 let body = self.tcx.hir().body(body_id);
5017 if let ExprKind::Block(block, _) = &body.value.node {
5018 return Some(block.span);
5026 /// Given a function block's `HirId`, returns its `FnDecl` if it exists, or `None` otherwise.
5027 fn get_parent_fn_decl(&self, blk_id: hir::HirId) -> Option<(hir::FnDecl, ast::Ident)> {
5028 let parent = self.tcx.hir().get_by_hir_id(self.tcx.hir().get_parent_item(blk_id));
5029 self.get_node_fn_decl(parent).map(|(fn_decl, ident, _)| (fn_decl, ident))
5032 /// Given a function `Node`, return its `FnDecl` if it exists, or `None` otherwise.
5033 fn get_node_fn_decl(&self, node: Node<'_>) -> Option<(hir::FnDecl, ast::Ident, bool)> {
5035 Node::Item(&hir::Item {
5036 ident, node: hir::ItemKind::Fn(ref decl, ..), ..
5037 }) => decl.clone().and_then(|decl| {
5038 // This is less than ideal, it will not suggest a return type span on any
5039 // method called `main`, regardless of whether it is actually the entry point,
5040 // but it will still present it as the reason for the expected type.
5041 Some((decl, ident, ident.name != sym::main))
5043 Node::TraitItem(&hir::TraitItem {
5044 ident, node: hir::TraitItemKind::Method(hir::MethodSig {
5047 }) => decl.clone().and_then(|decl| Some((decl, ident, true))),
5048 Node::ImplItem(&hir::ImplItem {
5049 ident, node: hir::ImplItemKind::Method(hir::MethodSig {
5052 }) => decl.clone().and_then(|decl| Some((decl, ident, false))),
5057 /// Given a `HirId`, return the `FnDecl` of the method it is enclosed by and whether a
5058 /// suggestion can be made, `None` otherwise.
5059 pub fn get_fn_decl(&self, blk_id: hir::HirId) -> Option<(hir::FnDecl, bool)> {
5060 // Get enclosing Fn, if it is a function or a trait method, unless there's a `loop` or
5061 // `while` before reaching it, as block tail returns are not available in them.
5062 self.tcx.hir().get_return_block(blk_id).and_then(|blk_id| {
5063 let parent = self.tcx.hir().get_by_hir_id(blk_id);
5064 self.get_node_fn_decl(parent).map(|(fn_decl, _, is_main)| (fn_decl, is_main))
5068 /// On implicit return expressions with mismatched types, provides the following suggestions:
5070 /// - Points out the method's return type as the reason for the expected type.
5071 /// - Possible missing semicolon.
5072 /// - Possible missing return type if the return type is the default, and not `fn main()`.
5073 pub fn suggest_mismatched_types_on_tail(
5075 err: &mut DiagnosticBuilder<'tcx>,
5076 expression: &'gcx hir::Expr,
5082 self.suggest_missing_semicolon(err, expression, expected, cause_span);
5083 let mut pointing_at_return_type = false;
5084 if let Some((fn_decl, can_suggest)) = self.get_fn_decl(blk_id) {
5085 pointing_at_return_type = self.suggest_missing_return_type(
5086 err, &fn_decl, expected, found, can_suggest);
5088 self.suggest_ref_or_into(err, expression, expected, found);
5089 pointing_at_return_type
5092 pub fn suggest_ref_or_into(
5094 err: &mut DiagnosticBuilder<'tcx>,
5099 if let Some((sp, msg, suggestion)) = self.check_ref(expr, found, expected) {
5100 err.span_suggestion(
5104 Applicability::MachineApplicable,
5106 } else if !self.check_for_cast(err, expr, found, expected) {
5107 let is_struct_pat_shorthand_field = self.is_hir_id_from_struct_pattern_shorthand_field(
5111 let methods = self.get_conversion_methods(expr.span, expected, found);
5112 if let Ok(expr_text) = self.sess().source_map().span_to_snippet(expr.span) {
5113 let mut suggestions = iter::repeat(&expr_text).zip(methods.iter())
5114 .filter_map(|(receiver, method)| {
5115 let method_call = format!(".{}()", method.ident);
5116 if receiver.ends_with(&method_call) {
5117 None // do not suggest code that is already there (#53348)
5119 let method_call_list = [".to_vec()", ".to_string()"];
5120 let sugg = if receiver.ends_with(".clone()")
5121 && method_call_list.contains(&method_call.as_str()) {
5122 let max_len = receiver.rfind(".").unwrap();
5123 format!("{}{}", &receiver[..max_len], method_call)
5125 format!("{}{}", receiver, method_call)
5127 Some(if is_struct_pat_shorthand_field {
5128 format!("{}: {}", receiver, sugg)
5134 if suggestions.peek().is_some() {
5135 err.span_suggestions(
5137 "try using a conversion method",
5139 Applicability::MaybeIncorrect,
5146 /// A common error is to forget to add a semicolon at the end of a block, e.g.,
5150 /// bar_that_returns_u32()
5154 /// This routine checks if the return expression in a block would make sense on its own as a
5155 /// statement and the return type has been left as default or has been specified as `()`. If so,
5156 /// it suggests adding a semicolon.
5157 fn suggest_missing_semicolon(&self,
5158 err: &mut DiagnosticBuilder<'tcx>,
5159 expression: &'gcx hir::Expr,
5162 if expected.is_unit() {
5163 // `BlockTailExpression` only relevant if the tail expr would be
5164 // useful on its own.
5165 match expression.node {
5166 ExprKind::Call(..) |
5167 ExprKind::MethodCall(..) |
5168 ExprKind::While(..) |
5169 ExprKind::Loop(..) |
5170 ExprKind::Match(..) |
5171 ExprKind::Block(..) => {
5172 let sp = self.tcx.sess.source_map().next_point(cause_span);
5173 err.span_suggestion(
5175 "try adding a semicolon",
5177 Applicability::MachineApplicable);
5184 /// A possible error is to forget to add a return type that is needed:
5188 /// bar_that_returns_u32()
5192 /// This routine checks if the return type is left as default, the method is not part of an
5193 /// `impl` block and that it isn't the `main` method. If so, it suggests setting the return
5195 fn suggest_missing_return_type(
5197 err: &mut DiagnosticBuilder<'tcx>,
5198 fn_decl: &hir::FnDecl,
5203 // Only suggest changing the return type for methods that
5204 // haven't set a return type at all (and aren't `fn main()` or an impl).
5205 match (&fn_decl.output, found.is_suggestable(), can_suggest, expected.is_unit()) {
5206 (&hir::FunctionRetTy::DefaultReturn(span), true, true, true) => {
5207 err.span_suggestion(
5209 "try adding a return type",
5210 format!("-> {} ", self.resolve_type_vars_with_obligations(found)),
5211 Applicability::MachineApplicable);
5214 (&hir::FunctionRetTy::DefaultReturn(span), false, true, true) => {
5215 err.span_label(span, "possibly return type missing here?");
5218 (&hir::FunctionRetTy::DefaultReturn(span), _, false, true) => {
5219 // `fn main()` must return `()`, do not suggest changing return type
5220 err.span_label(span, "expected `()` because of default return type");
5223 // expectation was caused by something else, not the default return
5224 (&hir::FunctionRetTy::DefaultReturn(_), _, _, false) => false,
5225 (&hir::FunctionRetTy::Return(ref ty), _, _, _) => {
5226 // Only point to return type if the expected type is the return type, as if they
5227 // are not, the expectation must have been caused by something else.
5228 debug!("suggest_missing_return_type: return type {:?} node {:?}", ty, ty.node);
5230 let ty = AstConv::ast_ty_to_ty(self, ty);
5231 debug!("suggest_missing_return_type: return type {:?}", ty);
5232 debug!("suggest_missing_return_type: expected type {:?}", ty);
5233 if ty.sty == expected.sty {
5234 err.span_label(sp, format!("expected `{}` because of return type",
5243 /// A common error is to add an extra semicolon:
5246 /// fn foo() -> usize {
5251 /// This routine checks if the final statement in a block is an
5252 /// expression with an explicit semicolon whose type is compatible
5253 /// with `expected_ty`. If so, it suggests removing the semicolon.
5254 fn consider_hint_about_removing_semicolon(
5256 blk: &'gcx hir::Block,
5257 expected_ty: Ty<'tcx>,
5258 err: &mut DiagnosticBuilder<'_>,
5260 if let Some(span_semi) = self.could_remove_semicolon(blk, expected_ty) {
5261 err.span_suggestion(
5263 "consider removing this semicolon",
5265 Applicability::MachineApplicable,
5270 fn could_remove_semicolon(
5272 blk: &'gcx hir::Block,
5273 expected_ty: Ty<'tcx>,
5275 // Be helpful when the user wrote `{... expr;}` and
5276 // taking the `;` off is enough to fix the error.
5277 let last_stmt = blk.stmts.last()?;
5278 let last_expr = match last_stmt.node {
5279 hir::StmtKind::Semi(ref e) => e,
5282 let last_expr_ty = self.node_ty(last_expr.hir_id);
5283 if self.can_sub(self.param_env, last_expr_ty, expected_ty).is_err() {
5286 let original_span = original_sp(last_stmt.span, blk.span);
5287 Some(original_span.with_lo(original_span.hi() - BytePos(1)))
5290 // Rewrite `SelfCtor` to `Ctor`
5291 pub fn rewrite_self_ctor(
5295 ) -> Result<Res, ErrorReported> {
5297 if let Res::SelfCtor(impl_def_id) = res {
5298 let ty = self.impl_self_ty(span, impl_def_id).ty;
5299 let adt_def = ty.ty_adt_def();
5302 Some(adt_def) if adt_def.has_ctor() => {
5303 let variant = adt_def.non_enum_variant();
5304 let ctor_def_id = variant.ctor_def_id.unwrap();
5305 Ok(Res::Def(DefKind::Ctor(CtorOf::Struct, variant.ctor_kind), ctor_def_id))
5308 let mut err = tcx.sess.struct_span_err(span,
5309 "the `Self` constructor can only be used with tuple or unit structs");
5310 if let Some(adt_def) = adt_def {
5311 match adt_def.adt_kind() {
5313 err.help("did you mean to use one of the enum's variants?");
5317 err.span_suggestion(
5319 "use curly brackets",
5320 String::from("Self { /* fields */ }"),
5321 Applicability::HasPlaceholders,
5336 // Instantiates the given path, which must refer to an item with the given
5337 // number of type parameters and type.
5338 pub fn instantiate_value_path(&self,
5339 segments: &[hir::PathSegment],
5340 self_ty: Option<Ty<'tcx>>,
5344 -> (Ty<'tcx>, Res) {
5346 "instantiate_value_path(segments={:?}, self_ty={:?}, res={:?}, hir_id={})",
5355 let res = match self.rewrite_self_ctor(res, span) {
5357 Err(ErrorReported) => return (tcx.types.err, res),
5359 let path_segs = match res {
5360 Res::Local(_) => vec![],
5361 Res::Def(kind, def_id) =>
5362 AstConv::def_ids_for_value_path_segments(self, segments, self_ty, kind, def_id),
5363 _ => bug!("instantiate_value_path on {:?}", res),
5366 let mut user_self_ty = None;
5367 let mut is_alias_variant_ctor = false;
5369 Res::Def(DefKind::Ctor(CtorOf::Variant, _), _) => {
5370 if let Some(self_ty) = self_ty {
5371 let adt_def = self_ty.ty_adt_def().unwrap();
5372 user_self_ty = Some(UserSelfTy {
5373 impl_def_id: adt_def.did,
5376 is_alias_variant_ctor = true;
5379 Res::Def(DefKind::Method, def_id)
5380 | Res::Def(DefKind::AssocConst, def_id) => {
5381 let container = tcx.associated_item(def_id).container;
5382 debug!("instantiate_value_path: def_id={:?} container={:?}", def_id, container);
5384 ty::TraitContainer(trait_did) => {
5385 callee::check_legal_trait_for_method_call(tcx, span, trait_did)
5387 ty::ImplContainer(impl_def_id) => {
5388 if segments.len() == 1 {
5389 // `<T>::assoc` will end up here, and so
5390 // can `T::assoc`. It this came from an
5391 // inherent impl, we need to record the
5392 // `T` for posterity (see `UserSelfTy` for
5394 let self_ty = self_ty.expect("UFCS sugared assoc missing Self");
5395 user_self_ty = Some(UserSelfTy {
5406 // Now that we have categorized what space the parameters for each
5407 // segment belong to, let's sort out the parameters that the user
5408 // provided (if any) into their appropriate spaces. We'll also report
5409 // errors if type parameters are provided in an inappropriate place.
5411 let generic_segs: FxHashSet<_> = path_segs.iter().map(|PathSeg(_, index)| index).collect();
5412 let generics_has_err = AstConv::prohibit_generics(
5413 self, segments.iter().enumerate().filter_map(|(index, seg)| {
5414 if !generic_segs.contains(&index) || is_alias_variant_ctor {
5421 if let Res::Local(hid) = res {
5422 let ty = self.local_ty(span, hid).decl_ty;
5423 let ty = self.normalize_associated_types_in(span, &ty);
5424 self.write_ty(hir_id, ty);
5428 if generics_has_err {
5429 // Don't try to infer type parameters when prohibited generic arguments were given.
5430 user_self_ty = None;
5433 // Now we have to compare the types that the user *actually*
5434 // provided against the types that were *expected*. If the user
5435 // did not provide any types, then we want to substitute inference
5436 // variables. If the user provided some types, we may still need
5437 // to add defaults. If the user provided *too many* types, that's
5440 let mut infer_args_for_err = FxHashSet::default();
5441 for &PathSeg(def_id, index) in &path_segs {
5442 let seg = &segments[index];
5443 let generics = tcx.generics_of(def_id);
5444 // Argument-position `impl Trait` is treated as a normal generic
5445 // parameter internally, but we don't allow users to specify the
5446 // parameter's value explicitly, so we have to do some error-
5448 let suppress_errors = AstConv::check_generic_arg_count_for_call(
5453 false, // `is_method_call`
5455 if suppress_errors {
5456 infer_args_for_err.insert(index);
5457 self.set_tainted_by_errors(); // See issue #53251.
5461 let has_self = path_segs.last().map(|PathSeg(def_id, _)| {
5462 tcx.generics_of(*def_id).has_self
5463 }).unwrap_or(false);
5465 let def_id = res.def_id();
5467 // The things we are substituting into the type should not contain
5468 // escaping late-bound regions, and nor should the base type scheme.
5469 let ty = tcx.type_of(def_id);
5471 let substs = AstConv::create_substs_for_generic_args(
5477 // Provide the generic args, and whether types should be inferred.
5479 if let Some(&PathSeg(_, index)) = path_segs.iter().find(|&PathSeg(did, _)| {
5482 // If we've encountered an `impl Trait`-related error, we're just
5483 // going to infer the arguments for better error messages.
5484 if !infer_args_for_err.contains(&index) {
5485 // Check whether the user has provided generic arguments.
5486 if let Some(ref data) = segments[index].args {
5487 return (Some(data), segments[index].infer_args);
5490 return (None, segments[index].infer_args);
5495 // Provide substitutions for parameters for which (valid) arguments have been provided.
5497 match (¶m.kind, arg) {
5498 (GenericParamDefKind::Lifetime, GenericArg::Lifetime(lt)) => {
5499 AstConv::ast_region_to_region(self, lt, Some(param)).into()
5501 (GenericParamDefKind::Type { .. }, GenericArg::Type(ty)) => {
5502 self.to_ty(ty).into()
5504 (GenericParamDefKind::Const, GenericArg::Const(ct)) => {
5505 self.to_const(&ct.value, self.tcx.type_of(param.def_id)).into()
5507 _ => unreachable!(),
5510 // Provide substitutions for parameters for which arguments are inferred.
5511 |substs, param, infer_args| {
5513 GenericParamDefKind::Lifetime => {
5514 self.re_infer(Some(param), span).unwrap().into()
5516 GenericParamDefKind::Type { has_default, .. } => {
5517 if !infer_args && has_default {
5518 // If we have a default, then we it doesn't matter that we're not
5519 // inferring the type arguments: we provide the default where any
5521 let default = tcx.type_of(param.def_id);
5524 default.subst_spanned(tcx, substs.unwrap(), Some(span))
5527 // If no type arguments were provided, we have to infer them.
5528 // This case also occurs as a result of some malformed input, e.g.
5529 // a lifetime argument being given instead of a type parameter.
5530 // Using inference instead of `Error` gives better error messages.
5531 self.var_for_def(span, param)
5534 GenericParamDefKind::Const => {
5535 // FIXME(const_generics:defaults)
5536 // No const parameters were provided, we have to infer them.
5537 self.var_for_def(span, param)
5542 assert!(!substs.has_escaping_bound_vars());
5543 assert!(!ty.has_escaping_bound_vars());
5545 // First, store the "user substs" for later.
5546 self.write_user_type_annotation_from_substs(hir_id, def_id, substs, user_self_ty);
5548 // Add all the obligations that are required, substituting and
5549 // normalized appropriately.
5550 let bounds = self.instantiate_bounds(span, def_id, &substs);
5551 self.add_obligations_for_parameters(
5552 traits::ObligationCause::new(span, self.body_id, traits::ItemObligation(def_id)),
5555 // Substitute the values for the type parameters into the type of
5556 // the referenced item.
5557 let ty_substituted = self.instantiate_type_scheme(span, &substs, &ty);
5559 if let Some(UserSelfTy { impl_def_id, self_ty }) = user_self_ty {
5560 // In the case of `Foo<T>::method` and `<Foo<T>>::method`, if `method`
5561 // is inherent, there is no `Self` parameter; instead, the impl needs
5562 // type parameters, which we can infer by unifying the provided `Self`
5563 // with the substituted impl type.
5564 // This also occurs for an enum variant on a type alias.
5565 let ty = tcx.type_of(impl_def_id);
5567 let impl_ty = self.instantiate_type_scheme(span, &substs, &ty);
5568 match self.at(&self.misc(span), self.param_env).sup(impl_ty, self_ty) {
5569 Ok(ok) => self.register_infer_ok_obligations(ok),
5571 self.tcx.sess.delay_span_bug(span, &format!(
5572 "instantiate_value_path: (UFCS) {:?} was a subtype of {:?} but now is not?",
5580 self.check_rustc_args_require_const(def_id, hir_id, span);
5582 debug!("instantiate_value_path: type of {:?} is {:?}",
5585 self.write_substs(hir_id, substs);
5587 (ty_substituted, res)
5590 fn check_rustc_args_require_const(&self,
5594 // We're only interested in functions tagged with
5595 // #[rustc_args_required_const], so ignore anything that's not.
5596 if !self.tcx.has_attr(def_id, sym::rustc_args_required_const) {
5600 // If our calling expression is indeed the function itself, we're good!
5601 // If not, generate an error that this can only be called directly.
5602 if let Node::Expr(expr) = self.tcx.hir().get_by_hir_id(
5603 self.tcx.hir().get_parent_node_by_hir_id(hir_id))
5605 if let ExprKind::Call(ref callee, ..) = expr.node {
5606 if callee.hir_id == hir_id {
5612 self.tcx.sess.span_err(span, "this function can only be invoked \
5613 directly, not through a function pointer");
5616 // Resolves `typ` by a single level if `typ` is a type variable.
5617 // If no resolution is possible, then an error is reported.
5618 // Numeric inference variables may be left unresolved.
5619 pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
5620 let ty = self.resolve_type_vars_with_obligations(ty);
5621 if !ty.is_ty_var() {
5624 if !self.is_tainted_by_errors() {
5625 self.need_type_info_err((**self).body_id, sp, ty)
5626 .note("type must be known at this point")
5629 self.demand_suptype(sp, self.tcx.types.err, ty);
5634 fn with_breakable_ctxt<F: FnOnce() -> R, R>(&self, id: hir::HirId,
5635 ctxt: BreakableCtxt<'gcx, 'tcx>, f: F)
5636 -> (BreakableCtxt<'gcx, 'tcx>, R) {
5639 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5640 index = enclosing_breakables.stack.len();
5641 enclosing_breakables.by_id.insert(id, index);
5642 enclosing_breakables.stack.push(ctxt);
5646 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5647 debug_assert!(enclosing_breakables.stack.len() == index + 1);
5648 enclosing_breakables.by_id.remove(&id).expect("missing breakable context");
5649 enclosing_breakables.stack.pop().expect("missing breakable context")
5654 /// Instantiate a QueryResponse in a probe context, without a
5655 /// good ObligationCause.
5656 fn probe_instantiate_query_response(
5659 original_values: &OriginalQueryValues<'tcx>,
5660 query_result: &Canonical<'tcx, QueryResponse<'tcx, Ty<'tcx>>>,
5661 ) -> InferResult<'tcx, Ty<'tcx>>
5663 self.instantiate_query_response_and_region_obligations(
5664 &traits::ObligationCause::misc(span, self.body_id),
5670 /// Returns `true` if an expression is contained inside the LHS of an assignment expression.
5671 fn expr_in_place(&self, mut expr_id: hir::HirId) -> bool {
5672 let mut contained_in_place = false;
5674 while let hir::Node::Expr(parent_expr) =
5675 self.tcx.hir().get_by_hir_id(self.tcx.hir().get_parent_node_by_hir_id(expr_id))
5677 match &parent_expr.node {
5678 hir::ExprKind::Assign(lhs, ..) | hir::ExprKind::AssignOp(_, lhs, ..) => {
5679 if lhs.hir_id == expr_id {
5680 contained_in_place = true;
5686 expr_id = parent_expr.hir_id;
5693 pub fn check_bounds_are_used<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
5694 generics: &ty::Generics,
5696 let own_counts = generics.own_counts();
5698 "check_bounds_are_used(n_tys={}, n_cts={}, ty={:?})",
5704 if own_counts.types == 0 {
5708 // Make a vector of booleans initially false, set to true when used.
5709 let mut types_used = vec![false; own_counts.types];
5711 for leaf_ty in ty.walk() {
5712 if let ty::Param(ty::ParamTy { index, .. }) = leaf_ty.sty {
5713 debug!("Found use of ty param num {}", index);
5714 types_used[index as usize - own_counts.lifetimes] = true;
5715 } else if let ty::Error = leaf_ty.sty {
5716 // If there is already another error, do not emit
5717 // an error for not using a type Parameter.
5718 assert!(tcx.sess.err_count() > 0);
5723 let types = generics.params.iter().filter(|param| match param.kind {
5724 ty::GenericParamDefKind::Type { .. } => true,
5727 for (&used, param) in types_used.iter().zip(types) {
5729 let id = tcx.hir().as_local_hir_id(param.def_id).unwrap();
5730 let span = tcx.hir().span_by_hir_id(id);
5731 struct_span_err!(tcx.sess, span, E0091, "type parameter `{}` is unused", param.name)
5732 .span_label(span, "unused type parameter")
5738 fn fatally_break_rust(sess: &Session) {
5739 let handler = sess.diagnostic();
5740 handler.span_bug_no_panic(
5742 "It looks like you're trying to break rust; would you like some ICE?",
5744 handler.note_without_error("the compiler expectedly panicked. this is a feature.");
5745 handler.note_without_error(
5746 "we would appreciate a joke overview: \
5747 https://github.com/rust-lang/rust/issues/43162#issuecomment-320764675"
5749 handler.note_without_error(&format!("rustc {} running on {}",
5750 option_env!("CFG_VERSION").unwrap_or("unknown_version"),
5751 crate::session::config::host_triple(),
5755 fn potentially_plural_count(count: usize, word: &str) -> String {
5756 format!("{} {}{}", count, word, if count == 1 { "" } else { "s" })