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, 'tcx: 'a> {
198 infcx: InferCtxt<'a, '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<'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, 'tcx> Deref for Inherited<'a, 'tcx> {
241 type Target = InferCtxt<'a, '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, '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, '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, '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, '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, '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, '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, '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<'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<'tcx>>,
502 pub struct EnclosingBreakables<'tcx> {
503 stack: Vec<BreakableCtxt<'tcx>>,
504 by_id: HirIdMap<usize>,
507 impl<'tcx> EnclosingBreakables<'tcx> {
508 fn find_breakable(&mut self, target_id: hir::HirId) -> &mut BreakableCtxt<'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, '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<'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<'tcx>>,
578 inh: &'a Inherited<'a, 'tcx>,
581 impl<'a, 'tcx> Deref for FnCtxt<'a, 'tcx> {
582 type Target = Inherited<'a, '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 'tcx FnOnce(Inherited<'b, 'tcx>)`.
591 pub struct InheritedBuilder<'tcx> {
592 infcx: infer::InferCtxtBuilder<'tcx>,
596 impl Inherited<'_, 'tcx> {
597 pub fn build(tcx: TyCtxt<'tcx>, def_id: DefId) -> InheritedBuilder<'tcx> {
598 let hir_id_root = if def_id.is_local() {
599 let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
600 DefId::local(hir_id.owner)
606 infcx: tcx.infer_ctxt().with_fresh_in_progress_tables(hir_id_root),
612 impl<'tcx> InheritedBuilder<'tcx> {
613 fn enter<F, R>(&mut self, f: F) -> R
615 F: for<'a> FnOnce(Inherited<'a, 'tcx>) -> R,
617 let def_id = self.def_id;
618 self.infcx.enter(|infcx| f(Inherited::new(infcx, def_id)))
622 impl Inherited<'a, 'tcx> {
623 fn new(infcx: InferCtxt<'a, '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<'tcx> {
692 impl ItemLikeVisitor<'tcx> for CheckItemTypesVisitor<'tcx> {
693 fn visit_item(&mut self, i: &'tcx hir::Item) {
694 check_item_type(self.tcx, i);
696 fn visit_trait_item(&mut self, _: &'tcx hir::TraitItem) { }
697 fn visit_impl_item(&mut self, _: &'tcx hir::ImplItem) { }
700 pub fn check_wf_new<'tcx>(tcx: TyCtxt<'tcx>) -> Result<(), ErrorReported> {
701 tcx.sess.track_errors(|| {
702 let mut visit = wfcheck::CheckTypeWellFormedVisitor::new(tcx);
703 tcx.hir().krate().par_visit_all_item_likes(&mut visit);
707 fn check_mod_item_types<'tcx>(tcx: TyCtxt<'tcx>, module_def_id: DefId) {
708 tcx.hir().visit_item_likes_in_module(module_def_id, &mut CheckItemTypesVisitor { tcx });
711 fn typeck_item_bodies<'tcx>(tcx: TyCtxt<'tcx>, crate_num: CrateNum) {
712 debug_assert!(crate_num == LOCAL_CRATE);
713 tcx.par_body_owners(|body_owner_def_id| {
714 tcx.ensure().typeck_tables_of(body_owner_def_id);
718 fn check_item_well_formed<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) {
719 wfcheck::check_item_well_formed(tcx, def_id);
722 fn check_trait_item_well_formed<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) {
723 wfcheck::check_trait_item(tcx, def_id);
726 fn check_impl_item_well_formed<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) {
727 wfcheck::check_impl_item(tcx, def_id);
730 pub fn provide(providers: &mut Providers<'_>) {
731 method::provide(providers);
732 *providers = Providers {
738 check_item_well_formed,
739 check_trait_item_well_formed,
740 check_impl_item_well_formed,
741 check_mod_item_types,
746 fn adt_destructor<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) -> 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<'tcx>(
762 ) -> 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<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) -> bool {
801 // Closures' tables come from their outermost function,
802 // as they are part of the same "inference environment".
803 let outer_def_id = tcx.closure_base_def_id(def_id);
804 if outer_def_id != def_id {
805 return tcx.has_typeck_tables(outer_def_id);
808 let id = tcx.hir().as_local_hir_id(def_id).unwrap();
809 primary_body_of(tcx, id).is_some()
812 fn used_trait_imports<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) -> &'tcx DefIdSet {
813 &*tcx.typeck_tables_of(def_id).used_trait_imports
816 fn typeck_tables_of<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId) -> &'tcx ty::TypeckTables<'tcx> {
817 // Closures' tables come from their outermost function,
818 // as they are part of the same "inference environment".
819 let outer_def_id = tcx.closure_base_def_id(def_id);
820 if outer_def_id != def_id {
821 return tcx.typeck_tables_of(outer_def_id);
824 let id = tcx.hir().as_local_hir_id(def_id).unwrap();
825 let span = tcx.hir().span_by_hir_id(id);
827 // Figure out what primary body this item has.
828 let (body_id, fn_decl) = primary_body_of(tcx, id).unwrap_or_else(|| {
829 span_bug!(span, "can't type-check body of {:?}", def_id);
831 let body = tcx.hir().body(body_id);
833 let tables = Inherited::build(tcx, def_id).enter(|inh| {
834 let param_env = tcx.param_env(def_id);
835 let fcx = if let Some(decl) = fn_decl {
836 let fn_sig = tcx.fn_sig(def_id);
838 check_abi(tcx, span, fn_sig.abi());
840 // Compute the fty from point of view of inside the fn.
842 tcx.liberate_late_bound_regions(def_id, &fn_sig);
844 inh.normalize_associated_types_in(body.value.span,
849 let fcx = check_fn(&inh, param_env, fn_sig, decl, id, body, None).0;
852 let fcx = FnCtxt::new(&inh, param_env, body.value.hir_id);
853 let expected_type = tcx.type_of(def_id);
854 let expected_type = fcx.normalize_associated_types_in(body.value.span, &expected_type);
855 fcx.require_type_is_sized(expected_type, body.value.span, traits::ConstSized);
857 let revealed_ty = if tcx.features().impl_trait_in_bindings {
858 fcx.instantiate_opaque_types_from_value(
866 // Gather locals in statics (because of block expressions).
867 GatherLocalsVisitor { fcx: &fcx, parent_id: id, }.visit_body(body);
869 fcx.check_expr_coercable_to_type(&body.value, revealed_ty);
871 fcx.write_ty(id, revealed_ty);
876 // All type checking constraints were added, try to fallback unsolved variables.
877 fcx.select_obligations_where_possible(false);
878 let mut fallback_has_occurred = false;
879 for ty in &fcx.unsolved_variables() {
880 fallback_has_occurred |= fcx.fallback_if_possible(ty);
882 fcx.select_obligations_where_possible(fallback_has_occurred);
884 // Even though coercion casts provide type hints, we check casts after fallback for
885 // backwards compatibility. This makes fallback a stronger type hint than a cast coercion.
888 // Closure and generator analysis may run after fallback
889 // because they don't constrain other type variables.
890 fcx.closure_analyze(body);
891 assert!(fcx.deferred_call_resolutions.borrow().is_empty());
892 fcx.resolve_generator_interiors(def_id);
894 for (ty, span, code) in fcx.deferred_sized_obligations.borrow_mut().drain(..) {
895 let ty = fcx.normalize_ty(span, ty);
896 fcx.require_type_is_sized(ty, span, code);
898 fcx.select_all_obligations_or_error();
900 if fn_decl.is_some() {
901 fcx.regionck_fn(id, body);
903 fcx.regionck_expr(body);
906 fcx.resolve_type_vars_in_body(body)
909 // Consistency check our TypeckTables instance can hold all ItemLocalIds
910 // it will need to hold.
911 assert_eq!(tables.local_id_root, Some(DefId::local(id.owner)));
916 fn check_abi<'tcx>(tcx: TyCtxt<'tcx>, span: Span, abi: Abi) {
917 if !tcx.sess.target.target.is_abi_supported(abi) {
918 struct_span_err!(tcx.sess, span, E0570,
919 "The ABI `{}` is not supported for the current target", abi).emit()
923 struct GatherLocalsVisitor<'a, 'tcx: 'a> {
924 fcx: &'a FnCtxt<'a, 'tcx>,
925 parent_id: hir::HirId,
928 impl<'a, 'tcx> GatherLocalsVisitor<'a, 'tcx> {
929 fn assign(&mut self, span: Span, nid: hir::HirId, ty_opt: Option<LocalTy<'tcx>>) -> Ty<'tcx> {
932 // infer the variable's type
933 let var_ty = self.fcx.next_ty_var(TypeVariableOrigin {
934 kind: TypeVariableOriginKind::TypeInference,
937 self.fcx.locals.borrow_mut().insert(nid, LocalTy {
944 // take type that the user specified
945 self.fcx.locals.borrow_mut().insert(nid, typ);
952 impl<'a, 'tcx> Visitor<'tcx> for GatherLocalsVisitor<'a, 'tcx> {
953 fn nested_visit_map<'this>(&'this mut self) -> NestedVisitorMap<'this, 'tcx> {
954 NestedVisitorMap::None
957 // Add explicitly-declared locals.
958 fn visit_local(&mut self, local: &'tcx hir::Local) {
959 let local_ty = match local.ty {
961 let o_ty = self.fcx.to_ty(&ty);
963 let revealed_ty = if self.fcx.tcx.features().impl_trait_in_bindings {
964 self.fcx.instantiate_opaque_types_from_value(
972 let c_ty = self.fcx.inh.infcx.canonicalize_user_type_annotation(
973 &UserType::Ty(revealed_ty)
975 debug!("visit_local: ty.hir_id={:?} o_ty={:?} revealed_ty={:?} c_ty={:?}",
976 ty.hir_id, o_ty, revealed_ty, c_ty);
977 self.fcx.tables.borrow_mut().user_provided_types_mut().insert(ty.hir_id, c_ty);
979 Some(LocalTy { decl_ty: o_ty, revealed_ty })
983 self.assign(local.span, local.hir_id, local_ty);
985 debug!("Local variable {:?} is assigned type {}",
987 self.fcx.ty_to_string(
988 self.fcx.locals.borrow().get(&local.hir_id).unwrap().clone().decl_ty));
989 intravisit::walk_local(self, local);
992 // Add pattern bindings.
993 fn visit_pat(&mut self, p: &'tcx hir::Pat) {
994 if let PatKind::Binding(_, _, ident, _) = p.node {
995 let var_ty = self.assign(p.span, p.hir_id, None);
997 let node_id = self.fcx.tcx.hir().hir_to_node_id(p.hir_id);
998 if !self.fcx.tcx.features().unsized_locals {
999 self.fcx.require_type_is_sized(var_ty, p.span,
1000 traits::VariableType(node_id));
1003 debug!("Pattern binding {} is assigned to {} with type {:?}",
1005 self.fcx.ty_to_string(
1006 self.fcx.locals.borrow().get(&p.hir_id).unwrap().clone().decl_ty),
1009 intravisit::walk_pat(self, p);
1012 // Don't descend into the bodies of nested closures
1015 _: intravisit::FnKind<'tcx>,
1016 _: &'tcx hir::FnDecl,
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, 'tcx>(
1044 inherited: &'a Inherited<'a, 'tcx>,
1045 param_env: ty::ParamEnv<'tcx>,
1046 fn_sig: ty::FnSig<'tcx>,
1047 decl: &'tcx hir::FnDecl,
1049 body: &'tcx hir::Body,
1050 can_be_generator: Option<hir::GeneratorMovability>,
1051 ) -> (FnCtxt<'a, '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<'tcx>(tcx: TyCtxt<'tcx>, id: hir::HirId, span: Span) {
1291 let def_id = tcx.hir().local_def_id_from_hir_id(id);
1292 let def = tcx.adt_def(def_id);
1293 def.destructor(tcx); // force the destructor to be evaluated
1294 check_representable(tcx, span, def_id);
1296 if def.repr.simd() {
1297 check_simd(tcx, span, def_id);
1300 check_transparent(tcx, span, def_id);
1301 check_packed(tcx, span, def_id);
1304 fn check_union<'tcx>(tcx: TyCtxt<'tcx>, id: hir::HirId, span: Span) {
1305 let def_id = tcx.hir().local_def_id_from_hir_id(id);
1306 let def = tcx.adt_def(def_id);
1307 def.destructor(tcx); // force the destructor to be evaluated
1308 check_representable(tcx, span, def_id);
1309 check_transparent(tcx, span, def_id);
1310 check_packed(tcx, span, def_id);
1313 fn check_opaque<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId, substs: SubstsRef<'tcx>, span: Span) {
1314 if let Err(partially_expanded_type) = tcx.try_expand_impl_trait_type(def_id, substs) {
1315 let mut err = struct_span_err!(
1316 tcx.sess, span, E0720,
1317 "opaque type expands to a recursive type",
1319 err.span_label(span, "expands to self-referential type");
1320 if let ty::Opaque(..) = partially_expanded_type.sty {
1321 err.note("type resolves to itself");
1323 err.note(&format!("expanded type is `{}`", partially_expanded_type));
1329 pub fn check_item_type<'tcx>(tcx: TyCtxt<'tcx>, it: &'tcx hir::Item) {
1331 "check_item_type(it.hir_id={}, it.name={})",
1333 tcx.def_path_str(tcx.hir().local_def_id_from_hir_id(it.hir_id))
1335 let _indenter = indenter();
1337 // Consts can play a role in type-checking, so they are included here.
1338 hir::ItemKind::Static(..) => {
1339 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1340 tcx.typeck_tables_of(def_id);
1341 maybe_check_static_with_link_section(tcx, def_id, it.span);
1343 hir::ItemKind::Const(..) => {
1344 tcx.typeck_tables_of(tcx.hir().local_def_id_from_hir_id(it.hir_id));
1346 hir::ItemKind::Enum(ref enum_definition, _) => {
1347 check_enum(tcx, it.span, &enum_definition.variants, it.hir_id);
1349 hir::ItemKind::Fn(..) => {} // entirely within check_item_body
1350 hir::ItemKind::Impl(.., ref impl_item_refs) => {
1351 debug!("ItemKind::Impl {} with id {}", it.ident, it.hir_id);
1352 let impl_def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1353 if let Some(impl_trait_ref) = tcx.impl_trait_ref(impl_def_id) {
1354 check_impl_items_against_trait(
1361 let trait_def_id = impl_trait_ref.def_id;
1362 check_on_unimplemented(tcx, trait_def_id, it);
1365 hir::ItemKind::Trait(..) => {
1366 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1367 check_on_unimplemented(tcx, def_id, it);
1369 hir::ItemKind::Struct(..) => {
1370 check_struct(tcx, it.hir_id, it.span);
1372 hir::ItemKind::Union(..) => {
1373 check_union(tcx, it.hir_id, it.span);
1375 hir::ItemKind::Existential(..) => {
1376 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1378 let substs = InternalSubsts::identity_for_item(tcx, def_id);
1379 check_opaque(tcx, def_id, substs, it.span);
1381 hir::ItemKind::Ty(..) => {
1382 let def_id = tcx.hir().local_def_id_from_hir_id(it.hir_id);
1383 let pty_ty = tcx.type_of(def_id);
1384 let generics = tcx.generics_of(def_id);
1385 check_bounds_are_used(tcx, &generics, pty_ty);
1387 hir::ItemKind::ForeignMod(ref m) => {
1388 check_abi(tcx, it.span, m.abi);
1390 if m.abi == Abi::RustIntrinsic {
1391 for item in &m.items {
1392 intrinsic::check_intrinsic_type(tcx, item);
1394 } else if m.abi == Abi::PlatformIntrinsic {
1395 for item in &m.items {
1396 intrinsic::check_platform_intrinsic_type(tcx, item);
1399 for item in &m.items {
1400 let generics = tcx.generics_of(tcx.hir().local_def_id_from_hir_id(item.hir_id));
1401 if generics.params.len() - generics.own_counts().lifetimes != 0 {
1402 let mut err = struct_span_err!(
1406 "foreign items may not have type parameters"
1408 err.span_label(item.span, "can't have type parameters");
1409 // FIXME: once we start storing spans for type arguments, turn this into a
1412 "use specialization instead of type parameters by replacing them \
1413 with concrete types like `u32`",
1418 if let hir::ForeignItemKind::Fn(ref fn_decl, _, _) = item.node {
1419 require_c_abi_if_c_variadic(tcx, fn_decl, m.abi, item.span);
1424 _ => { /* nothing to do */ }
1428 fn maybe_check_static_with_link_section(tcx: TyCtxt<'_>, id: DefId, span: Span) {
1429 // Only restricted on wasm32 target for now
1430 if !tcx.sess.opts.target_triple.triple().starts_with("wasm32") {
1434 // If `#[link_section]` is missing, then nothing to verify
1435 let attrs = tcx.codegen_fn_attrs(id);
1436 if attrs.link_section.is_none() {
1440 // For the wasm32 target statics with #[link_section] are placed into custom
1441 // sections of the final output file, but this isn't link custom sections of
1442 // other executable formats. Namely we can only embed a list of bytes,
1443 // nothing with pointers to anything else or relocations. If any relocation
1444 // show up, reject them here.
1445 let instance = ty::Instance::mono(tcx, id);
1446 let cid = GlobalId {
1450 let param_env = ty::ParamEnv::reveal_all();
1451 if let Ok(static_) = tcx.const_eval(param_env.and(cid)) {
1452 let alloc = if let ConstValue::ByRef(_, allocation) = static_.val {
1455 bug!("Matching on non-ByRef static")
1457 if alloc.relocations.len() != 0 {
1458 let msg = "statics with a custom `#[link_section]` must be a \
1459 simple list of bytes on the wasm target with no \
1460 extra levels of indirection such as references";
1461 tcx.sess.span_err(span, msg);
1466 fn check_on_unimplemented<'tcx>(tcx: TyCtxt<'tcx>, trait_def_id: DefId, item: &hir::Item) {
1467 let item_def_id = tcx.hir().local_def_id_from_hir_id(item.hir_id);
1468 // an error would be reported if this fails.
1469 let _ = traits::OnUnimplementedDirective::of_item(tcx, trait_def_id, item_def_id);
1472 fn report_forbidden_specialization<'tcx>(
1474 impl_item: &hir::ImplItem,
1477 let mut err = struct_span_err!(
1478 tcx.sess, impl_item.span, E0520,
1479 "`{}` specializes an item from a parent `impl`, but \
1480 that item is not marked `default`",
1482 err.span_label(impl_item.span, format!("cannot specialize default item `{}`",
1485 match tcx.span_of_impl(parent_impl) {
1487 err.span_label(span, "parent `impl` is here");
1488 err.note(&format!("to specialize, `{}` in the parent `impl` must be marked `default`",
1492 err.note(&format!("parent implementation is in crate `{}`", cname));
1499 fn check_specialization_validity<'tcx>(
1501 trait_def: &ty::TraitDef,
1502 trait_item: &ty::AssocItem,
1504 impl_item: &hir::ImplItem,
1506 let ancestors = trait_def.ancestors(tcx, impl_id);
1508 let kind = match impl_item.node {
1509 hir::ImplItemKind::Const(..) => ty::AssocKind::Const,
1510 hir::ImplItemKind::Method(..) => ty::AssocKind::Method,
1511 hir::ImplItemKind::Existential(..) => ty::AssocKind::Existential,
1512 hir::ImplItemKind::Type(_) => ty::AssocKind::Type
1515 let parent = ancestors.defs(tcx, trait_item.ident, kind, trait_def.def_id).nth(1)
1516 .map(|node_item| node_item.map(|parent| parent.defaultness));
1518 if let Some(parent) = parent {
1519 if tcx.impl_item_is_final(&parent) {
1520 report_forbidden_specialization(tcx, impl_item, parent.node.def_id());
1526 fn check_impl_items_against_trait<'tcx>(
1530 impl_trait_ref: ty::TraitRef<'tcx>,
1531 impl_item_refs: &[hir::ImplItemRef],
1533 let impl_span = tcx.sess.source_map().def_span(impl_span);
1535 // If the trait reference itself is erroneous (so the compilation is going
1536 // to fail), skip checking the items here -- the `impl_item` table in `tcx`
1537 // isn't populated for such impls.
1538 if impl_trait_ref.references_error() { return; }
1540 // Locate trait definition and items
1541 let trait_def = tcx.trait_def(impl_trait_ref.def_id);
1542 let mut overridden_associated_type = None;
1544 let impl_items = || impl_item_refs.iter().map(|iiref| tcx.hir().impl_item(iiref.id));
1546 // Check existing impl methods to see if they are both present in trait
1547 // and compatible with trait signature
1548 for impl_item in impl_items() {
1549 let ty_impl_item = tcx.associated_item(
1550 tcx.hir().local_def_id_from_hir_id(impl_item.hir_id));
1551 let ty_trait_item = tcx.associated_items(impl_trait_ref.def_id)
1552 .find(|ac| Namespace::from(&impl_item.node) == Namespace::from(ac.kind) &&
1553 tcx.hygienic_eq(ty_impl_item.ident, ac.ident, impl_trait_ref.def_id))
1555 // Not compatible, but needed for the error message
1556 tcx.associated_items(impl_trait_ref.def_id)
1557 .find(|ac| tcx.hygienic_eq(ty_impl_item.ident, ac.ident, impl_trait_ref.def_id))
1560 // Check that impl definition matches trait definition
1561 if let Some(ty_trait_item) = ty_trait_item {
1562 match impl_item.node {
1563 hir::ImplItemKind::Const(..) => {
1564 // Find associated const definition.
1565 if ty_trait_item.kind == ty::AssocKind::Const {
1566 compare_const_impl(tcx,
1572 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0323,
1573 "item `{}` is an associated const, \
1574 which doesn't match its trait `{}`",
1577 err.span_label(impl_item.span, "does not match trait");
1578 // We can only get the spans from local trait definition
1579 // Same for E0324 and E0325
1580 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
1581 err.span_label(trait_span, "item in trait");
1586 hir::ImplItemKind::Method(..) => {
1587 let trait_span = tcx.hir().span_if_local(ty_trait_item.def_id);
1588 if ty_trait_item.kind == ty::AssocKind::Method {
1589 compare_impl_method(tcx,
1596 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0324,
1597 "item `{}` is an associated method, \
1598 which doesn't match its trait `{}`",
1601 err.span_label(impl_item.span, "does not match trait");
1602 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
1603 err.span_label(trait_span, "item in trait");
1608 hir::ImplItemKind::Existential(..) |
1609 hir::ImplItemKind::Type(_) => {
1610 if ty_trait_item.kind == ty::AssocKind::Type {
1611 if ty_trait_item.defaultness.has_value() {
1612 overridden_associated_type = Some(impl_item);
1615 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0325,
1616 "item `{}` is an associated type, \
1617 which doesn't match its trait `{}`",
1620 err.span_label(impl_item.span, "does not match trait");
1621 if let Some(trait_span) = tcx.hir().span_if_local(ty_trait_item.def_id) {
1622 err.span_label(trait_span, "item in trait");
1629 check_specialization_validity(tcx, trait_def, &ty_trait_item, impl_id, impl_item);
1633 // Check for missing items from trait
1634 let mut missing_items = Vec::new();
1635 let mut invalidated_items = Vec::new();
1636 let associated_type_overridden = overridden_associated_type.is_some();
1637 for trait_item in tcx.associated_items(impl_trait_ref.def_id) {
1638 let is_implemented = trait_def.ancestors(tcx, impl_id)
1639 .defs(tcx, trait_item.ident, trait_item.kind, impl_trait_ref.def_id)
1641 .map(|node_item| !node_item.node.is_from_trait())
1644 if !is_implemented && !tcx.impl_is_default(impl_id) {
1645 if !trait_item.defaultness.has_value() {
1646 missing_items.push(trait_item);
1647 } else if associated_type_overridden {
1648 invalidated_items.push(trait_item.ident);
1653 if !missing_items.is_empty() {
1654 let mut err = struct_span_err!(tcx.sess, impl_span, E0046,
1655 "not all trait items implemented, missing: `{}`",
1656 missing_items.iter()
1657 .map(|trait_item| trait_item.ident.to_string())
1658 .collect::<Vec<_>>().join("`, `"));
1659 err.span_label(impl_span, format!("missing `{}` in implementation",
1660 missing_items.iter()
1661 .map(|trait_item| trait_item.ident.to_string())
1662 .collect::<Vec<_>>().join("`, `")));
1663 for trait_item in missing_items {
1664 if let Some(span) = tcx.hir().span_if_local(trait_item.def_id) {
1665 err.span_label(span, format!("`{}` from trait", trait_item.ident));
1667 err.note_trait_signature(trait_item.ident.to_string(),
1668 trait_item.signature(tcx));
1674 if !invalidated_items.is_empty() {
1675 let invalidator = overridden_associated_type.unwrap();
1676 span_err!(tcx.sess, invalidator.span, E0399,
1677 "the following trait items need to be reimplemented \
1678 as `{}` was overridden: `{}`",
1680 invalidated_items.iter()
1681 .map(|name| name.to_string())
1682 .collect::<Vec<_>>().join("`, `"))
1686 /// Checks whether a type can be represented in memory. In particular, it
1687 /// identifies types that contain themselves without indirection through a
1688 /// pointer, which would mean their size is unbounded.
1689 fn check_representable<'tcx>(tcx: TyCtxt<'tcx>, sp: Span, item_def_id: DefId) -> bool {
1690 let rty = tcx.type_of(item_def_id);
1692 // Check that it is possible to represent this type. This call identifies
1693 // (1) types that contain themselves and (2) types that contain a different
1694 // recursive type. It is only necessary to throw an error on those that
1695 // contain themselves. For case 2, there must be an inner type that will be
1696 // caught by case 1.
1697 match rty.is_representable(tcx, sp) {
1698 Representability::SelfRecursive(spans) => {
1699 let mut err = tcx.recursive_type_with_infinite_size_error(item_def_id);
1701 err.span_label(span, "recursive without indirection");
1706 Representability::Representable | Representability::ContainsRecursive => (),
1711 pub fn check_simd<'tcx>(tcx: TyCtxt<'tcx>, sp: Span, def_id: DefId) {
1712 let t = tcx.type_of(def_id);
1713 if let ty::Adt(def, substs) = t.sty {
1714 if def.is_struct() {
1715 let fields = &def.non_enum_variant().fields;
1716 if fields.is_empty() {
1717 span_err!(tcx.sess, sp, E0075, "SIMD vector cannot be empty");
1720 let e = fields[0].ty(tcx, substs);
1721 if !fields.iter().all(|f| f.ty(tcx, substs) == e) {
1722 struct_span_err!(tcx.sess, sp, E0076, "SIMD vector should be homogeneous")
1723 .span_label(sp, "SIMD elements must have the same type")
1728 ty::Param(_) => { /* struct<T>(T, T, T, T) is ok */ }
1729 _ if e.is_machine() => { /* struct(u8, u8, u8, u8) is ok */ }
1731 span_err!(tcx.sess, sp, E0077,
1732 "SIMD vector element type should be machine type");
1740 fn check_packed<'tcx>(tcx: TyCtxt<'tcx>, sp: Span, def_id: DefId) {
1741 let repr = tcx.adt_def(def_id).repr;
1743 for attr in tcx.get_attrs(def_id).iter() {
1744 for r in attr::find_repr_attrs(&tcx.sess.parse_sess, attr) {
1745 if let attr::ReprPacked(pack) = r {
1746 if pack != repr.pack {
1747 struct_span_err!(tcx.sess, sp, E0634,
1748 "type has conflicting packed representation hints").emit();
1754 struct_span_err!(tcx.sess, sp, E0587,
1755 "type has conflicting packed and align representation hints").emit();
1757 else if check_packed_inner(tcx, def_id, &mut Vec::new()) {
1758 struct_span_err!(tcx.sess, sp, E0588,
1759 "packed type cannot transitively contain a `[repr(align)]` type").emit();
1764 fn check_packed_inner<'tcx>(tcx: TyCtxt<'tcx>, def_id: DefId, stack: &mut Vec<DefId>) -> bool {
1765 let t = tcx.type_of(def_id);
1766 if stack.contains(&def_id) {
1767 debug!("check_packed_inner: {:?} is recursive", t);
1770 if let ty::Adt(def, substs) = t.sty {
1771 if def.is_struct() || def.is_union() {
1772 if tcx.adt_def(def.did).repr.align > 0 {
1775 // push struct def_id before checking fields
1777 for field in &def.non_enum_variant().fields {
1778 let f = field.ty(tcx, substs);
1779 if let ty::Adt(def, _) = f.sty {
1780 if check_packed_inner(tcx, def.did, stack) {
1785 // only need to pop if not early out
1792 /// Emit an error when encountering more or less than one variant in a transparent enum.
1793 fn bad_variant_count<'tcx>(tcx: TyCtxt<'tcx>, adt: &'tcx ty::AdtDef, sp: Span, did: DefId) {
1794 let variant_spans: Vec<_> = adt.variants.iter().map(|variant| {
1795 tcx.hir().span_if_local(variant.def_id).unwrap()
1798 "needs exactly one variant, but has {}",
1801 let mut err = struct_span_err!(tcx.sess, sp, E0731, "transparent enum {}", msg);
1802 err.span_label(sp, &msg);
1803 if let &[ref start.., ref end] = &variant_spans[..] {
1804 for variant_span in start {
1805 err.span_label(*variant_span, "");
1807 err.span_label(*end, &format!("too many variants in `{}`", tcx.def_path_str(did)));
1812 /// Emit an error when encountering more or less than one non-zero-sized field in a transparent
1814 fn bad_non_zero_sized_fields<'tcx>(
1816 adt: &'tcx ty::AdtDef,
1818 field_spans: impl Iterator<Item = Span>,
1821 let msg = format!("needs exactly one non-zero-sized field, but has {}", field_count);
1822 let mut err = struct_span_err!(
1826 "{}transparent {} {}",
1827 if adt.is_enum() { "the variant of a " } else { "" },
1831 err.span_label(sp, &msg);
1832 for sp in field_spans {
1833 err.span_label(sp, "this field is non-zero-sized");
1838 fn check_transparent<'tcx>(tcx: TyCtxt<'tcx>, sp: Span, def_id: DefId) {
1839 let adt = tcx.adt_def(def_id);
1840 if !adt.repr.transparent() {
1843 let sp = tcx.sess.source_map().def_span(sp);
1846 if !tcx.features().transparent_enums {
1848 &tcx.sess.parse_sess,
1849 sym::transparent_enums,
1851 GateIssue::Language,
1852 "transparent enums are unstable",
1855 if adt.variants.len() != 1 {
1856 bad_variant_count(tcx, adt, sp, def_id);
1857 if adt.variants.is_empty() {
1858 // Don't bother checking the fields. No variants (and thus no fields) exist.
1864 if adt.is_union() && !tcx.features().transparent_unions {
1865 emit_feature_err(&tcx.sess.parse_sess,
1866 sym::transparent_unions,
1868 GateIssue::Language,
1869 "transparent unions are unstable");
1872 // For each field, figure out if it's known to be a ZST and align(1)
1873 let field_infos = adt.all_fields().map(|field| {
1874 let ty = field.ty(tcx, InternalSubsts::identity_for_item(tcx, field.did));
1875 let param_env = tcx.param_env(field.did);
1876 let layout = tcx.layout_of(param_env.and(ty));
1877 // We are currently checking the type this field came from, so it must be local
1878 let span = tcx.hir().span_if_local(field.did).unwrap();
1879 let zst = layout.map(|layout| layout.is_zst()).unwrap_or(false);
1880 let align1 = layout.map(|layout| layout.align.abi.bytes() == 1).unwrap_or(false);
1884 let non_zst_fields = field_infos.clone().filter_map(|(span, zst, _align1)| if !zst {
1889 let non_zst_count = non_zst_fields.clone().count();
1890 if non_zst_count != 1 {
1891 bad_non_zero_sized_fields(tcx, adt, non_zst_count, non_zst_fields, sp);
1893 for (span, zst, align1) in field_infos {
1899 "zero-sized field in transparent {} has alignment larger than 1",
1901 ).span_label(span, "has alignment larger than 1").emit();
1906 #[allow(trivial_numeric_casts)]
1907 pub fn check_enum<'tcx>(tcx: TyCtxt<'tcx>, sp: Span, vs: &'tcx [hir::Variant], id: hir::HirId) {
1908 let def_id = tcx.hir().local_def_id_from_hir_id(id);
1909 let def = tcx.adt_def(def_id);
1910 def.destructor(tcx); // force the destructor to be evaluated
1913 let attributes = tcx.get_attrs(def_id);
1914 if let Some(attr) = attr::find_by_name(&attributes, sym::repr) {
1916 tcx.sess, attr.span, E0084,
1917 "unsupported representation for zero-variant enum")
1918 .span_label(sp, "zero-variant enum")
1923 let repr_type_ty = def.repr.discr_type().to_ty(tcx);
1924 if repr_type_ty == tcx.types.i128 || repr_type_ty == tcx.types.u128 {
1925 if !tcx.features().repr128 {
1926 emit_feature_err(&tcx.sess.parse_sess,
1929 GateIssue::Language,
1930 "repr with 128-bit type is unstable");
1935 if let Some(ref e) = v.node.disr_expr {
1936 tcx.typeck_tables_of(tcx.hir().local_def_id_from_hir_id(e.hir_id));
1940 let mut disr_vals: Vec<Discr<'tcx>> = Vec::with_capacity(vs.len());
1941 for ((_, discr), v) in def.discriminants(tcx).zip(vs) {
1942 // Check for duplicate discriminant values
1943 if let Some(i) = disr_vals.iter().position(|&x| x.val == discr.val) {
1944 let variant_did = def.variants[VariantIdx::new(i)].def_id;
1945 let variant_i_hir_id = tcx.hir().as_local_hir_id(variant_did).unwrap();
1946 let variant_i = tcx.hir().expect_variant(variant_i_hir_id);
1947 let i_span = match variant_i.node.disr_expr {
1948 Some(ref expr) => tcx.hir().span_by_hir_id(expr.hir_id),
1949 None => tcx.hir().span_by_hir_id(variant_i_hir_id)
1951 let span = match v.node.disr_expr {
1952 Some(ref expr) => tcx.hir().span_by_hir_id(expr.hir_id),
1955 struct_span_err!(tcx.sess, span, E0081,
1956 "discriminant value `{}` already exists", disr_vals[i])
1957 .span_label(i_span, format!("first use of `{}`", disr_vals[i]))
1958 .span_label(span , format!("enum already has `{}`", disr_vals[i]))
1961 disr_vals.push(discr);
1964 check_representable(tcx, sp, def_id);
1965 check_transparent(tcx, sp, def_id);
1968 fn report_unexpected_variant_res<'tcx>(tcx: TyCtxt<'tcx>, res: Res, span: Span, qpath: &QPath) {
1969 span_err!(tcx.sess, span, E0533,
1970 "expected unit struct/variant or constant, found {} `{}`",
1972 hir::print::to_string(tcx.hir(), |s| s.print_qpath(qpath, false)));
1975 impl<'a, 'tcx> AstConv<'tcx> for FnCtxt<'a, 'tcx> {
1976 fn tcx<'b>(&'b self) -> TyCtxt<'tcx> {
1980 fn get_type_parameter_bounds(&self, _: Span, def_id: DefId)
1981 -> &'tcx ty::GenericPredicates<'tcx>
1984 let hir_id = tcx.hir().as_local_hir_id(def_id).unwrap();
1985 let item_id = tcx.hir().ty_param_owner(hir_id);
1986 let item_def_id = tcx.hir().local_def_id_from_hir_id(item_id);
1987 let generics = tcx.generics_of(item_def_id);
1988 let index = generics.param_def_id_to_index[&def_id];
1989 tcx.arena.alloc(ty::GenericPredicates {
1991 predicates: self.param_env.caller_bounds.iter().filter_map(|&predicate| {
1993 ty::Predicate::Trait(ref data)
1994 if data.skip_binder().self_ty().is_param(index) => {
1995 // HACK(eddyb) should get the original `Span`.
1996 let span = tcx.def_span(def_id);
1997 Some((predicate, span))
2007 def: Option<&ty::GenericParamDef>,
2009 ) -> Option<ty::Region<'tcx>> {
2011 Some(def) => infer::EarlyBoundRegion(span, def.name),
2012 None => infer::MiscVariable(span)
2014 Some(self.next_region_var(v))
2017 fn ty_infer(&self, param: Option<&ty::GenericParamDef>, span: Span) -> Ty<'tcx> {
2018 if let Some(param) = param {
2019 if let UnpackedKind::Type(ty) = self.var_for_def(span, param).unpack() {
2024 self.next_ty_var(TypeVariableOrigin {
2025 kind: TypeVariableOriginKind::TypeInference,
2034 param: Option<&ty::GenericParamDef>,
2036 ) -> &'tcx Const<'tcx> {
2037 if let Some(param) = param {
2038 if let UnpackedKind::Const(ct) = self.var_for_def(span, param).unpack() {
2043 self.next_const_var(ty, ConstVariableOrigin {
2044 kind: ConstVariableOriginKind::ConstInference,
2050 fn projected_ty_from_poly_trait_ref(&self,
2053 poly_trait_ref: ty::PolyTraitRef<'tcx>)
2056 let (trait_ref, _) = self.replace_bound_vars_with_fresh_vars(
2058 infer::LateBoundRegionConversionTime::AssocTypeProjection(item_def_id),
2062 self.tcx().mk_projection(item_def_id, trait_ref.substs)
2065 fn normalize_ty(&self, span: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
2066 if ty.has_escaping_bound_vars() {
2067 ty // FIXME: normalization and escaping regions
2069 self.normalize_associated_types_in(span, &ty)
2073 fn set_tainted_by_errors(&self) {
2074 self.infcx.set_tainted_by_errors()
2077 fn record_ty(&self, hir_id: hir::HirId, ty: Ty<'tcx>, _span: Span) {
2078 self.write_ty(hir_id, ty)
2082 /// Controls whether the arguments are tupled. This is used for the call
2085 /// Tupling means that all call-side arguments are packed into a tuple and
2086 /// passed as a single parameter. For example, if tupling is enabled, this
2089 /// fn f(x: (isize, isize))
2091 /// Can be called as:
2098 #[derive(Clone, Eq, PartialEq)]
2099 enum TupleArgumentsFlag {
2104 impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
2106 inh: &'a Inherited<'a, 'tcx>,
2107 param_env: ty::ParamEnv<'tcx>,
2108 body_id: hir::HirId,
2109 ) -> FnCtxt<'a, 'tcx> {
2113 err_count_on_creation: inh.tcx.sess.err_count(),
2115 ret_coercion_span: RefCell::new(None),
2117 ps: RefCell::new(UnsafetyState::function(hir::Unsafety::Normal,
2118 hir::CRATE_HIR_ID)),
2119 diverges: Cell::new(Diverges::Maybe),
2120 has_errors: Cell::new(false),
2121 enclosing_breakables: RefCell::new(EnclosingBreakables {
2123 by_id: Default::default(),
2129 pub fn sess(&self) -> &Session {
2133 pub fn err_count_since_creation(&self) -> usize {
2134 self.tcx.sess.err_count() - self.err_count_on_creation
2137 /// Produces warning on the given node, if the current point in the
2138 /// function is unreachable, and there hasn't been another warning.
2139 fn warn_if_unreachable(&self, id: hir::HirId, span: Span, kind: &str) {
2140 if self.diverges.get() == Diverges::Always &&
2141 // If span arose from a desugaring of `if` then it is the condition itself,
2142 // which diverges, that we are about to lint on. This gives suboptimal diagnostics
2143 // and so we stop here and allow the block of the `if`-expression to be linted instead.
2144 !span.is_compiler_desugaring(CompilerDesugaringKind::IfTemporary) {
2145 self.diverges.set(Diverges::WarnedAlways);
2147 debug!("warn_if_unreachable: id={:?} span={:?} kind={}", id, span, kind);
2149 let msg = format!("unreachable {}", kind);
2150 self.tcx().lint_hir(lint::builtin::UNREACHABLE_CODE, id, span, &msg);
2156 code: ObligationCauseCode<'tcx>)
2157 -> ObligationCause<'tcx> {
2158 ObligationCause::new(span, self.body_id, code)
2161 pub fn misc(&self, span: Span) -> ObligationCause<'tcx> {
2162 self.cause(span, ObligationCauseCode::MiscObligation)
2165 /// Resolves type variables in `ty` if possible. Unlike the infcx
2166 /// version (resolve_vars_if_possible), this version will
2167 /// also select obligations if it seems useful, in an effort
2168 /// to get more type information.
2169 fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
2170 debug!("resolve_type_vars_with_obligations(ty={:?})", ty);
2172 // No Infer()? Nothing needs doing.
2173 if !ty.has_infer_types() {
2174 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
2178 // If `ty` is a type variable, see whether we already know what it is.
2179 ty = self.resolve_vars_if_possible(&ty);
2180 if !ty.has_infer_types() {
2181 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
2185 // If not, try resolving pending obligations as much as
2186 // possible. This can help substantially when there are
2187 // indirect dependencies that don't seem worth tracking
2189 self.select_obligations_where_possible(false);
2190 ty = self.resolve_vars_if_possible(&ty);
2192 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
2196 fn record_deferred_call_resolution(
2198 closure_def_id: DefId,
2199 r: DeferredCallResolution<'tcx>,
2201 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
2202 deferred_call_resolutions.entry(closure_def_id).or_default().push(r);
2205 fn remove_deferred_call_resolutions(
2207 closure_def_id: DefId,
2208 ) -> Vec<DeferredCallResolution<'tcx>> {
2209 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
2210 deferred_call_resolutions.remove(&closure_def_id).unwrap_or(vec![])
2213 pub fn tag(&self) -> String {
2214 format!("{:p}", self)
2217 pub fn local_ty(&self, span: Span, nid: hir::HirId) -> LocalTy<'tcx> {
2218 self.locals.borrow().get(&nid).cloned().unwrap_or_else(||
2219 span_bug!(span, "no type for local variable {}",
2220 self.tcx.hir().hir_to_string(nid))
2225 pub fn write_ty(&self, id: hir::HirId, ty: Ty<'tcx>) {
2226 debug!("write_ty({:?}, {:?}) in fcx {}",
2227 id, self.resolve_vars_if_possible(&ty), self.tag());
2228 self.tables.borrow_mut().node_types_mut().insert(id, ty);
2230 if ty.references_error() {
2231 self.has_errors.set(true);
2232 self.set_tainted_by_errors();
2236 pub fn write_field_index(&self, hir_id: hir::HirId, index: usize) {
2237 self.tables.borrow_mut().field_indices_mut().insert(hir_id, index);
2240 fn write_resolution(&self, hir_id: hir::HirId, r: Result<(DefKind, DefId), ErrorReported>) {
2241 self.tables.borrow_mut().type_dependent_defs_mut().insert(hir_id, r);
2244 pub fn write_method_call(&self,
2246 method: MethodCallee<'tcx>) {
2247 debug!("write_method_call(hir_id={:?}, method={:?})", hir_id, method);
2248 self.write_resolution(hir_id, Ok((DefKind::Method, method.def_id)));
2249 self.write_substs(hir_id, method.substs);
2251 // When the method is confirmed, the `method.substs` includes
2252 // parameters from not just the method, but also the impl of
2253 // the method -- in particular, the `Self` type will be fully
2254 // resolved. However, those are not something that the "user
2255 // specified" -- i.e., those types come from the inferred type
2256 // of the receiver, not something the user wrote. So when we
2257 // create the user-substs, we want to replace those earlier
2258 // types with just the types that the user actually wrote --
2259 // that is, those that appear on the *method itself*.
2261 // As an example, if the user wrote something like
2262 // `foo.bar::<u32>(...)` -- the `Self` type here will be the
2263 // type of `foo` (possibly adjusted), but we don't want to
2264 // include that. We want just the `[_, u32]` part.
2265 if !method.substs.is_noop() {
2266 let method_generics = self.tcx.generics_of(method.def_id);
2267 if !method_generics.params.is_empty() {
2268 let user_type_annotation = self.infcx.probe(|_| {
2269 let user_substs = UserSubsts {
2270 substs: InternalSubsts::for_item(self.tcx, method.def_id, |param, _| {
2271 let i = param.index as usize;
2272 if i < method_generics.parent_count {
2273 self.infcx.var_for_def(DUMMY_SP, param)
2278 user_self_ty: None, // not relevant here
2281 self.infcx.canonicalize_user_type_annotation(&UserType::TypeOf(
2287 debug!("write_method_call: user_type_annotation={:?}", user_type_annotation);
2288 self.write_user_type_annotation(hir_id, user_type_annotation);
2293 pub fn write_substs(&self, node_id: hir::HirId, substs: SubstsRef<'tcx>) {
2294 if !substs.is_noop() {
2295 debug!("write_substs({:?}, {:?}) in fcx {}",
2300 self.tables.borrow_mut().node_substs_mut().insert(node_id, substs);
2304 /// Given the substs that we just converted from the HIR, try to
2305 /// canonicalize them and store them as user-given substitutions
2306 /// (i.e., substitutions that must be respected by the NLL check).
2308 /// This should be invoked **before any unifications have
2309 /// occurred**, so that annotations like `Vec<_>` are preserved
2311 pub fn write_user_type_annotation_from_substs(
2315 substs: SubstsRef<'tcx>,
2316 user_self_ty: Option<UserSelfTy<'tcx>>,
2319 "write_user_type_annotation_from_substs: hir_id={:?} def_id={:?} substs={:?} \
2320 user_self_ty={:?} in fcx {}",
2321 hir_id, def_id, substs, user_self_ty, self.tag(),
2324 if Self::can_contain_user_lifetime_bounds((substs, user_self_ty)) {
2325 let canonicalized = self.infcx.canonicalize_user_type_annotation(
2326 &UserType::TypeOf(def_id, UserSubsts {
2331 debug!("write_user_type_annotation_from_substs: canonicalized={:?}", canonicalized);
2332 self.write_user_type_annotation(hir_id, canonicalized);
2336 pub fn write_user_type_annotation(
2339 canonical_user_type_annotation: CanonicalUserType<'tcx>,
2342 "write_user_type_annotation: hir_id={:?} canonical_user_type_annotation={:?} tag={}",
2343 hir_id, canonical_user_type_annotation, self.tag(),
2346 if !canonical_user_type_annotation.is_identity() {
2347 self.tables.borrow_mut().user_provided_types_mut().insert(
2348 hir_id, canonical_user_type_annotation
2351 debug!("write_user_type_annotation: skipping identity substs");
2355 pub fn apply_adjustments(&self, expr: &hir::Expr, adj: Vec<Adjustment<'tcx>>) {
2356 debug!("apply_adjustments(expr={:?}, adj={:?})", expr, adj);
2362 match self.tables.borrow_mut().adjustments_mut().entry(expr.hir_id) {
2363 Entry::Vacant(entry) => { entry.insert(adj); },
2364 Entry::Occupied(mut entry) => {
2365 debug!(" - composing on top of {:?}", entry.get());
2366 match (&entry.get()[..], &adj[..]) {
2367 // Applying any adjustment on top of a NeverToAny
2368 // is a valid NeverToAny adjustment, because it can't
2370 (&[Adjustment { kind: Adjust::NeverToAny, .. }], _) => return,
2372 Adjustment { kind: Adjust::Deref(_), .. },
2373 Adjustment { kind: Adjust::Borrow(AutoBorrow::Ref(..)), .. },
2375 Adjustment { kind: Adjust::Deref(_), .. },
2376 .. // Any following adjustments are allowed.
2378 // A reborrow has no effect before a dereference.
2380 // FIXME: currently we never try to compose autoderefs
2381 // and ReifyFnPointer/UnsafeFnPointer, but we could.
2383 bug!("while adjusting {:?}, can't compose {:?} and {:?}",
2384 expr, entry.get(), adj)
2386 *entry.get_mut() = adj;
2391 /// Basically whenever we are converting from a type scheme into
2392 /// the fn body space, we always want to normalize associated
2393 /// types as well. This function combines the two.
2394 fn instantiate_type_scheme<T>(&self,
2396 substs: SubstsRef<'tcx>,
2399 where T : TypeFoldable<'tcx>
2401 let value = value.subst(self.tcx, substs);
2402 let result = self.normalize_associated_types_in(span, &value);
2403 debug!("instantiate_type_scheme(value={:?}, substs={:?}) = {:?}",
2410 /// As `instantiate_type_scheme`, but for the bounds found in a
2411 /// generic type scheme.
2412 fn instantiate_bounds(&self, span: Span, def_id: DefId, substs: SubstsRef<'tcx>)
2413 -> ty::InstantiatedPredicates<'tcx> {
2414 let bounds = self.tcx.predicates_of(def_id);
2415 let result = bounds.instantiate(self.tcx, substs);
2416 let result = self.normalize_associated_types_in(span, &result);
2417 debug!("instantiate_bounds(bounds={:?}, substs={:?}) = {:?}",
2424 /// Replaces the opaque types from the given value with type variables,
2425 /// and records the `OpaqueTypeMap` for later use during writeback. See
2426 /// `InferCtxt::instantiate_opaque_types` for more details.
2427 fn instantiate_opaque_types_from_value<T: TypeFoldable<'tcx>>(
2429 parent_id: hir::HirId,
2432 let parent_def_id = self.tcx.hir().local_def_id_from_hir_id(parent_id);
2433 debug!("instantiate_opaque_types_from_value(parent_def_id={:?}, value={:?})",
2437 let (value, opaque_type_map) = self.register_infer_ok_obligations(
2438 self.instantiate_opaque_types(
2446 let mut opaque_types = self.opaque_types.borrow_mut();
2447 for (ty, decl) in opaque_type_map {
2448 let old_value = opaque_types.insert(ty, decl);
2449 assert!(old_value.is_none(), "instantiated twice: {:?}/{:?}", ty, decl);
2455 fn normalize_associated_types_in<T>(&self, span: Span, value: &T) -> T
2456 where T : TypeFoldable<'tcx>
2458 self.inh.normalize_associated_types_in(span, self.body_id, self.param_env, value)
2461 fn normalize_associated_types_in_as_infer_ok<T>(&self, span: Span, value: &T)
2463 where T : TypeFoldable<'tcx>
2465 self.inh.partially_normalize_associated_types_in(span,
2471 pub fn require_type_meets(&self,
2474 code: traits::ObligationCauseCode<'tcx>,
2477 self.register_bound(
2480 traits::ObligationCause::new(span, self.body_id, code));
2483 pub fn require_type_is_sized(&self,
2486 code: traits::ObligationCauseCode<'tcx>)
2488 let lang_item = self.tcx.require_lang_item(lang_items::SizedTraitLangItem);
2489 self.require_type_meets(ty, span, code, lang_item);
2492 pub fn require_type_is_sized_deferred(&self,
2495 code: traits::ObligationCauseCode<'tcx>)
2497 self.deferred_sized_obligations.borrow_mut().push((ty, span, code));
2500 pub fn register_bound(&self,
2503 cause: traits::ObligationCause<'tcx>)
2505 self.fulfillment_cx.borrow_mut()
2506 .register_bound(self, self.param_env, ty, def_id, cause);
2509 pub fn to_ty(&self, ast_t: &hir::Ty) -> Ty<'tcx> {
2510 let t = AstConv::ast_ty_to_ty(self, ast_t);
2511 self.register_wf_obligation(t, ast_t.span, traits::MiscObligation);
2515 pub fn to_ty_saving_user_provided_ty(&self, ast_ty: &hir::Ty) -> Ty<'tcx> {
2516 let ty = self.to_ty(ast_ty);
2517 debug!("to_ty_saving_user_provided_ty: ty={:?}", ty);
2519 if Self::can_contain_user_lifetime_bounds(ty) {
2520 let c_ty = self.infcx.canonicalize_response(&UserType::Ty(ty));
2521 debug!("to_ty_saving_user_provided_ty: c_ty={:?}", c_ty);
2522 self.tables.borrow_mut().user_provided_types_mut().insert(ast_ty.hir_id, c_ty);
2528 /// Returns the `DefId` of the constant parameter that the provided expression is a path to.
2529 pub fn const_param_def_id(&self, hir_c: &hir::AnonConst) -> Option<DefId> {
2530 AstConv::const_param_def_id(self, &self.tcx.hir().body(hir_c.body).value)
2533 pub fn to_const(&self, ast_c: &hir::AnonConst, ty: Ty<'tcx>) -> &'tcx ty::Const<'tcx> {
2534 AstConv::ast_const_to_const(self, ast_c, ty)
2537 // If the type given by the user has free regions, save it for later, since
2538 // NLL would like to enforce those. Also pass in types that involve
2539 // projections, since those can resolve to `'static` bounds (modulo #54940,
2540 // which hopefully will be fixed by the time you see this comment, dear
2541 // reader, although I have my doubts). Also pass in types with inference
2542 // types, because they may be repeated. Other sorts of things are already
2543 // sufficiently enforced with erased regions. =)
2544 fn can_contain_user_lifetime_bounds<T>(t: T) -> bool
2546 T: TypeFoldable<'tcx>
2548 t.has_free_regions() || t.has_projections() || t.has_infer_types()
2551 pub fn node_ty(&self, id: hir::HirId) -> Ty<'tcx> {
2552 match self.tables.borrow().node_types().get(id) {
2554 None if self.is_tainted_by_errors() => self.tcx.types.err,
2556 let node_id = self.tcx.hir().hir_to_node_id(id);
2557 bug!("no type for node {}: {} in fcx {}",
2558 node_id, self.tcx.hir().node_to_string(node_id),
2564 /// Registers an obligation for checking later, during regionck, that the type `ty` must
2565 /// outlive the region `r`.
2566 pub fn register_wf_obligation(&self,
2569 code: traits::ObligationCauseCode<'tcx>)
2571 // WF obligations never themselves fail, so no real need to give a detailed cause:
2572 let cause = traits::ObligationCause::new(span, self.body_id, code);
2573 self.register_predicate(traits::Obligation::new(cause,
2575 ty::Predicate::WellFormed(ty)));
2578 /// Registers obligations that all types appearing in `substs` are well-formed.
2579 pub fn add_wf_bounds(&self, substs: SubstsRef<'tcx>, expr: &hir::Expr) {
2580 for ty in substs.types() {
2581 self.register_wf_obligation(ty, expr.span, traits::MiscObligation);
2585 /// Given a fully substituted set of bounds (`generic_bounds`), and the values with which each
2586 /// type/region parameter was instantiated (`substs`), creates and registers suitable
2587 /// trait/region obligations.
2589 /// For example, if there is a function:
2592 /// fn foo<'a,T:'a>(...)
2595 /// and a reference:
2601 /// Then we will create a fresh region variable `'$0` and a fresh type variable `$1` for `'a`
2602 /// and `T`. This routine will add a region obligation `$1:'$0` and register it locally.
2603 pub fn add_obligations_for_parameters(&self,
2604 cause: traits::ObligationCause<'tcx>,
2605 predicates: &ty::InstantiatedPredicates<'tcx>)
2607 assert!(!predicates.has_escaping_bound_vars());
2609 debug!("add_obligations_for_parameters(predicates={:?})",
2612 for obligation in traits::predicates_for_generics(cause, self.param_env, predicates) {
2613 self.register_predicate(obligation);
2617 // FIXME(arielb1): use this instead of field.ty everywhere
2618 // Only for fields! Returns <none> for methods>
2619 // Indifferent to privacy flags
2620 pub fn field_ty(&self,
2622 field: &'tcx ty::FieldDef,
2623 substs: SubstsRef<'tcx>)
2626 self.normalize_associated_types_in(span, &field.ty(self.tcx, substs))
2629 fn check_casts(&self) {
2630 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
2631 for cast in deferred_cast_checks.drain(..) {
2636 fn resolve_generator_interiors(&self, def_id: DefId) {
2637 let mut generators = self.deferred_generator_interiors.borrow_mut();
2638 for (body_id, interior) in generators.drain(..) {
2639 self.select_obligations_where_possible(false);
2640 generator_interior::resolve_interior(self, def_id, body_id, interior);
2644 // Tries to apply a fallback to `ty` if it is an unsolved variable.
2645 // Non-numerics get replaced with ! or () (depending on whether
2646 // feature(never_type) is enabled, unconstrained ints with i32,
2647 // unconstrained floats with f64.
2648 // Fallback becomes very dubious if we have encountered type-checking errors.
2649 // In that case, fallback to Error.
2650 // The return value indicates whether fallback has occurred.
2651 fn fallback_if_possible(&self, ty: Ty<'tcx>) -> bool {
2652 use rustc::ty::error::UnconstrainedNumeric::Neither;
2653 use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedInt, UnconstrainedFloat};
2655 assert!(ty.is_ty_infer());
2656 let fallback = match self.type_is_unconstrained_numeric(ty) {
2657 _ if self.is_tainted_by_errors() => self.tcx().types.err,
2658 UnconstrainedInt => self.tcx.types.i32,
2659 UnconstrainedFloat => self.tcx.types.f64,
2660 Neither if self.type_var_diverges(ty) => self.tcx.mk_diverging_default(),
2661 Neither => return false,
2663 debug!("fallback_if_possible: defaulting `{:?}` to `{:?}`", ty, fallback);
2664 self.demand_eqtype(syntax_pos::DUMMY_SP, ty, fallback);
2668 fn select_all_obligations_or_error(&self) {
2669 debug!("select_all_obligations_or_error");
2670 if let Err(errors) = self.fulfillment_cx.borrow_mut().select_all_or_error(&self) {
2671 self.report_fulfillment_errors(&errors, self.inh.body_id, false);
2675 /// Select as many obligations as we can at present.
2676 fn select_obligations_where_possible(&self, fallback_has_occurred: bool) {
2677 if let Err(errors) = self.fulfillment_cx.borrow_mut().select_where_possible(self) {
2678 self.report_fulfillment_errors(&errors, self.inh.body_id, fallback_has_occurred);
2682 /// For the overloaded place expressions (`*x`, `x[3]`), the trait
2683 /// returns a type of `&T`, but the actual type we assign to the
2684 /// *expression* is `T`. So this function just peels off the return
2685 /// type by one layer to yield `T`.
2686 fn make_overloaded_place_return_type(&self,
2687 method: MethodCallee<'tcx>)
2688 -> ty::TypeAndMut<'tcx>
2690 // extract method return type, which will be &T;
2691 let ret_ty = method.sig.output();
2693 // method returns &T, but the type as visible to user is T, so deref
2694 ret_ty.builtin_deref(true).unwrap()
2700 base_expr: &'tcx hir::Expr,
2704 ) -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)> {
2705 // FIXME(#18741) -- this is almost but not quite the same as the
2706 // autoderef that normal method probing does. They could likely be
2709 let mut autoderef = self.autoderef(base_expr.span, base_ty);
2710 let mut result = None;
2711 while result.is_none() && autoderef.next().is_some() {
2712 result = self.try_index_step(expr, base_expr, &autoderef, needs, idx_ty);
2714 autoderef.finalize(self);
2718 /// To type-check `base_expr[index_expr]`, we progressively autoderef
2719 /// (and otherwise adjust) `base_expr`, looking for a type which either
2720 /// supports builtin indexing or overloaded indexing.
2721 /// This loop implements one step in that search; the autoderef loop
2722 /// is implemented by `lookup_indexing`.
2726 base_expr: &hir::Expr,
2727 autoderef: &Autoderef<'a, 'tcx>,
2730 ) -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)> {
2731 let adjusted_ty = autoderef.unambiguous_final_ty(self);
2732 debug!("try_index_step(expr={:?}, base_expr={:?}, adjusted_ty={:?}, \
2739 for &unsize in &[false, true] {
2740 let mut self_ty = adjusted_ty;
2742 // We only unsize arrays here.
2743 if let ty::Array(element_ty, _) = adjusted_ty.sty {
2744 self_ty = self.tcx.mk_slice(element_ty);
2750 // If some lookup succeeds, write callee into table and extract index/element
2751 // type from the method signature.
2752 // If some lookup succeeded, install method in table
2753 let input_ty = self.next_ty_var(TypeVariableOrigin {
2754 kind: TypeVariableOriginKind::AutoDeref,
2755 span: base_expr.span,
2757 let method = self.try_overloaded_place_op(
2758 expr.span, self_ty, &[input_ty], needs, PlaceOp::Index);
2760 let result = method.map(|ok| {
2761 debug!("try_index_step: success, using overloaded indexing");
2762 let method = self.register_infer_ok_obligations(ok);
2764 let mut adjustments = autoderef.adjust_steps(self, needs);
2765 if let ty::Ref(region, _, r_mutbl) = method.sig.inputs()[0].sty {
2766 let mutbl = match r_mutbl {
2767 hir::MutImmutable => AutoBorrowMutability::Immutable,
2768 hir::MutMutable => AutoBorrowMutability::Mutable {
2769 // Indexing can be desugared to a method call,
2770 // so maybe we could use two-phase here.
2771 // See the documentation of AllowTwoPhase for why that's
2772 // not the case today.
2773 allow_two_phase_borrow: AllowTwoPhase::No,
2776 adjustments.push(Adjustment {
2777 kind: Adjust::Borrow(AutoBorrow::Ref(region, mutbl)),
2778 target: self.tcx.mk_ref(region, ty::TypeAndMut {
2785 adjustments.push(Adjustment {
2786 kind: Adjust::Pointer(PointerCast::Unsize),
2787 target: method.sig.inputs()[0]
2790 self.apply_adjustments(base_expr, adjustments);
2792 self.write_method_call(expr.hir_id, method);
2793 (input_ty, self.make_overloaded_place_return_type(method).ty)
2795 if result.is_some() {
2803 fn resolve_place_op(&self, op: PlaceOp, is_mut: bool) -> (Option<DefId>, ast::Ident) {
2804 let (tr, name) = match (op, is_mut) {
2805 (PlaceOp::Deref, false) => (self.tcx.lang_items().deref_trait(), sym::deref),
2806 (PlaceOp::Deref, true) => (self.tcx.lang_items().deref_mut_trait(), sym::deref_mut),
2807 (PlaceOp::Index, false) => (self.tcx.lang_items().index_trait(), sym::index),
2808 (PlaceOp::Index, true) => (self.tcx.lang_items().index_mut_trait(), sym::index_mut),
2810 (tr, ast::Ident::with_empty_ctxt(name))
2813 fn try_overloaded_place_op(&self,
2816 arg_tys: &[Ty<'tcx>],
2819 -> Option<InferOk<'tcx, MethodCallee<'tcx>>>
2821 debug!("try_overloaded_place_op({:?},{:?},{:?},{:?})",
2827 // Try Mut first, if needed.
2828 let (mut_tr, mut_op) = self.resolve_place_op(op, true);
2829 let method = match (needs, mut_tr) {
2830 (Needs::MutPlace, Some(trait_did)) => {
2831 self.lookup_method_in_trait(span, mut_op, trait_did, base_ty, Some(arg_tys))
2836 // Otherwise, fall back to the immutable version.
2837 let (imm_tr, imm_op) = self.resolve_place_op(op, false);
2838 let method = match (method, imm_tr) {
2839 (None, Some(trait_did)) => {
2840 self.lookup_method_in_trait(span, imm_op, trait_did, base_ty, Some(arg_tys))
2842 (method, _) => method,
2848 fn check_method_argument_types(
2852 method: Result<MethodCallee<'tcx>, ()>,
2853 args_no_rcvr: &'tcx [hir::Expr],
2854 tuple_arguments: TupleArgumentsFlag,
2855 expected: Expectation<'tcx>,
2857 let has_error = match method {
2859 method.substs.references_error() || method.sig.references_error()
2864 let err_inputs = self.err_args(args_no_rcvr.len());
2866 let err_inputs = match tuple_arguments {
2867 DontTupleArguments => err_inputs,
2868 TupleArguments => vec![self.tcx.intern_tup(&err_inputs[..])],
2871 self.check_argument_types(sp, expr_sp, &err_inputs[..], &[], args_no_rcvr,
2872 false, tuple_arguments, None);
2873 return self.tcx.types.err;
2876 let method = method.unwrap();
2877 // HACK(eddyb) ignore self in the definition (see above).
2878 let expected_arg_tys = self.expected_inputs_for_expected_output(
2881 method.sig.output(),
2882 &method.sig.inputs()[1..]
2884 self.check_argument_types(sp, expr_sp, &method.sig.inputs()[1..], &expected_arg_tys[..],
2885 args_no_rcvr, method.sig.c_variadic, tuple_arguments,
2886 self.tcx.hir().span_if_local(method.def_id));
2890 fn self_type_matches_expected_vid(
2892 trait_ref: ty::PolyTraitRef<'tcx>,
2893 expected_vid: ty::TyVid,
2895 let self_ty = self.shallow_resolve(trait_ref.self_ty());
2897 "self_type_matches_expected_vid(trait_ref={:?}, self_ty={:?}, expected_vid={:?})",
2898 trait_ref, self_ty, expected_vid
2901 ty::Infer(ty::TyVar(found_vid)) => {
2902 // FIXME: consider using `sub_root_var` here so we
2903 // can see through subtyping.
2904 let found_vid = self.root_var(found_vid);
2905 debug!("self_type_matches_expected_vid - found_vid={:?}", found_vid);
2906 expected_vid == found_vid
2912 fn obligations_for_self_ty<'b>(
2915 ) -> impl Iterator<Item = (ty::PolyTraitRef<'tcx>, traits::PredicateObligation<'tcx>)>
2918 // FIXME: consider using `sub_root_var` here so we
2919 // can see through subtyping.
2920 let ty_var_root = self.root_var(self_ty);
2921 debug!("obligations_for_self_ty: self_ty={:?} ty_var_root={:?} pending_obligations={:?}",
2922 self_ty, ty_var_root,
2923 self.fulfillment_cx.borrow().pending_obligations());
2927 .pending_obligations()
2929 .filter_map(move |obligation| match obligation.predicate {
2930 ty::Predicate::Projection(ref data) =>
2931 Some((data.to_poly_trait_ref(self.tcx), obligation)),
2932 ty::Predicate::Trait(ref data) =>
2933 Some((data.to_poly_trait_ref(), obligation)),
2934 ty::Predicate::Subtype(..) => None,
2935 ty::Predicate::RegionOutlives(..) => None,
2936 ty::Predicate::TypeOutlives(..) => None,
2937 ty::Predicate::WellFormed(..) => None,
2938 ty::Predicate::ObjectSafe(..) => None,
2939 ty::Predicate::ConstEvaluatable(..) => None,
2940 // N.B., this predicate is created by breaking down a
2941 // `ClosureType: FnFoo()` predicate, where
2942 // `ClosureType` represents some `Closure`. It can't
2943 // possibly be referring to the current closure,
2944 // because we haven't produced the `Closure` for
2945 // this closure yet; this is exactly why the other
2946 // code is looking for a self type of a unresolved
2947 // inference variable.
2948 ty::Predicate::ClosureKind(..) => None,
2949 }).filter(move |(tr, _)| self.self_type_matches_expected_vid(*tr, ty_var_root))
2952 fn type_var_is_sized(&self, self_ty: ty::TyVid) -> bool {
2953 self.obligations_for_self_ty(self_ty).any(|(tr, _)| {
2954 Some(tr.def_id()) == self.tcx.lang_items().sized_trait()
2958 /// Generic function that factors out common logic from function calls,
2959 /// method calls and overloaded operators.
2960 fn check_argument_types(
2964 fn_inputs: &[Ty<'tcx>],
2965 expected_arg_tys: &[Ty<'tcx>],
2966 args: &'tcx [hir::Expr],
2968 tuple_arguments: TupleArgumentsFlag,
2969 def_span: Option<Span>,
2973 // Grab the argument types, supplying fresh type variables
2974 // if the wrong number of arguments were supplied
2975 let supplied_arg_count = if tuple_arguments == DontTupleArguments {
2981 // All the input types from the fn signature must outlive the call
2982 // so as to validate implied bounds.
2983 for &fn_input_ty in fn_inputs {
2984 self.register_wf_obligation(fn_input_ty, sp, traits::MiscObligation);
2987 let expected_arg_count = fn_inputs.len();
2989 let param_count_error = |expected_count: usize,
2994 let mut err = tcx.sess.struct_span_err_with_code(sp,
2995 &format!("this function takes {}{} but {} {} supplied",
2996 if c_variadic { "at least " } else { "" },
2997 potentially_plural_count(expected_count, "parameter"),
2998 potentially_plural_count(arg_count, "parameter"),
2999 if arg_count == 1 {"was"} else {"were"}),
3000 DiagnosticId::Error(error_code.to_owned()));
3002 if let Some(def_s) = def_span.map(|sp| tcx.sess.source_map().def_span(sp)) {
3003 err.span_label(def_s, "defined here");
3006 let sugg_span = tcx.sess.source_map().end_point(expr_sp);
3007 // remove closing `)` from the span
3008 let sugg_span = sugg_span.shrink_to_lo();
3009 err.span_suggestion(
3011 "expected the unit value `()`; create it with empty parentheses",
3013 Applicability::MachineApplicable);
3015 err.span_label(sp, format!("expected {}{}",
3016 if c_variadic { "at least " } else { "" },
3017 potentially_plural_count(expected_count, "parameter")));
3022 let mut expected_arg_tys = expected_arg_tys.to_vec();
3024 let formal_tys = if tuple_arguments == TupleArguments {
3025 let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
3026 match tuple_type.sty {
3027 ty::Tuple(arg_types) if arg_types.len() != args.len() => {
3028 param_count_error(arg_types.len(), args.len(), "E0057", false, false);
3029 expected_arg_tys = vec![];
3030 self.err_args(args.len())
3032 ty::Tuple(arg_types) => {
3033 expected_arg_tys = match expected_arg_tys.get(0) {
3034 Some(&ty) => match ty.sty {
3035 ty::Tuple(ref tys) => tys.iter().map(|k| k.expect_ty()).collect(),
3040 arg_types.iter().map(|k| k.expect_ty()).collect()
3043 span_err!(tcx.sess, sp, E0059,
3044 "cannot use call notation; the first type parameter \
3045 for the function trait is neither a tuple nor unit");
3046 expected_arg_tys = vec![];
3047 self.err_args(args.len())
3050 } else if expected_arg_count == supplied_arg_count {
3052 } else if c_variadic {
3053 if supplied_arg_count >= expected_arg_count {
3056 param_count_error(expected_arg_count, supplied_arg_count, "E0060", true, false);
3057 expected_arg_tys = vec![];
3058 self.err_args(supplied_arg_count)
3061 // is the missing argument of type `()`?
3062 let sugg_unit = if expected_arg_tys.len() == 1 && supplied_arg_count == 0 {
3063 self.resolve_vars_if_possible(&expected_arg_tys[0]).is_unit()
3064 } else if fn_inputs.len() == 1 && supplied_arg_count == 0 {
3065 self.resolve_vars_if_possible(&fn_inputs[0]).is_unit()
3069 param_count_error(expected_arg_count, supplied_arg_count, "E0061", false, sugg_unit);
3071 expected_arg_tys = vec![];
3072 self.err_args(supplied_arg_count)
3075 debug!("check_argument_types: formal_tys={:?}",
3076 formal_tys.iter().map(|t| self.ty_to_string(*t)).collect::<Vec<String>>());
3078 // If there is no expectation, expect formal_tys.
3079 let expected_arg_tys = if !expected_arg_tys.is_empty() {
3085 // Check the arguments.
3086 // We do this in a pretty awful way: first we type-check any arguments
3087 // that are not closures, then we type-check the closures. This is so
3088 // that we have more information about the types of arguments when we
3089 // type-check the functions. This isn't really the right way to do this.
3090 for &check_closures in &[false, true] {
3091 debug!("check_closures={}", check_closures);
3093 // More awful hacks: before we check argument types, try to do
3094 // an "opportunistic" vtable resolution of any trait bounds on
3095 // the call. This helps coercions.
3097 self.select_obligations_where_possible(false);
3100 // For C-variadic functions, we don't have a declared type for all of
3101 // the arguments hence we only do our usual type checking with
3102 // the arguments who's types we do know.
3103 let t = if c_variadic {
3105 } else if tuple_arguments == TupleArguments {
3110 for (i, arg) in args.iter().take(t).enumerate() {
3111 // Warn only for the first loop (the "no closures" one).
3112 // Closure arguments themselves can't be diverging, but
3113 // a previous argument can, e.g., `foo(panic!(), || {})`.
3114 if !check_closures {
3115 self.warn_if_unreachable(arg.hir_id, arg.span, "expression");
3118 let is_closure = match arg.node {
3119 ExprKind::Closure(..) => true,
3123 if is_closure != check_closures {
3127 debug!("checking the argument");
3128 let formal_ty = formal_tys[i];
3130 // The special-cased logic below has three functions:
3131 // 1. Provide as good of an expected type as possible.
3132 let expected = Expectation::rvalue_hint(self, expected_arg_tys[i]);
3134 let checked_ty = self.check_expr_with_expectation(&arg, expected);
3136 // 2. Coerce to the most detailed type that could be coerced
3137 // to, which is `expected_ty` if `rvalue_hint` returns an
3138 // `ExpectHasType(expected_ty)`, or the `formal_ty` otherwise.
3139 let coerce_ty = expected.only_has_type(self).unwrap_or(formal_ty);
3140 // We're processing function arguments so we definitely want to use
3141 // two-phase borrows.
3142 self.demand_coerce(&arg, checked_ty, coerce_ty, AllowTwoPhase::Yes);
3144 // 3. Relate the expected type and the formal one,
3145 // if the expected type was used for the coercion.
3146 self.demand_suptype(arg.span, formal_ty, coerce_ty);
3150 // We also need to make sure we at least write the ty of the other
3151 // arguments which we skipped above.
3153 fn variadic_error<'tcx>(s: &Session, span: Span, t: Ty<'tcx>, cast_ty: &str) {
3154 use crate::structured_errors::{VariadicError, StructuredDiagnostic};
3155 VariadicError::new(s, span, t, cast_ty).diagnostic().emit();
3158 for arg in args.iter().skip(expected_arg_count) {
3159 let arg_ty = self.check_expr(&arg);
3161 // There are a few types which get autopromoted when passed via varargs
3162 // in C but we just error out instead and require explicit casts.
3163 let arg_ty = self.structurally_resolved_type(arg.span, arg_ty);
3165 ty::Float(ast::FloatTy::F32) => {
3166 variadic_error(tcx.sess, arg.span, arg_ty, "c_double");
3168 ty::Int(ast::IntTy::I8) | ty::Int(ast::IntTy::I16) | ty::Bool => {
3169 variadic_error(tcx.sess, arg.span, arg_ty, "c_int");
3171 ty::Uint(ast::UintTy::U8) | ty::Uint(ast::UintTy::U16) => {
3172 variadic_error(tcx.sess, arg.span, arg_ty, "c_uint");
3175 let ptr_ty = self.tcx.mk_fn_ptr(arg_ty.fn_sig(self.tcx));
3176 let ptr_ty = self.resolve_vars_if_possible(&ptr_ty);
3177 variadic_error(tcx.sess, arg.span, arg_ty, &ptr_ty.to_string());
3185 fn err_args(&self, len: usize) -> Vec<Ty<'tcx>> {
3186 vec![self.tcx.types.err; len]
3189 // AST fragment checking
3192 expected: Expectation<'tcx>)
3198 ast::LitKind::Str(..) => tcx.mk_static_str(),
3199 ast::LitKind::ByteStr(ref v) => {
3200 tcx.mk_imm_ref(tcx.lifetimes.re_static,
3201 tcx.mk_array(tcx.types.u8, v.len() as u64))
3203 ast::LitKind::Byte(_) => tcx.types.u8,
3204 ast::LitKind::Char(_) => tcx.types.char,
3205 ast::LitKind::Int(_, ast::LitIntType::Signed(t)) => tcx.mk_mach_int(t),
3206 ast::LitKind::Int(_, ast::LitIntType::Unsigned(t)) => tcx.mk_mach_uint(t),
3207 ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
3208 let opt_ty = expected.to_option(self).and_then(|ty| {
3210 ty::Int(_) | ty::Uint(_) => Some(ty),
3211 ty::Char => Some(tcx.types.u8),
3212 ty::RawPtr(..) => Some(tcx.types.usize),
3213 ty::FnDef(..) | ty::FnPtr(_) => Some(tcx.types.usize),
3217 opt_ty.unwrap_or_else(|| self.next_int_var())
3219 ast::LitKind::Float(_, t) => tcx.mk_mach_float(t),
3220 ast::LitKind::FloatUnsuffixed(_) => {
3221 let opt_ty = expected.to_option(self).and_then(|ty| {
3223 ty::Float(_) => Some(ty),
3227 opt_ty.unwrap_or_else(|| self.next_float_var())
3229 ast::LitKind::Bool(_) => tcx.types.bool,
3230 ast::LitKind::Err(_) => tcx.types.err,
3234 fn check_expr_eq_type(&self, expr: &'tcx hir::Expr, expected: Ty<'tcx>) {
3235 let ty = self.check_expr_with_hint(expr, expected);
3236 self.demand_eqtype(expr.span, expected, ty);
3239 pub fn check_expr_has_type_or_error(
3241 expr: &'tcx hir::Expr,
3244 self.check_expr_meets_expectation_or_error(expr, ExpectHasType(expected))
3247 fn check_expr_meets_expectation_or_error(
3249 expr: &'tcx hir::Expr,
3250 expected: Expectation<'tcx>,
3252 let expected_ty = expected.to_option(&self).unwrap_or(self.tcx.types.bool);
3253 let mut ty = self.check_expr_with_expectation(expr, expected);
3255 // While we don't allow *arbitrary* coercions here, we *do* allow
3256 // coercions from ! to `expected`.
3258 assert!(!self.tables.borrow().adjustments().contains_key(expr.hir_id),
3259 "expression with never type wound up being adjusted");
3260 let adj_ty = self.next_diverging_ty_var(
3261 TypeVariableOrigin {
3262 kind: TypeVariableOriginKind::AdjustmentType,
3266 self.apply_adjustments(expr, vec![Adjustment {
3267 kind: Adjust::NeverToAny,
3273 if let Some(mut err) = self.demand_suptype_diag(expr.span, expected_ty, ty) {
3274 let expr = match &expr.node {
3275 ExprKind::DropTemps(expr) => expr,
3278 // Error possibly reported in `check_assign` so avoid emitting error again.
3279 err.emit_unless(self.is_assign_to_bool(expr, expected_ty));
3284 fn check_expr_coercable_to_type(&self, expr: &'tcx hir::Expr, expected: Ty<'tcx>) -> Ty<'tcx> {
3285 let ty = self.check_expr_with_hint(expr, expected);
3286 // checks don't need two phase
3287 self.demand_coerce(expr, ty, expected, AllowTwoPhase::No)
3290 fn check_expr_with_hint(&self, expr: &'tcx hir::Expr, expected: Ty<'tcx>) -> Ty<'tcx> {
3291 self.check_expr_with_expectation(expr, ExpectHasType(expected))
3294 fn check_expr_with_expectation(
3296 expr: &'tcx hir::Expr,
3297 expected: Expectation<'tcx>,
3299 self.check_expr_with_expectation_and_needs(expr, expected, Needs::None)
3302 fn check_expr(&self, expr: &'tcx hir::Expr) -> Ty<'tcx> {
3303 self.check_expr_with_expectation(expr, NoExpectation)
3306 fn check_expr_with_needs(&self, expr: &'tcx hir::Expr, needs: Needs) -> Ty<'tcx> {
3307 self.check_expr_with_expectation_and_needs(expr, NoExpectation, needs)
3310 // Determine the `Self` type, using fresh variables for all variables
3311 // declared on the impl declaration e.g., `impl<A,B> for Vec<(A,B)>`
3312 // would return `($0, $1)` where `$0` and `$1` are freshly instantiated type
3314 pub fn impl_self_ty(&self,
3315 span: Span, // (potential) receiver for this impl
3317 -> TypeAndSubsts<'tcx> {
3318 let ity = self.tcx.type_of(did);
3319 debug!("impl_self_ty: ity={:?}", ity);
3321 let substs = self.fresh_substs_for_item(span, did);
3322 let substd_ty = self.instantiate_type_scheme(span, &substs, &ity);
3324 TypeAndSubsts { substs: substs, ty: substd_ty }
3327 /// Unifies the output type with the expected type early, for more coercions
3328 /// and forward type information on the input expressions.
3329 fn expected_inputs_for_expected_output(&self,
3331 expected_ret: Expectation<'tcx>,
3332 formal_ret: Ty<'tcx>,
3333 formal_args: &[Ty<'tcx>])
3335 let formal_ret = self.resolve_type_vars_with_obligations(formal_ret);
3336 let ret_ty = match expected_ret.only_has_type(self) {
3338 None => return Vec::new()
3340 let expect_args = self.fudge_inference_if_ok(|| {
3341 // Attempt to apply a subtyping relationship between the formal
3342 // return type (likely containing type variables if the function
3343 // is polymorphic) and the expected return type.
3344 // No argument expectations are produced if unification fails.
3345 let origin = self.misc(call_span);
3346 let ures = self.at(&origin, self.param_env).sup(ret_ty, &formal_ret);
3348 // FIXME(#27336) can't use ? here, Try::from_error doesn't default
3349 // to identity so the resulting type is not constrained.
3352 // Process any obligations locally as much as
3353 // we can. We don't care if some things turn
3354 // out unconstrained or ambiguous, as we're
3355 // just trying to get hints here.
3356 self.save_and_restore_in_snapshot_flag(|_| {
3357 let mut fulfill = TraitEngine::new(self.tcx);
3358 for obligation in ok.obligations {
3359 fulfill.register_predicate_obligation(self, obligation);
3361 fulfill.select_where_possible(self)
3362 }).map_err(|_| ())?;
3364 Err(_) => return Err(()),
3367 // Record all the argument types, with the substitutions
3368 // produced from the above subtyping unification.
3369 Ok(formal_args.iter().map(|ty| {
3370 self.resolve_vars_if_possible(ty)
3372 }).unwrap_or_default();
3373 debug!("expected_inputs_for_expected_output(formal={:?} -> {:?}, expected={:?} -> {:?})",
3374 formal_args, formal_ret,
3375 expect_args, expected_ret);
3379 // Checks a method call.
3380 fn check_method_call(
3382 expr: &'tcx hir::Expr,
3383 segment: &hir::PathSegment,
3385 args: &'tcx [hir::Expr],
3386 expected: Expectation<'tcx>,
3389 let rcvr = &args[0];
3390 let rcvr_t = self.check_expr_with_needs(&rcvr, needs);
3391 // no need to check for bot/err -- callee does that
3392 let rcvr_t = self.structurally_resolved_type(args[0].span, rcvr_t);
3394 let method = match self.lookup_method(rcvr_t,
3400 self.write_method_call(expr.hir_id, method);
3404 if segment.ident.name != kw::Invalid {
3405 self.report_method_error(span,
3408 SelfSource::MethodCall(rcvr),
3416 // Call the generic checker.
3417 self.check_method_argument_types(span,
3425 fn check_return_expr(&self, return_expr: &'tcx hir::Expr) {
3429 .unwrap_or_else(|| span_bug!(return_expr.span,
3430 "check_return_expr called outside fn body"));
3432 let ret_ty = ret_coercion.borrow().expected_ty();
3433 let return_expr_ty = self.check_expr_with_hint(return_expr, ret_ty.clone());
3434 ret_coercion.borrow_mut()
3436 &self.cause(return_expr.span,
3437 ObligationCauseCode::ReturnType(return_expr.hir_id)),
3442 // Check field access expressions
3445 expr: &'tcx hir::Expr,
3447 base: &'tcx hir::Expr,
3450 let expr_t = self.check_expr_with_needs(base, needs);
3451 let expr_t = self.structurally_resolved_type(base.span,
3453 let mut private_candidate = None;
3454 let mut autoderef = self.autoderef(expr.span, expr_t);
3455 while let Some((base_t, _)) = autoderef.next() {
3457 ty::Adt(base_def, substs) if !base_def.is_enum() => {
3458 debug!("struct named {:?}", base_t);
3459 let (ident, def_scope) =
3460 self.tcx.adjust_ident_and_get_scope(field, base_def.did, self.body_id);
3461 let fields = &base_def.non_enum_variant().fields;
3462 if let Some(index) = fields.iter().position(|f| f.ident.modern() == ident) {
3463 let field = &fields[index];
3464 let field_ty = self.field_ty(expr.span, field, substs);
3465 // Save the index of all fields regardless of their visibility in case
3466 // of error recovery.
3467 self.write_field_index(expr.hir_id, index);
3468 if field.vis.is_accessible_from(def_scope, self.tcx) {
3469 let adjustments = autoderef.adjust_steps(self, needs);
3470 self.apply_adjustments(base, adjustments);
3471 autoderef.finalize(self);
3473 self.tcx.check_stability(field.did, Some(expr.hir_id), expr.span);
3476 private_candidate = Some((base_def.did, field_ty));
3479 ty::Tuple(ref tys) => {
3480 let fstr = field.as_str();
3481 if let Ok(index) = fstr.parse::<usize>() {
3482 if fstr == index.to_string() {
3483 if let Some(field_ty) = tys.get(index) {
3484 let adjustments = autoderef.adjust_steps(self, needs);
3485 self.apply_adjustments(base, adjustments);
3486 autoderef.finalize(self);
3488 self.write_field_index(expr.hir_id, index);
3489 return field_ty.expect_ty();
3497 autoderef.unambiguous_final_ty(self);
3499 if let Some((did, field_ty)) = private_candidate {
3500 let struct_path = self.tcx().def_path_str(did);
3501 let mut err = struct_span_err!(self.tcx().sess, expr.span, E0616,
3502 "field `{}` of struct `{}` is private",
3503 field, struct_path);
3504 // Also check if an accessible method exists, which is often what is meant.
3505 if self.method_exists(field, expr_t, expr.hir_id, false)
3506 && !self.expr_in_place(expr.hir_id)
3508 self.suggest_method_call(
3510 &format!("a method `{}` also exists, call it with parentheses", field),
3518 } else if field.name == kw::Invalid {
3519 self.tcx().types.err
3520 } else if self.method_exists(field, expr_t, expr.hir_id, true) {
3521 let mut err = type_error_struct!(self.tcx().sess, field.span, expr_t, E0615,
3522 "attempted to take value of method `{}` on type `{}`",
3525 if !self.expr_in_place(expr.hir_id) {
3526 self.suggest_method_call(
3528 "use parentheses to call the method",
3534 err.help("methods are immutable and cannot be assigned to");
3538 self.tcx().types.err
3540 if !expr_t.is_primitive_ty() {
3541 let mut err = self.no_such_field_err(field.span, field, expr_t);
3544 ty::Adt(def, _) if !def.is_enum() => {
3545 if let Some(suggested_field_name) =
3546 Self::suggest_field_name(def.non_enum_variant(),
3547 &field.as_str(), vec![]) {
3548 err.span_suggestion(
3550 "a field with a similar name exists",
3551 suggested_field_name.to_string(),
3552 Applicability::MaybeIncorrect,
3555 err.span_label(field.span, "unknown field");
3556 let struct_variant_def = def.non_enum_variant();
3557 let field_names = self.available_field_names(struct_variant_def);
3558 if !field_names.is_empty() {
3559 err.note(&format!("available fields are: {}",
3560 self.name_series_display(field_names)));
3564 ty::Array(_, len) => {
3565 if let (Some(len), Ok(user_index)) = (
3566 len.assert_usize(self.tcx),
3567 field.as_str().parse::<u64>()
3569 let base = self.tcx.sess.source_map()
3570 .span_to_snippet(base.span)
3572 self.tcx.hir().hir_to_pretty_string(base.hir_id));
3573 let help = "instead of using tuple indexing, use array indexing";
3574 let suggestion = format!("{}[{}]", base, field);
3575 let applicability = if len < user_index {
3576 Applicability::MachineApplicable
3578 Applicability::MaybeIncorrect
3580 err.span_suggestion(
3581 expr.span, help, suggestion, applicability
3586 let base = self.tcx.sess.source_map()
3587 .span_to_snippet(base.span)
3588 .unwrap_or_else(|_| self.tcx.hir().hir_to_pretty_string(base.hir_id));
3589 let msg = format!("`{}` is a raw pointer; try dereferencing it", base);
3590 let suggestion = format!("(*{}).{}", base, field);
3591 err.span_suggestion(
3595 Applicability::MaybeIncorrect,
3602 type_error_struct!(self.tcx().sess, field.span, expr_t, E0610,
3603 "`{}` is a primitive type and therefore doesn't have fields",
3606 self.tcx().types.err
3610 // Return an hint about the closest match in field names
3611 fn suggest_field_name(variant: &'tcx ty::VariantDef,
3613 skip: Vec<LocalInternedString>)
3615 let names = variant.fields.iter().filter_map(|field| {
3616 // ignore already set fields and private fields from non-local crates
3617 if skip.iter().any(|x| *x == field.ident.as_str()) ||
3618 (!variant.def_id.is_local() && field.vis != Visibility::Public)
3622 Some(&field.ident.name)
3626 find_best_match_for_name(names, field, None)
3629 fn available_field_names(&self, variant: &'tcx ty::VariantDef) -> Vec<ast::Name> {
3630 variant.fields.iter().filter(|field| {
3632 self.tcx.adjust_ident_and_get_scope(field.ident, variant.def_id, self.body_id).1;
3633 field.vis.is_accessible_from(def_scope, self.tcx)
3635 .map(|field| field.ident.name)
3639 fn name_series_display(&self, names: Vec<ast::Name>) -> String {
3640 // dynamic limit, to never omit just one field
3641 let limit = if names.len() == 6 { 6 } else { 5 };
3642 let mut display = names.iter().take(limit)
3643 .map(|n| format!("`{}`", n)).collect::<Vec<_>>().join(", ");
3644 if names.len() > limit {
3645 display = format!("{} ... and {} others", display, names.len() - limit);
3650 fn no_such_field_err<T: Display>(&self, span: Span, field: T, expr_t: &ty::TyS<'_>)
3651 -> DiagnosticBuilder<'_> {
3652 type_error_struct!(self.tcx().sess, span, expr_t, E0609,
3653 "no field `{}` on type `{}`",
3657 fn report_unknown_field(
3660 variant: &'tcx ty::VariantDef,
3662 skip_fields: &[hir::Field],
3665 if variant.recovered {
3668 let mut err = self.type_error_struct_with_diag(
3670 |actual| match ty.sty {
3671 ty::Adt(adt, ..) if adt.is_enum() => {
3672 struct_span_err!(self.tcx.sess, field.ident.span, E0559,
3673 "{} `{}::{}` has no field named `{}`",
3674 kind_name, actual, variant.ident, field.ident)
3677 struct_span_err!(self.tcx.sess, field.ident.span, E0560,
3678 "{} `{}` has no field named `{}`",
3679 kind_name, actual, field.ident)
3683 // prevent all specified fields from being suggested
3684 let skip_fields = skip_fields.iter().map(|ref x| x.ident.as_str());
3685 if let Some(field_name) = Self::suggest_field_name(variant,
3686 &field.ident.as_str(),
3687 skip_fields.collect()) {
3688 err.span_suggestion(
3690 "a field with a similar name exists",
3691 field_name.to_string(),
3692 Applicability::MaybeIncorrect,
3696 ty::Adt(adt, ..) => {
3698 err.span_label(field.ident.span,
3699 format!("`{}::{}` does not have this field",
3700 ty, variant.ident));
3702 err.span_label(field.ident.span,
3703 format!("`{}` does not have this field", ty));
3705 let available_field_names = self.available_field_names(variant);
3706 if !available_field_names.is_empty() {
3707 err.note(&format!("available fields are: {}",
3708 self.name_series_display(available_field_names)));
3711 _ => bug!("non-ADT passed to report_unknown_field")
3717 fn check_expr_struct_fields(
3720 expected: Expectation<'tcx>,
3721 expr_id: hir::HirId,
3723 variant: &'tcx ty::VariantDef,
3724 ast_fields: &'tcx [hir::Field],
3725 check_completeness: bool,
3730 self.expected_inputs_for_expected_output(span, expected, adt_ty, &[adt_ty])
3731 .get(0).cloned().unwrap_or(adt_ty);
3732 // re-link the regions that EIfEO can erase.
3733 self.demand_eqtype(span, adt_ty_hint, adt_ty);
3735 let (substs, adt_kind, kind_name) = match &adt_ty.sty {
3736 &ty::Adt(adt, substs) => {
3737 (substs, adt.adt_kind(), adt.variant_descr())
3739 _ => span_bug!(span, "non-ADT passed to check_expr_struct_fields")
3742 let mut remaining_fields = variant.fields.iter().enumerate().map(|(i, field)|
3743 (field.ident.modern(), (i, field))
3744 ).collect::<FxHashMap<_, _>>();
3746 let mut seen_fields = FxHashMap::default();
3748 let mut error_happened = false;
3750 // Type-check each field.
3751 for field in ast_fields {
3752 let ident = tcx.adjust_ident(field.ident, variant.def_id);
3753 let field_type = if let Some((i, v_field)) = remaining_fields.remove(&ident) {
3754 seen_fields.insert(ident, field.span);
3755 self.write_field_index(field.hir_id, i);
3757 // We don't look at stability attributes on
3758 // struct-like enums (yet...), but it's definitely not
3759 // a bug to have constructed one.
3760 if adt_kind != AdtKind::Enum {
3761 tcx.check_stability(v_field.did, Some(expr_id), field.span);
3764 self.field_ty(field.span, v_field, substs)
3766 error_happened = true;
3767 if let Some(prev_span) = seen_fields.get(&ident) {
3768 let mut err = struct_span_err!(self.tcx.sess,
3771 "field `{}` specified more than once",
3774 err.span_label(field.ident.span, "used more than once");
3775 err.span_label(*prev_span, format!("first use of `{}`", ident));
3779 self.report_unknown_field(adt_ty, variant, field, ast_fields, kind_name);
3785 // Make sure to give a type to the field even if there's
3786 // an error, so we can continue type-checking.
3787 self.check_expr_coercable_to_type(&field.expr, field_type);
3790 // Make sure the programmer specified correct number of fields.
3791 if kind_name == "union" {
3792 if ast_fields.len() != 1 {
3793 tcx.sess.span_err(span, "union expressions should have exactly one field");
3795 } else if check_completeness && !error_happened && !remaining_fields.is_empty() {
3796 let len = remaining_fields.len();
3798 let mut displayable_field_names = remaining_fields
3800 .map(|ident| ident.as_str())
3801 .collect::<Vec<_>>();
3803 displayable_field_names.sort();
3805 let truncated_fields_error = if len <= 3 {
3808 format!(" and {} other field{}", (len - 3), if len - 3 == 1 {""} else {"s"})
3811 let remaining_fields_names = displayable_field_names.iter().take(3)
3812 .map(|n| format!("`{}`", n))
3813 .collect::<Vec<_>>()
3816 struct_span_err!(tcx.sess, span, E0063,
3817 "missing field{} {}{} in initializer of `{}`",
3818 if remaining_fields.len() == 1 { "" } else { "s" },
3819 remaining_fields_names,
3820 truncated_fields_error,
3822 .span_label(span, format!("missing {}{}",
3823 remaining_fields_names,
3824 truncated_fields_error))
3830 fn check_struct_fields_on_error(
3832 fields: &'tcx [hir::Field],
3833 base_expr: &'tcx Option<P<hir::Expr>>,
3835 for field in fields {
3836 self.check_expr(&field.expr);
3838 if let Some(ref base) = *base_expr {
3839 self.check_expr(&base);
3843 pub fn check_struct_path(&self,
3846 -> Option<(&'tcx ty::VariantDef, Ty<'tcx>)> {
3847 let path_span = match *qpath {
3848 QPath::Resolved(_, ref path) => path.span,
3849 QPath::TypeRelative(ref qself, _) => qself.span
3851 let (def, ty) = self.finish_resolving_struct_path(qpath, path_span, hir_id);
3852 let variant = match def {
3854 self.set_tainted_by_errors();
3857 Res::Def(DefKind::Variant, _) => {
3859 ty::Adt(adt, substs) => {
3860 Some((adt.variant_of_res(def), adt.did, substs))
3862 _ => bug!("unexpected type: {:?}", ty)
3865 Res::Def(DefKind::Struct, _)
3866 | Res::Def(DefKind::Union, _)
3867 | Res::Def(DefKind::TyAlias, _)
3868 | Res::Def(DefKind::AssocTy, _)
3869 | Res::SelfTy(..) => {
3871 ty::Adt(adt, substs) if !adt.is_enum() => {
3872 Some((adt.non_enum_variant(), adt.did, substs))
3877 _ => bug!("unexpected definition: {:?}", def)
3880 if let Some((variant, did, substs)) = variant {
3881 debug!("check_struct_path: did={:?} substs={:?}", did, substs);
3882 self.write_user_type_annotation_from_substs(hir_id, did, substs, None);
3884 // Check bounds on type arguments used in the path.
3885 let bounds = self.instantiate_bounds(path_span, did, substs);
3886 let cause = traits::ObligationCause::new(path_span, self.body_id,
3887 traits::ItemObligation(did));
3888 self.add_obligations_for_parameters(cause, &bounds);
3892 struct_span_err!(self.tcx.sess, path_span, E0071,
3893 "expected struct, variant or union type, found {}",
3894 ty.sort_string(self.tcx))
3895 .span_label(path_span, "not a struct")
3901 fn check_expr_struct(
3904 expected: Expectation<'tcx>,
3906 fields: &'tcx [hir::Field],
3907 base_expr: &'tcx Option<P<hir::Expr>>,
3909 // Find the relevant variant
3910 let (variant, adt_ty) =
3911 if let Some(variant_ty) = self.check_struct_path(qpath, expr.hir_id) {
3914 self.check_struct_fields_on_error(fields, base_expr);
3915 return self.tcx.types.err;
3918 let path_span = match *qpath {
3919 QPath::Resolved(_, ref path) => path.span,
3920 QPath::TypeRelative(ref qself, _) => qself.span
3923 // Prohibit struct expressions when non-exhaustive flag is set.
3924 let adt = adt_ty.ty_adt_def().expect("`check_struct_path` returned non-ADT type");
3925 if !adt.did.is_local() && variant.is_field_list_non_exhaustive() {
3926 span_err!(self.tcx.sess, expr.span, E0639,
3927 "cannot create non-exhaustive {} using struct expression",
3928 adt.variant_descr());
3931 let error_happened = self.check_expr_struct_fields(adt_ty, expected, expr.hir_id, path_span,
3932 variant, fields, base_expr.is_none());
3933 if let &Some(ref base_expr) = base_expr {
3934 // If check_expr_struct_fields hit an error, do not attempt to populate
3935 // the fields with the base_expr. This could cause us to hit errors later
3936 // when certain fields are assumed to exist that in fact do not.
3937 if !error_happened {
3938 self.check_expr_has_type_or_error(base_expr, adt_ty);
3940 ty::Adt(adt, substs) if adt.is_struct() => {
3941 let fru_field_types = adt.non_enum_variant().fields.iter().map(|f| {
3942 self.normalize_associated_types_in(expr.span, &f.ty(self.tcx, substs))
3947 .fru_field_types_mut()
3948 .insert(expr.hir_id, fru_field_types);
3951 span_err!(self.tcx.sess, base_expr.span, E0436,
3952 "functional record update syntax requires a struct");
3957 self.require_type_is_sized(adt_ty, expr.span, traits::StructInitializerSized);
3963 /// If an expression has any sub-expressions that result in a type error,
3964 /// inspecting that expression's type with `ty.references_error()` will return
3965 /// true. Likewise, if an expression is known to diverge, inspecting its
3966 /// type with `ty::type_is_bot` will return true (n.b.: since Rust is
3967 /// strict, _|_ can appear in the type of an expression that does not,
3968 /// itself, diverge: for example, fn() -> _|_.)
3969 /// Note that inspecting a type's structure *directly* may expose the fact
3970 /// that there are actually multiple representations for `Error`, so avoid
3971 /// that when err needs to be handled differently.
3972 fn check_expr_with_expectation_and_needs(
3974 expr: &'tcx hir::Expr,
3975 expected: Expectation<'tcx>,
3978 debug!(">> type-checking: expr={:?} expected={:?}",
3981 // Warn for expressions after diverging siblings.
3982 self.warn_if_unreachable(expr.hir_id, expr.span, "expression");
3984 // Hide the outer diverging and has_errors flags.
3985 let old_diverges = self.diverges.get();
3986 let old_has_errors = self.has_errors.get();
3987 self.diverges.set(Diverges::Maybe);
3988 self.has_errors.set(false);
3990 let ty = self.check_expr_kind(expr, expected, needs);
3992 // Warn for non-block expressions with diverging children.
3994 ExprKind::Block(..) |
3995 ExprKind::Loop(..) | ExprKind::While(..) |
3996 ExprKind::Match(..) => {}
3998 _ => self.warn_if_unreachable(expr.hir_id, expr.span, "expression")
4001 // Any expression that produces a value of type `!` must have diverged
4003 self.diverges.set(self.diverges.get() | Diverges::Always);
4006 // Record the type, which applies it effects.
4007 // We need to do this after the warning above, so that
4008 // we don't warn for the diverging expression itself.
4009 self.write_ty(expr.hir_id, ty);
4011 // Combine the diverging and has_error flags.
4012 self.diverges.set(self.diverges.get() | old_diverges);
4013 self.has_errors.set(self.has_errors.get() | old_has_errors);
4015 debug!("type of {} is...", self.tcx.hir().hir_to_string(expr.hir_id));
4016 debug!("... {:?}, expected is {:?}", ty, expected);
4023 expr: &'tcx hir::Expr,
4024 expected: Expectation<'tcx>,
4028 "check_expr_kind(expr={:?}, expected={:?}, needs={:?})",
4035 let id = expr.hir_id;
4037 ExprKind::Box(ref subexpr) => {
4038 let expected_inner = expected.to_option(self).map_or(NoExpectation, |ty| {
4040 ty::Adt(def, _) if def.is_box()
4041 => Expectation::rvalue_hint(self, ty.boxed_ty()),
4045 let referent_ty = self.check_expr_with_expectation(subexpr, expected_inner);
4046 tcx.mk_box(referent_ty)
4049 ExprKind::Lit(ref lit) => {
4050 self.check_lit(&lit, expected)
4052 ExprKind::Binary(op, ref lhs, ref rhs) => {
4053 self.check_binop(expr, op, lhs, rhs)
4055 ExprKind::AssignOp(op, ref lhs, ref rhs) => {
4056 self.check_binop_assign(expr, op, lhs, rhs)
4058 ExprKind::Unary(unop, ref oprnd) => {
4059 let expected_inner = match unop {
4060 hir::UnNot | hir::UnNeg => {
4067 let needs = match unop {
4068 hir::UnDeref => needs,
4071 let mut oprnd_t = self.check_expr_with_expectation_and_needs(&oprnd,
4075 if !oprnd_t.references_error() {
4076 oprnd_t = self.structurally_resolved_type(expr.span, oprnd_t);
4079 if let Some(mt) = oprnd_t.builtin_deref(true) {
4081 } else if let Some(ok) = self.try_overloaded_deref(
4082 expr.span, oprnd_t, needs) {
4083 let method = self.register_infer_ok_obligations(ok);
4084 if let ty::Ref(region, _, mutbl) = method.sig.inputs()[0].sty {
4085 let mutbl = match mutbl {
4086 hir::MutImmutable => AutoBorrowMutability::Immutable,
4087 hir::MutMutable => AutoBorrowMutability::Mutable {
4088 // (It shouldn't actually matter for unary ops whether
4089 // we enable two-phase borrows or not, since a unary
4090 // op has no additional operands.)
4091 allow_two_phase_borrow: AllowTwoPhase::No,
4094 self.apply_adjustments(oprnd, vec![Adjustment {
4095 kind: Adjust::Borrow(AutoBorrow::Ref(region, mutbl)),
4096 target: method.sig.inputs()[0]
4099 oprnd_t = self.make_overloaded_place_return_type(method).ty;
4100 self.write_method_call(expr.hir_id, method);
4102 let mut err = type_error_struct!(
4107 "type `{}` cannot be dereferenced",
4110 let sp = tcx.sess.source_map().start_point(expr.span);
4111 if let Some(sp) = tcx.sess.parse_sess.ambiguous_block_expr_parse
4114 tcx.sess.parse_sess.expr_parentheses_needed(
4121 oprnd_t = tcx.types.err;
4125 let result = self.check_user_unop(expr, oprnd_t, unop);
4126 // If it's builtin, we can reuse the type, this helps inference.
4127 if !(oprnd_t.is_integral() || oprnd_t.sty == ty::Bool) {
4132 let result = self.check_user_unop(expr, oprnd_t, unop);
4133 // If it's builtin, we can reuse the type, this helps inference.
4134 if !oprnd_t.is_numeric() {
4142 ExprKind::AddrOf(mutbl, ref oprnd) => {
4143 let hint = expected.only_has_type(self).map_or(NoExpectation, |ty| {
4145 ty::Ref(_, ty, _) | ty::RawPtr(ty::TypeAndMut { ty, .. }) => {
4146 if oprnd.is_place_expr() {
4147 // Places may legitimately have unsized types.
4148 // For example, dereferences of a fat pointer and
4149 // the last field of a struct can be unsized.
4152 Expectation::rvalue_hint(self, ty)
4158 let needs = Needs::maybe_mut_place(mutbl);
4159 let ty = self.check_expr_with_expectation_and_needs(&oprnd, hint, needs);
4161 let tm = ty::TypeAndMut { ty: ty, mutbl: mutbl };
4162 if tm.ty.references_error() {
4165 // Note: at this point, we cannot say what the best lifetime
4166 // is to use for resulting pointer. We want to use the
4167 // shortest lifetime possible so as to avoid spurious borrowck
4168 // errors. Moreover, the longest lifetime will depend on the
4169 // precise details of the value whose address is being taken
4170 // (and how long it is valid), which we don't know yet until type
4171 // inference is complete.
4173 // Therefore, here we simply generate a region variable. The
4174 // region inferencer will then select the ultimate value.
4175 // Finally, borrowck is charged with guaranteeing that the
4176 // value whose address was taken can actually be made to live
4177 // as long as it needs to live.
4178 let region = self.next_region_var(infer::AddrOfRegion(expr.span));
4179 tcx.mk_ref(region, tm)
4182 ExprKind::Path(ref qpath) => {
4183 let (res, opt_ty, segs) = self.resolve_ty_and_res_ufcs(qpath, expr.hir_id,
4185 let ty = match res {
4187 self.set_tainted_by_errors();
4190 Res::Def(DefKind::Ctor(_, CtorKind::Fictive), _) => {
4191 report_unexpected_variant_res(tcx, res, expr.span, qpath);
4194 _ => self.instantiate_value_path(segs, opt_ty, res, expr.span, id).0,
4197 if let ty::FnDef(..) = ty.sty {
4198 let fn_sig = ty.fn_sig(tcx);
4199 if !tcx.features().unsized_locals {
4200 // We want to remove some Sized bounds from std functions,
4201 // but don't want to expose the removal to stable Rust.
4202 // i.e., we don't want to allow
4208 // to work in stable even if the Sized bound on `drop` is relaxed.
4209 for i in 0..fn_sig.inputs().skip_binder().len() {
4210 // We just want to check sizedness, so instead of introducing
4211 // placeholder lifetimes with probing, we just replace higher lifetimes
4213 let input = self.replace_bound_vars_with_fresh_vars(
4215 infer::LateBoundRegionConversionTime::FnCall,
4216 &fn_sig.input(i)).0;
4217 self.require_type_is_sized_deferred(input, expr.span,
4218 traits::SizedArgumentType);
4221 // Here we want to prevent struct constructors from returning unsized types.
4222 // There were two cases this happened: fn pointer coercion in stable
4223 // and usual function call in presense of unsized_locals.
4224 // Also, as we just want to check sizedness, instead of introducing
4225 // placeholder lifetimes with probing, we just replace higher lifetimes
4227 let output = self.replace_bound_vars_with_fresh_vars(
4229 infer::LateBoundRegionConversionTime::FnCall,
4230 &fn_sig.output()).0;
4231 self.require_type_is_sized_deferred(output, expr.span, traits::SizedReturnType);
4234 // We always require that the type provided as the value for
4235 // a type parameter outlives the moment of instantiation.
4236 let substs = self.tables.borrow().node_substs(expr.hir_id);
4237 self.add_wf_bounds(substs, expr);
4241 ExprKind::InlineAsm(_, ref outputs, ref inputs) => {
4242 for expr in outputs.iter().chain(inputs.iter()) {
4243 self.check_expr(expr);
4247 ExprKind::Break(destination, ref expr_opt) => {
4248 if let Ok(target_id) = destination.target_id {
4250 if let Some(ref e) = *expr_opt {
4251 // If this is a break with a value, we need to type-check
4252 // the expression. Get an expected type from the loop context.
4253 let opt_coerce_to = {
4254 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4255 enclosing_breakables.find_breakable(target_id)
4258 .map(|coerce| coerce.expected_ty())
4261 // If the loop context is not a `loop { }`, then break with
4262 // a value is illegal, and `opt_coerce_to` will be `None`.
4263 // Just set expectation to error in that case.
4264 let coerce_to = opt_coerce_to.unwrap_or(tcx.types.err);
4266 // Recurse without `enclosing_breakables` borrowed.
4267 e_ty = self.check_expr_with_hint(e, coerce_to);
4268 cause = self.misc(e.span);
4270 // Otherwise, this is a break *without* a value. That's
4271 // always legal, and is equivalent to `break ()`.
4272 e_ty = tcx.mk_unit();
4273 cause = self.misc(expr.span);
4276 // Now that we have type-checked `expr_opt`, borrow
4277 // the `enclosing_loops` field and let's coerce the
4278 // type of `expr_opt` into what is expected.
4279 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4280 let ctxt = enclosing_breakables.find_breakable(target_id);
4281 if let Some(ref mut coerce) = ctxt.coerce {
4282 if let Some(ref e) = *expr_opt {
4283 coerce.coerce(self, &cause, e, e_ty);
4285 assert!(e_ty.is_unit());
4286 coerce.coerce_forced_unit(self, &cause, &mut |_| (), true);
4289 // If `ctxt.coerce` is `None`, we can just ignore
4290 // the type of the expresison. This is because
4291 // either this was a break *without* a value, in
4292 // which case it is always a legal type (`()`), or
4293 // else an error would have been flagged by the
4294 // `loops` pass for using break with an expression
4295 // where you are not supposed to.
4296 assert!(expr_opt.is_none() || self.tcx.sess.err_count() > 0);
4299 ctxt.may_break = true;
4301 // the type of a `break` is always `!`, since it diverges
4304 // Otherwise, we failed to find the enclosing loop;
4305 // this can only happen if the `break` was not
4306 // inside a loop at all, which is caught by the
4307 // loop-checking pass.
4308 if self.tcx.sess.err_count() == 0 {
4309 self.tcx.sess.delay_span_bug(expr.span,
4310 "break was outside loop, but no error was emitted");
4313 // We still need to assign a type to the inner expression to
4314 // prevent the ICE in #43162.
4315 if let Some(ref e) = *expr_opt {
4316 self.check_expr_with_hint(e, tcx.types.err);
4318 // ... except when we try to 'break rust;'.
4319 // ICE this expression in particular (see #43162).
4320 if let ExprKind::Path(QPath::Resolved(_, ref path)) = e.node {
4321 if path.segments.len() == 1 &&
4322 path.segments[0].ident.name == sym::rust {
4323 fatally_break_rust(self.tcx.sess);
4327 // There was an error; make type-check fail.
4332 ExprKind::Continue(destination) => {
4333 if destination.target_id.is_ok() {
4336 // There was an error; make type-check fail.
4340 ExprKind::Ret(ref expr_opt) => {
4341 if self.ret_coercion.is_none() {
4342 struct_span_err!(self.tcx.sess, expr.span, E0572,
4343 "return statement outside of function body").emit();
4344 } else if let Some(ref e) = *expr_opt {
4345 if self.ret_coercion_span.borrow().is_none() {
4346 *self.ret_coercion_span.borrow_mut() = Some(e.span);
4348 self.check_return_expr(e);
4350 let mut coercion = self.ret_coercion.as_ref().unwrap().borrow_mut();
4351 if self.ret_coercion_span.borrow().is_none() {
4352 *self.ret_coercion_span.borrow_mut() = Some(expr.span);
4354 let cause = self.cause(expr.span, ObligationCauseCode::ReturnNoExpression);
4355 if let Some((fn_decl, _)) = self.get_fn_decl(expr.hir_id) {
4356 coercion.coerce_forced_unit(
4361 fn_decl.output.span(),
4363 "expected `{}` because of this return type",
4371 coercion.coerce_forced_unit(self, &cause, &mut |_| (), true);
4376 ExprKind::Assign(ref lhs, ref rhs) => {
4377 self.check_assign(expr, expected, lhs, rhs)
4379 ExprKind::While(ref cond, ref body, _) => {
4380 let ctxt = BreakableCtxt {
4381 // cannot use break with a value from a while loop
4383 may_break: false, // Will get updated if/when we find a `break`.
4386 let (ctxt, ()) = self.with_breakable_ctxt(expr.hir_id, ctxt, || {
4387 self.check_expr_has_type_or_error(&cond, tcx.types.bool);
4388 let cond_diverging = self.diverges.get();
4389 self.check_block_no_value(&body);
4391 // We may never reach the body so it diverging means nothing.
4392 self.diverges.set(cond_diverging);
4396 // No way to know whether it's diverging because
4397 // of a `break` or an outer `break` or `return`.
4398 self.diverges.set(Diverges::Maybe);
4403 ExprKind::Loop(ref body, _, source) => {
4404 let coerce = match source {
4405 // you can only use break with a value from a normal `loop { }`
4406 hir::LoopSource::Loop => {
4407 let coerce_to = expected.coercion_target_type(self, body.span);
4408 Some(CoerceMany::new(coerce_to))
4411 hir::LoopSource::WhileLet |
4412 hir::LoopSource::ForLoop => {
4417 let ctxt = BreakableCtxt {
4419 may_break: false, // Will get updated if/when we find a `break`.
4422 let (ctxt, ()) = self.with_breakable_ctxt(expr.hir_id, ctxt, || {
4423 self.check_block_no_value(&body);
4427 // No way to know whether it's diverging because
4428 // of a `break` or an outer `break` or `return`.
4429 self.diverges.set(Diverges::Maybe);
4432 // If we permit break with a value, then result type is
4433 // the LUB of the breaks (possibly ! if none); else, it
4434 // is nil. This makes sense because infinite loops
4435 // (which would have type !) are only possible iff we
4436 // permit break with a value [1].
4437 if ctxt.coerce.is_none() && !ctxt.may_break {
4439 self.tcx.sess.delay_span_bug(body.span, "no coercion, but loop may not break");
4441 ctxt.coerce.map(|c| c.complete(self)).unwrap_or_else(|| self.tcx.mk_unit())
4443 ExprKind::Match(ref discrim, ref arms, match_src) => {
4444 self.check_match(expr, &discrim, arms, expected, match_src)
4446 ExprKind::Closure(capture, ref decl, body_id, _, gen) => {
4447 self.check_expr_closure(expr, capture, &decl, body_id, gen, expected)
4449 ExprKind::Block(ref body, _) => {
4450 self.check_block_with_expected(&body, expected)
4452 ExprKind::Call(ref callee, ref args) => {
4453 self.check_call(expr, &callee, args, expected)
4455 ExprKind::MethodCall(ref segment, span, ref args) => {
4456 self.check_method_call(expr, segment, span, args, expected, needs)
4458 ExprKind::Cast(ref e, ref t) => {
4459 // Find the type of `e`. Supply hints based on the type we are casting to,
4461 let t_cast = self.to_ty_saving_user_provided_ty(t);
4462 let t_cast = self.resolve_vars_if_possible(&t_cast);
4463 let t_expr = self.check_expr_with_expectation(e, ExpectCastableToType(t_cast));
4464 let t_cast = self.resolve_vars_if_possible(&t_cast);
4466 // Eagerly check for some obvious errors.
4467 if t_expr.references_error() || t_cast.references_error() {
4470 // Defer other checks until we're done type checking.
4471 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
4472 match cast::CastCheck::new(self, e, t_expr, t_cast, t.span, expr.span) {
4474 deferred_cast_checks.push(cast_check);
4477 Err(ErrorReported) => {
4483 ExprKind::Type(ref e, ref t) => {
4484 let ty = self.to_ty_saving_user_provided_ty(&t);
4485 self.check_expr_eq_type(&e, ty);
4488 ExprKind::DropTemps(ref e) => {
4489 self.check_expr_with_expectation(e, expected)
4491 ExprKind::Array(ref args) => {
4492 let uty = expected.to_option(self).and_then(|uty| {
4494 ty::Array(ty, _) | ty::Slice(ty) => Some(ty),
4499 let element_ty = if !args.is_empty() {
4500 let coerce_to = uty.unwrap_or_else(|| {
4501 self.next_ty_var(TypeVariableOrigin {
4502 kind: TypeVariableOriginKind::TypeInference,
4506 let mut coerce = CoerceMany::with_coercion_sites(coerce_to, args);
4507 assert_eq!(self.diverges.get(), Diverges::Maybe);
4509 let e_ty = self.check_expr_with_hint(e, coerce_to);
4510 let cause = self.misc(e.span);
4511 coerce.coerce(self, &cause, e, e_ty);
4513 coerce.complete(self)
4515 self.next_ty_var(TypeVariableOrigin {
4516 kind: TypeVariableOriginKind::TypeInference,
4520 tcx.mk_array(element_ty, args.len() as u64)
4522 ExprKind::Repeat(ref element, ref count) => {
4523 let count_def_id = tcx.hir().local_def_id_from_hir_id(count.hir_id);
4524 let count = if self.const_param_def_id(count).is_some() {
4525 Ok(self.to_const(count, self.tcx.type_of(count_def_id)))
4527 let param_env = ty::ParamEnv::empty();
4528 let substs = InternalSubsts::identity_for_item(tcx.global_tcx(), count_def_id);
4529 let instance = ty::Instance::resolve(
4535 let global_id = GlobalId {
4540 tcx.const_eval(param_env.and(global_id))
4543 let uty = match expected {
4544 ExpectHasType(uty) => {
4546 ty::Array(ty, _) | ty::Slice(ty) => Some(ty),
4553 let (element_ty, t) = match uty {
4555 self.check_expr_coercable_to_type(&element, uty);
4559 let ty = self.next_ty_var(TypeVariableOrigin {
4560 kind: TypeVariableOriginKind::MiscVariable,
4563 let element_ty = self.check_expr_has_type_or_error(&element, ty);
4568 if let Ok(count) = count {
4569 let zero_or_one = count.assert_usize(tcx).map_or(false, |count| count <= 1);
4571 // For [foo, ..n] where n > 1, `foo` must have
4573 let lang_item = self.tcx.require_lang_item(lang_items::CopyTraitLangItem);
4574 self.require_type_meets(t, expr.span, traits::RepeatVec, lang_item);
4578 if element_ty.references_error() {
4580 } else if let Ok(count) = count {
4581 tcx.mk_ty(ty::Array(t, count))
4586 ExprKind::Tup(ref elts) => {
4587 let flds = expected.only_has_type(self).and_then(|ty| {
4588 let ty = self.resolve_type_vars_with_obligations(ty);
4590 ty::Tuple(ref flds) => Some(&flds[..]),
4595 let elt_ts_iter = elts.iter().enumerate().map(|(i, e)| {
4596 let t = match flds {
4597 Some(ref fs) if i < fs.len() => {
4598 let ety = fs[i].expect_ty();
4599 self.check_expr_coercable_to_type(&e, ety);
4603 self.check_expr_with_expectation(&e, NoExpectation)
4608 let tuple = tcx.mk_tup(elt_ts_iter);
4609 if tuple.references_error() {
4612 self.require_type_is_sized(tuple, expr.span, traits::TupleInitializerSized);
4616 ExprKind::Struct(ref qpath, ref fields, ref base_expr) => {
4617 self.check_expr_struct(expr, expected, qpath, fields, base_expr)
4619 ExprKind::Field(ref base, field) => {
4620 self.check_field(expr, needs, &base, field)
4622 ExprKind::Index(ref base, ref idx) => {
4623 let base_t = self.check_expr_with_needs(&base, needs);
4624 let idx_t = self.check_expr(&idx);
4626 if base_t.references_error() {
4628 } else if idx_t.references_error() {
4631 let base_t = self.structurally_resolved_type(base.span, base_t);
4632 match self.lookup_indexing(expr, base, base_t, idx_t, needs) {
4633 Some((index_ty, element_ty)) => {
4634 // two-phase not needed because index_ty is never mutable
4635 self.demand_coerce(idx, idx_t, index_ty, AllowTwoPhase::No);
4640 type_error_struct!(tcx.sess, expr.span, base_t, E0608,
4641 "cannot index into a value of type `{}`",
4643 // Try to give some advice about indexing tuples.
4644 if let ty::Tuple(..) = base_t.sty {
4645 let mut needs_note = true;
4646 // If the index is an integer, we can show the actual
4647 // fixed expression:
4648 if let ExprKind::Lit(ref lit) = idx.node {
4649 if let ast::LitKind::Int(i,
4650 ast::LitIntType::Unsuffixed) = lit.node {
4651 let snip = tcx.sess.source_map().span_to_snippet(base.span);
4652 if let Ok(snip) = snip {
4653 err.span_suggestion(
4655 "to access tuple elements, use",
4656 format!("{}.{}", snip, i),
4657 Applicability::MachineApplicable,
4664 err.help("to access tuple elements, use tuple indexing \
4665 syntax (e.g., `tuple.0`)");
4674 ExprKind::Yield(ref value) => {
4675 match self.yield_ty {
4677 self.check_expr_coercable_to_type(&value, ty);
4680 struct_span_err!(self.tcx.sess, expr.span, E0627,
4681 "yield statement outside of generator literal").emit();
4686 hir::ExprKind::Err => {
4692 /// Type check assignment expression `expr` of form `lhs = rhs`.
4693 /// The expected type is `()` and is passsed to the function for the purposes of diagnostics.
4696 expr: &'tcx hir::Expr,
4697 expected: Expectation<'tcx>,
4698 lhs: &'tcx hir::Expr,
4699 rhs: &'tcx hir::Expr,
4701 let lhs_ty = self.check_expr_with_needs(&lhs, Needs::MutPlace);
4702 let rhs_ty = self.check_expr_coercable_to_type(&rhs, lhs_ty);
4704 let expected_ty = expected.coercion_target_type(self, expr.span);
4705 if expected_ty == self.tcx.types.bool {
4706 // The expected type is `bool` but this will result in `()` so we can reasonably
4707 // say that the user intended to write `lhs == rhs` instead of `lhs = rhs`.
4708 // The likely cause of this is `if foo = bar { .. }`.
4709 let actual_ty = self.tcx.mk_unit();
4710 let mut err = self.demand_suptype_diag(expr.span, expected_ty, actual_ty).unwrap();
4711 let msg = "try comparing for equality";
4712 let left = self.tcx.sess.source_map().span_to_snippet(lhs.span);
4713 let right = self.tcx.sess.source_map().span_to_snippet(rhs.span);
4714 if let (Ok(left), Ok(right)) = (left, right) {
4715 let help = format!("{} == {}", left, right);
4716 err.span_suggestion(expr.span, msg, help, Applicability::MaybeIncorrect);
4721 } else if !lhs.is_place_expr() {
4722 struct_span_err!(self.tcx.sess, expr.span, E0070,
4723 "invalid left-hand side expression")
4724 .span_label(expr.span, "left-hand of expression not valid")
4728 self.require_type_is_sized(lhs_ty, lhs.span, traits::AssignmentLhsSized);
4730 if lhs_ty.references_error() || rhs_ty.references_error() {
4737 // Finish resolving a path in a struct expression or pattern `S::A { .. }` if necessary.
4738 // The newly resolved definition is written into `type_dependent_defs`.
4739 fn finish_resolving_struct_path(&self,
4746 QPath::Resolved(ref maybe_qself, ref path) => {
4747 let self_ty = maybe_qself.as_ref().map(|qself| self.to_ty(qself));
4748 let ty = AstConv::res_to_ty(self, self_ty, path, true);
4751 QPath::TypeRelative(ref qself, ref segment) => {
4752 let ty = self.to_ty(qself);
4754 let res = if let hir::TyKind::Path(QPath::Resolved(_, ref path)) = qself.node {
4759 let result = AstConv::associated_path_to_ty(
4768 let ty = result.map(|(ty, _, _)| ty).unwrap_or(self.tcx().types.err);
4769 let result = result.map(|(_, kind, def_id)| (kind, def_id));
4771 // Write back the new resolution.
4772 self.write_resolution(hir_id, result);
4774 (result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err), ty)
4779 /// Resolves associated value path into a base type and associated constant or method
4780 /// resolution. The newly resolved definition is written into `type_dependent_defs`.
4781 pub fn resolve_ty_and_res_ufcs<'b>(&self,
4785 -> (Res, Option<Ty<'tcx>>, &'b [hir::PathSegment])
4787 debug!("resolve_ty_and_res_ufcs: qpath={:?} hir_id={:?} span={:?}", qpath, hir_id, span);
4788 let (ty, qself, item_segment) = match *qpath {
4789 QPath::Resolved(ref opt_qself, ref path) => {
4791 opt_qself.as_ref().map(|qself| self.to_ty(qself)),
4792 &path.segments[..]);
4794 QPath::TypeRelative(ref qself, ref segment) => {
4795 (self.to_ty(qself), qself, segment)
4798 if let Some(&cached_result) = self.tables.borrow().type_dependent_defs().get(hir_id) {
4799 // Return directly on cache hit. This is useful to avoid doubly reporting
4800 // errors with default match binding modes. See #44614.
4801 let def = cached_result.map(|(kind, def_id)| Res::Def(kind, def_id))
4802 .unwrap_or(Res::Err);
4803 return (def, Some(ty), slice::from_ref(&**item_segment));
4805 let item_name = item_segment.ident;
4806 let result = self.resolve_ufcs(span, item_name, ty, hir_id).or_else(|error| {
4807 let result = match error {
4808 method::MethodError::PrivateMatch(kind, def_id, _) => Ok((kind, def_id)),
4809 _ => Err(ErrorReported),
4811 if item_name.name != kw::Invalid {
4812 self.report_method_error(
4816 SelfSource::QPath(qself),
4824 // Write back the new resolution.
4825 self.write_resolution(hir_id, result);
4827 result.map(|(kind, def_id)| Res::Def(kind, def_id)).unwrap_or(Res::Err),
4829 slice::from_ref(&**item_segment),
4833 pub fn check_decl_initializer(
4835 local: &'tcx hir::Local,
4836 init: &'tcx hir::Expr,
4838 // FIXME(tschottdorf): `contains_explicit_ref_binding()` must be removed
4839 // for #42640 (default match binding modes).
4842 let ref_bindings = local.pat.contains_explicit_ref_binding();
4844 let local_ty = self.local_ty(init.span, local.hir_id).revealed_ty;
4845 if let Some(m) = ref_bindings {
4846 // Somewhat subtle: if we have a `ref` binding in the pattern,
4847 // we want to avoid introducing coercions for the RHS. This is
4848 // both because it helps preserve sanity and, in the case of
4849 // ref mut, for soundness (issue #23116). In particular, in
4850 // the latter case, we need to be clear that the type of the
4851 // referent for the reference that results is *equal to* the
4852 // type of the place it is referencing, and not some
4853 // supertype thereof.
4854 let init_ty = self.check_expr_with_needs(init, Needs::maybe_mut_place(m));
4855 self.demand_eqtype(init.span, local_ty, init_ty);
4858 self.check_expr_coercable_to_type(init, local_ty)
4862 pub fn check_decl_local(&self, local: &'tcx hir::Local) {
4863 let t = self.local_ty(local.span, local.hir_id).decl_ty;
4864 self.write_ty(local.hir_id, t);
4866 if let Some(ref init) = local.init {
4867 let init_ty = self.check_decl_initializer(local, &init);
4868 if init_ty.references_error() {
4869 self.write_ty(local.hir_id, init_ty);
4873 self.check_pat_walk(
4876 ty::BindingMode::BindByValue(hir::Mutability::MutImmutable),
4879 let pat_ty = self.node_ty(local.pat.hir_id);
4880 if pat_ty.references_error() {
4881 self.write_ty(local.hir_id, pat_ty);
4885 pub fn check_stmt(&self, stmt: &'tcx hir::Stmt) {
4886 // Don't do all the complex logic below for `DeclItem`.
4888 hir::StmtKind::Item(..) => return,
4889 hir::StmtKind::Local(..) | hir::StmtKind::Expr(..) | hir::StmtKind::Semi(..) => {}
4892 self.warn_if_unreachable(stmt.hir_id, stmt.span, "statement");
4894 // Hide the outer diverging and `has_errors` flags.
4895 let old_diverges = self.diverges.get();
4896 let old_has_errors = self.has_errors.get();
4897 self.diverges.set(Diverges::Maybe);
4898 self.has_errors.set(false);
4901 hir::StmtKind::Local(ref l) => {
4902 self.check_decl_local(&l);
4905 hir::StmtKind::Item(_) => {}
4906 hir::StmtKind::Expr(ref expr) => {
4907 // Check with expected type of `()`.
4908 self.check_expr_has_type_or_error(&expr, self.tcx.mk_unit());
4910 hir::StmtKind::Semi(ref expr) => {
4911 self.check_expr(&expr);
4915 // Combine the diverging and `has_error` flags.
4916 self.diverges.set(self.diverges.get() | old_diverges);
4917 self.has_errors.set(self.has_errors.get() | old_has_errors);
4920 pub fn check_block_no_value(&self, blk: &'tcx hir::Block) {
4921 let unit = self.tcx.mk_unit();
4922 let ty = self.check_block_with_expected(blk, ExpectHasType(unit));
4924 // if the block produces a `!` value, that can always be
4925 // (effectively) coerced to unit.
4927 self.demand_suptype(blk.span, unit, ty);
4931 fn check_block_with_expected(
4933 blk: &'tcx hir::Block,
4934 expected: Expectation<'tcx>,
4937 let mut fcx_ps = self.ps.borrow_mut();
4938 let unsafety_state = fcx_ps.recurse(blk);
4939 replace(&mut *fcx_ps, unsafety_state)
4942 // In some cases, blocks have just one exit, but other blocks
4943 // can be targeted by multiple breaks. This can happen both
4944 // with labeled blocks as well as when we desugar
4945 // a `try { ... }` expression.
4949 // 'a: { if true { break 'a Err(()); } Ok(()) }
4951 // Here we would wind up with two coercions, one from
4952 // `Err(())` and the other from the tail expression
4953 // `Ok(())`. If the tail expression is omitted, that's a
4954 // "forced unit" -- unless the block diverges, in which
4955 // case we can ignore the tail expression (e.g., `'a: {
4956 // break 'a 22; }` would not force the type of the block
4958 let tail_expr = blk.expr.as_ref();
4959 let coerce_to_ty = expected.coercion_target_type(self, blk.span);
4960 let coerce = if blk.targeted_by_break {
4961 CoerceMany::new(coerce_to_ty)
4963 let tail_expr: &[P<hir::Expr>] = match tail_expr {
4964 Some(e) => slice::from_ref(e),
4967 CoerceMany::with_coercion_sites(coerce_to_ty, tail_expr)
4970 let prev_diverges = self.diverges.get();
4971 let ctxt = BreakableCtxt {
4972 coerce: Some(coerce),
4976 let (ctxt, ()) = self.with_breakable_ctxt(blk.hir_id, ctxt, || {
4977 for s in &blk.stmts {
4981 // check the tail expression **without** holding the
4982 // `enclosing_breakables` lock below.
4983 let tail_expr_ty = tail_expr.map(|t| self.check_expr_with_expectation(t, expected));
4985 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4986 let ctxt = enclosing_breakables.find_breakable(blk.hir_id);
4987 let coerce = ctxt.coerce.as_mut().unwrap();
4988 if let Some(tail_expr_ty) = tail_expr_ty {
4989 let tail_expr = tail_expr.unwrap();
4990 let cause = self.cause(tail_expr.span,
4991 ObligationCauseCode::BlockTailExpression(blk.hir_id));
4997 // Subtle: if there is no explicit tail expression,
4998 // that is typically equivalent to a tail expression
4999 // of `()` -- except if the block diverges. In that
5000 // case, there is no value supplied from the tail
5001 // expression (assuming there are no other breaks,
5002 // this implies that the type of the block will be
5005 // #41425 -- label the implicit `()` as being the
5006 // "found type" here, rather than the "expected type".
5007 if !self.diverges.get().always() {
5008 // #50009 -- Do not point at the entire fn block span, point at the return type
5009 // span, as it is the cause of the requirement, and
5010 // `consider_hint_about_removing_semicolon` will point at the last expression
5011 // if it were a relevant part of the error. This improves usability in editors
5012 // that highlight errors inline.
5013 let mut sp = blk.span;
5014 let mut fn_span = None;
5015 if let Some((decl, ident)) = self.get_parent_fn_decl(blk.hir_id) {
5016 let ret_sp = decl.output.span();
5017 if let Some(block_sp) = self.parent_item_span(blk.hir_id) {
5018 // HACK: on some cases (`ui/liveness/liveness-issue-2163.rs`) the
5019 // output would otherwise be incorrect and even misleading. Make sure
5020 // the span we're aiming at correspond to a `fn` body.
5021 if block_sp == blk.span {
5023 fn_span = Some(ident.span);
5027 coerce.coerce_forced_unit(self, &self.misc(sp), &mut |err| {
5028 if let Some(expected_ty) = expected.only_has_type(self) {
5029 self.consider_hint_about_removing_semicolon(blk, expected_ty, err);
5031 if let Some(fn_span) = fn_span {
5032 err.span_label(fn_span, "this function's body doesn't return");
5040 // If we can break from the block, then the block's exit is always reachable
5041 // (... as long as the entry is reachable) - regardless of the tail of the block.
5042 self.diverges.set(prev_diverges);
5045 let mut ty = ctxt.coerce.unwrap().complete(self);
5047 if self.has_errors.get() || ty.references_error() {
5048 ty = self.tcx.types.err
5051 self.write_ty(blk.hir_id, ty);
5053 *self.ps.borrow_mut() = prev;
5057 fn parent_item_span(&self, id: hir::HirId) -> Option<Span> {
5058 let node = self.tcx.hir().get_by_hir_id(self.tcx.hir().get_parent_item(id));
5060 Node::Item(&hir::Item {
5061 node: hir::ItemKind::Fn(_, _, _, body_id), ..
5063 Node::ImplItem(&hir::ImplItem {
5064 node: hir::ImplItemKind::Method(_, body_id), ..
5066 let body = self.tcx.hir().body(body_id);
5067 if let ExprKind::Block(block, _) = &body.value.node {
5068 return Some(block.span);
5076 /// Given a function block's `HirId`, returns its `FnDecl` if it exists, or `None` otherwise.
5077 fn get_parent_fn_decl(&self, blk_id: hir::HirId) -> Option<(hir::FnDecl, ast::Ident)> {
5078 let parent = self.tcx.hir().get_by_hir_id(self.tcx.hir().get_parent_item(blk_id));
5079 self.get_node_fn_decl(parent).map(|(fn_decl, ident, _)| (fn_decl, ident))
5082 /// Given a function `Node`, return its `FnDecl` if it exists, or `None` otherwise.
5083 fn get_node_fn_decl(&self, node: Node<'_>) -> Option<(hir::FnDecl, ast::Ident, bool)> {
5085 Node::Item(&hir::Item {
5086 ident, node: hir::ItemKind::Fn(ref decl, ..), ..
5087 }) => decl.clone().and_then(|decl| {
5088 // This is less than ideal, it will not suggest a return type span on any
5089 // method called `main`, regardless of whether it is actually the entry point,
5090 // but it will still present it as the reason for the expected type.
5091 Some((decl, ident, ident.name != sym::main))
5093 Node::TraitItem(&hir::TraitItem {
5094 ident, node: hir::TraitItemKind::Method(hir::MethodSig {
5097 }) => decl.clone().and_then(|decl| Some((decl, ident, true))),
5098 Node::ImplItem(&hir::ImplItem {
5099 ident, node: hir::ImplItemKind::Method(hir::MethodSig {
5102 }) => decl.clone().and_then(|decl| Some((decl, ident, false))),
5107 /// Given a `HirId`, return the `FnDecl` of the method it is enclosed by and whether a
5108 /// suggestion can be made, `None` otherwise.
5109 pub fn get_fn_decl(&self, blk_id: hir::HirId) -> Option<(hir::FnDecl, bool)> {
5110 // Get enclosing Fn, if it is a function or a trait method, unless there's a `loop` or
5111 // `while` before reaching it, as block tail returns are not available in them.
5112 self.tcx.hir().get_return_block(blk_id).and_then(|blk_id| {
5113 let parent = self.tcx.hir().get_by_hir_id(blk_id);
5114 self.get_node_fn_decl(parent).map(|(fn_decl, _, is_main)| (fn_decl, is_main))
5118 /// On implicit return expressions with mismatched types, provides the following suggestions:
5120 /// - Points out the method's return type as the reason for the expected type.
5121 /// - Possible missing semicolon.
5122 /// - Possible missing return type if the return type is the default, and not `fn main()`.
5123 pub fn suggest_mismatched_types_on_tail(
5125 err: &mut DiagnosticBuilder<'tcx>,
5126 expression: &'tcx hir::Expr,
5132 self.suggest_missing_semicolon(err, expression, expected, cause_span);
5133 let mut pointing_at_return_type = false;
5134 if let Some((fn_decl, can_suggest)) = self.get_fn_decl(blk_id) {
5135 pointing_at_return_type = self.suggest_missing_return_type(
5136 err, &fn_decl, expected, found, can_suggest);
5138 self.suggest_ref_or_into(err, expression, expected, found);
5139 pointing_at_return_type
5142 pub fn suggest_ref_or_into(
5144 err: &mut DiagnosticBuilder<'tcx>,
5149 if let Some((sp, msg, suggestion)) = self.check_ref(expr, found, expected) {
5150 err.span_suggestion(
5154 Applicability::MachineApplicable,
5156 } else if !self.check_for_cast(err, expr, found, expected) {
5157 let is_struct_pat_shorthand_field = self.is_hir_id_from_struct_pattern_shorthand_field(
5161 let methods = self.get_conversion_methods(expr.span, expected, found);
5162 if let Ok(expr_text) = self.sess().source_map().span_to_snippet(expr.span) {
5163 let mut suggestions = iter::repeat(&expr_text).zip(methods.iter())
5164 .filter_map(|(receiver, method)| {
5165 let method_call = format!(".{}()", method.ident);
5166 if receiver.ends_with(&method_call) {
5167 None // do not suggest code that is already there (#53348)
5169 let method_call_list = [".to_vec()", ".to_string()"];
5170 let sugg = if receiver.ends_with(".clone()")
5171 && method_call_list.contains(&method_call.as_str()) {
5172 let max_len = receiver.rfind(".").unwrap();
5173 format!("{}{}", &receiver[..max_len], method_call)
5175 format!("{}{}", receiver, method_call)
5177 Some(if is_struct_pat_shorthand_field {
5178 format!("{}: {}", receiver, sugg)
5184 if suggestions.peek().is_some() {
5185 err.span_suggestions(
5187 "try using a conversion method",
5189 Applicability::MaybeIncorrect,
5196 /// A common error is to forget to add a semicolon at the end of a block, e.g.,
5200 /// bar_that_returns_u32()
5204 /// This routine checks if the return expression in a block would make sense on its own as a
5205 /// statement and the return type has been left as default or has been specified as `()`. If so,
5206 /// it suggests adding a semicolon.
5207 fn suggest_missing_semicolon(
5209 err: &mut DiagnosticBuilder<'tcx>,
5210 expression: &'tcx hir::Expr,
5214 if expected.is_unit() {
5215 // `BlockTailExpression` only relevant if the tail expr would be
5216 // useful on its own.
5217 match expression.node {
5218 ExprKind::Call(..) |
5219 ExprKind::MethodCall(..) |
5220 ExprKind::While(..) |
5221 ExprKind::Loop(..) |
5222 ExprKind::Match(..) |
5223 ExprKind::Block(..) => {
5224 let sp = self.tcx.sess.source_map().next_point(cause_span);
5225 err.span_suggestion(
5227 "try adding a semicolon",
5229 Applicability::MachineApplicable);
5236 /// A possible error is to forget to add a return type that is needed:
5240 /// bar_that_returns_u32()
5244 /// This routine checks if the return type is left as default, the method is not part of an
5245 /// `impl` block and that it isn't the `main` method. If so, it suggests setting the return
5247 fn suggest_missing_return_type(
5249 err: &mut DiagnosticBuilder<'tcx>,
5250 fn_decl: &hir::FnDecl,
5255 // Only suggest changing the return type for methods that
5256 // haven't set a return type at all (and aren't `fn main()` or an impl).
5257 match (&fn_decl.output, found.is_suggestable(), can_suggest, expected.is_unit()) {
5258 (&hir::FunctionRetTy::DefaultReturn(span), true, true, true) => {
5259 err.span_suggestion(
5261 "try adding a return type",
5262 format!("-> {} ", self.resolve_type_vars_with_obligations(found)),
5263 Applicability::MachineApplicable);
5266 (&hir::FunctionRetTy::DefaultReturn(span), false, true, true) => {
5267 err.span_label(span, "possibly return type missing here?");
5270 (&hir::FunctionRetTy::DefaultReturn(span), _, false, true) => {
5271 // `fn main()` must return `()`, do not suggest changing return type
5272 err.span_label(span, "expected `()` because of default return type");
5275 // expectation was caused by something else, not the default return
5276 (&hir::FunctionRetTy::DefaultReturn(_), _, _, false) => false,
5277 (&hir::FunctionRetTy::Return(ref ty), _, _, _) => {
5278 // Only point to return type if the expected type is the return type, as if they
5279 // are not, the expectation must have been caused by something else.
5280 debug!("suggest_missing_return_type: return type {:?} node {:?}", ty, ty.node);
5282 let ty = AstConv::ast_ty_to_ty(self, ty);
5283 debug!("suggest_missing_return_type: return type {:?}", ty);
5284 debug!("suggest_missing_return_type: expected type {:?}", ty);
5285 if ty.sty == expected.sty {
5286 err.span_label(sp, format!("expected `{}` because of return type",
5295 /// A common error is to add an extra semicolon:
5298 /// fn foo() -> usize {
5303 /// This routine checks if the final statement in a block is an
5304 /// expression with an explicit semicolon whose type is compatible
5305 /// with `expected_ty`. If so, it suggests removing the semicolon.
5306 fn consider_hint_about_removing_semicolon(
5308 blk: &'tcx hir::Block,
5309 expected_ty: Ty<'tcx>,
5310 err: &mut DiagnosticBuilder<'_>,
5312 if let Some(span_semi) = self.could_remove_semicolon(blk, expected_ty) {
5313 err.span_suggestion(
5315 "consider removing this semicolon",
5317 Applicability::MachineApplicable,
5322 fn could_remove_semicolon(&self, blk: &'tcx hir::Block, expected_ty: Ty<'tcx>) -> Option<Span> {
5323 // Be helpful when the user wrote `{... expr;}` and
5324 // taking the `;` off is enough to fix the error.
5325 let last_stmt = blk.stmts.last()?;
5326 let last_expr = match last_stmt.node {
5327 hir::StmtKind::Semi(ref e) => e,
5330 let last_expr_ty = self.node_ty(last_expr.hir_id);
5331 if self.can_sub(self.param_env, last_expr_ty, expected_ty).is_err() {
5334 let original_span = original_sp(last_stmt.span, blk.span);
5335 Some(original_span.with_lo(original_span.hi() - BytePos(1)))
5338 // Rewrite `SelfCtor` to `Ctor`
5339 pub fn rewrite_self_ctor(
5343 ) -> Result<Res, ErrorReported> {
5345 if let Res::SelfCtor(impl_def_id) = res {
5346 let ty = self.impl_self_ty(span, impl_def_id).ty;
5347 let adt_def = ty.ty_adt_def();
5350 Some(adt_def) if adt_def.has_ctor() => {
5351 let variant = adt_def.non_enum_variant();
5352 let ctor_def_id = variant.ctor_def_id.unwrap();
5353 Ok(Res::Def(DefKind::Ctor(CtorOf::Struct, variant.ctor_kind), ctor_def_id))
5356 let mut err = tcx.sess.struct_span_err(span,
5357 "the `Self` constructor can only be used with tuple or unit structs");
5358 if let Some(adt_def) = adt_def {
5359 match adt_def.adt_kind() {
5361 err.help("did you mean to use one of the enum's variants?");
5365 err.span_suggestion(
5367 "use curly brackets",
5368 String::from("Self { /* fields */ }"),
5369 Applicability::HasPlaceholders,
5384 // Instantiates the given path, which must refer to an item with the given
5385 // number of type parameters and type.
5386 pub fn instantiate_value_path(&self,
5387 segments: &[hir::PathSegment],
5388 self_ty: Option<Ty<'tcx>>,
5392 -> (Ty<'tcx>, Res) {
5394 "instantiate_value_path(segments={:?}, self_ty={:?}, res={:?}, hir_id={})",
5403 let res = match self.rewrite_self_ctor(res, span) {
5405 Err(ErrorReported) => return (tcx.types.err, res),
5407 let path_segs = match res {
5408 Res::Local(_) => vec![],
5409 Res::Def(kind, def_id) =>
5410 AstConv::def_ids_for_value_path_segments(self, segments, self_ty, kind, def_id),
5411 _ => bug!("instantiate_value_path on {:?}", res),
5414 let mut user_self_ty = None;
5415 let mut is_alias_variant_ctor = false;
5417 Res::Def(DefKind::Ctor(CtorOf::Variant, _), _) => {
5418 if let Some(self_ty) = self_ty {
5419 let adt_def = self_ty.ty_adt_def().unwrap();
5420 user_self_ty = Some(UserSelfTy {
5421 impl_def_id: adt_def.did,
5424 is_alias_variant_ctor = true;
5427 Res::Def(DefKind::Method, def_id)
5428 | Res::Def(DefKind::AssocConst, def_id) => {
5429 let container = tcx.associated_item(def_id).container;
5430 debug!("instantiate_value_path: def_id={:?} container={:?}", def_id, container);
5432 ty::TraitContainer(trait_did) => {
5433 callee::check_legal_trait_for_method_call(tcx, span, trait_did)
5435 ty::ImplContainer(impl_def_id) => {
5436 if segments.len() == 1 {
5437 // `<T>::assoc` will end up here, and so
5438 // can `T::assoc`. It this came from an
5439 // inherent impl, we need to record the
5440 // `T` for posterity (see `UserSelfTy` for
5442 let self_ty = self_ty.expect("UFCS sugared assoc missing Self");
5443 user_self_ty = Some(UserSelfTy {
5454 // Now that we have categorized what space the parameters for each
5455 // segment belong to, let's sort out the parameters that the user
5456 // provided (if any) into their appropriate spaces. We'll also report
5457 // errors if type parameters are provided in an inappropriate place.
5459 let generic_segs: FxHashSet<_> = path_segs.iter().map(|PathSeg(_, index)| index).collect();
5460 let generics_has_err = AstConv::prohibit_generics(
5461 self, segments.iter().enumerate().filter_map(|(index, seg)| {
5462 if !generic_segs.contains(&index) || is_alias_variant_ctor {
5469 if let Res::Local(hid) = res {
5470 let ty = self.local_ty(span, hid).decl_ty;
5471 let ty = self.normalize_associated_types_in(span, &ty);
5472 self.write_ty(hir_id, ty);
5476 if generics_has_err {
5477 // Don't try to infer type parameters when prohibited generic arguments were given.
5478 user_self_ty = None;
5481 // Now we have to compare the types that the user *actually*
5482 // provided against the types that were *expected*. If the user
5483 // did not provide any types, then we want to substitute inference
5484 // variables. If the user provided some types, we may still need
5485 // to add defaults. If the user provided *too many* types, that's
5488 let mut infer_args_for_err = FxHashSet::default();
5489 for &PathSeg(def_id, index) in &path_segs {
5490 let seg = &segments[index];
5491 let generics = tcx.generics_of(def_id);
5492 // Argument-position `impl Trait` is treated as a normal generic
5493 // parameter internally, but we don't allow users to specify the
5494 // parameter's value explicitly, so we have to do some error-
5496 let suppress_errors = AstConv::check_generic_arg_count_for_call(
5501 false, // `is_method_call`
5503 if suppress_errors {
5504 infer_args_for_err.insert(index);
5505 self.set_tainted_by_errors(); // See issue #53251.
5509 let has_self = path_segs.last().map(|PathSeg(def_id, _)| {
5510 tcx.generics_of(*def_id).has_self
5511 }).unwrap_or(false);
5513 let def_id = res.def_id();
5515 // The things we are substituting into the type should not contain
5516 // escaping late-bound regions, and nor should the base type scheme.
5517 let ty = tcx.type_of(def_id);
5519 let substs = AstConv::create_substs_for_generic_args(
5525 // Provide the generic args, and whether types should be inferred.
5527 if let Some(&PathSeg(_, index)) = path_segs.iter().find(|&PathSeg(did, _)| {
5530 // If we've encountered an `impl Trait`-related error, we're just
5531 // going to infer the arguments for better error messages.
5532 if !infer_args_for_err.contains(&index) {
5533 // Check whether the user has provided generic arguments.
5534 if let Some(ref data) = segments[index].args {
5535 return (Some(data), segments[index].infer_args);
5538 return (None, segments[index].infer_args);
5543 // Provide substitutions for parameters for which (valid) arguments have been provided.
5545 match (¶m.kind, arg) {
5546 (GenericParamDefKind::Lifetime, GenericArg::Lifetime(lt)) => {
5547 AstConv::ast_region_to_region(self, lt, Some(param)).into()
5549 (GenericParamDefKind::Type { .. }, GenericArg::Type(ty)) => {
5550 self.to_ty(ty).into()
5552 (GenericParamDefKind::Const, GenericArg::Const(ct)) => {
5553 self.to_const(&ct.value, self.tcx.type_of(param.def_id)).into()
5555 _ => unreachable!(),
5558 // Provide substitutions for parameters for which arguments are inferred.
5559 |substs, param, infer_args| {
5561 GenericParamDefKind::Lifetime => {
5562 self.re_infer(Some(param), span).unwrap().into()
5564 GenericParamDefKind::Type { has_default, .. } => {
5565 if !infer_args && has_default {
5566 // If we have a default, then we it doesn't matter that we're not
5567 // inferring the type arguments: we provide the default where any
5569 let default = tcx.type_of(param.def_id);
5572 default.subst_spanned(tcx, substs.unwrap(), Some(span))
5575 // If no type arguments were provided, we have to infer them.
5576 // This case also occurs as a result of some malformed input, e.g.
5577 // a lifetime argument being given instead of a type parameter.
5578 // Using inference instead of `Error` gives better error messages.
5579 self.var_for_def(span, param)
5582 GenericParamDefKind::Const => {
5583 // FIXME(const_generics:defaults)
5584 // No const parameters were provided, we have to infer them.
5585 self.var_for_def(span, param)
5590 assert!(!substs.has_escaping_bound_vars());
5591 assert!(!ty.has_escaping_bound_vars());
5593 // First, store the "user substs" for later.
5594 self.write_user_type_annotation_from_substs(hir_id, def_id, substs, user_self_ty);
5596 // Add all the obligations that are required, substituting and
5597 // normalized appropriately.
5598 let bounds = self.instantiate_bounds(span, def_id, &substs);
5599 self.add_obligations_for_parameters(
5600 traits::ObligationCause::new(span, self.body_id, traits::ItemObligation(def_id)),
5603 // Substitute the values for the type parameters into the type of
5604 // the referenced item.
5605 let ty_substituted = self.instantiate_type_scheme(span, &substs, &ty);
5607 if let Some(UserSelfTy { impl_def_id, self_ty }) = user_self_ty {
5608 // In the case of `Foo<T>::method` and `<Foo<T>>::method`, if `method`
5609 // is inherent, there is no `Self` parameter; instead, the impl needs
5610 // type parameters, which we can infer by unifying the provided `Self`
5611 // with the substituted impl type.
5612 // This also occurs for an enum variant on a type alias.
5613 let ty = tcx.type_of(impl_def_id);
5615 let impl_ty = self.instantiate_type_scheme(span, &substs, &ty);
5616 match self.at(&self.misc(span), self.param_env).sup(impl_ty, self_ty) {
5617 Ok(ok) => self.register_infer_ok_obligations(ok),
5619 self.tcx.sess.delay_span_bug(span, &format!(
5620 "instantiate_value_path: (UFCS) {:?} was a subtype of {:?} but now is not?",
5628 self.check_rustc_args_require_const(def_id, hir_id, span);
5630 debug!("instantiate_value_path: type of {:?} is {:?}",
5633 self.write_substs(hir_id, substs);
5635 (ty_substituted, res)
5638 fn check_rustc_args_require_const(&self,
5642 // We're only interested in functions tagged with
5643 // #[rustc_args_required_const], so ignore anything that's not.
5644 if !self.tcx.has_attr(def_id, sym::rustc_args_required_const) {
5648 // If our calling expression is indeed the function itself, we're good!
5649 // If not, generate an error that this can only be called directly.
5650 if let Node::Expr(expr) = self.tcx.hir().get_by_hir_id(
5651 self.tcx.hir().get_parent_node_by_hir_id(hir_id))
5653 if let ExprKind::Call(ref callee, ..) = expr.node {
5654 if callee.hir_id == hir_id {
5660 self.tcx.sess.span_err(span, "this function can only be invoked \
5661 directly, not through a function pointer");
5664 // Resolves `typ` by a single level if `typ` is a type variable.
5665 // If no resolution is possible, then an error is reported.
5666 // Numeric inference variables may be left unresolved.
5667 pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
5668 let ty = self.resolve_type_vars_with_obligations(ty);
5669 if !ty.is_ty_var() {
5672 if !self.is_tainted_by_errors() {
5673 self.need_type_info_err((**self).body_id, sp, ty)
5674 .note("type must be known at this point")
5677 self.demand_suptype(sp, self.tcx.types.err, ty);
5682 fn with_breakable_ctxt<F: FnOnce() -> R, R>(
5685 ctxt: BreakableCtxt<'tcx>,
5687 ) -> (BreakableCtxt<'tcx>, R) {
5690 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5691 index = enclosing_breakables.stack.len();
5692 enclosing_breakables.by_id.insert(id, index);
5693 enclosing_breakables.stack.push(ctxt);
5697 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
5698 debug_assert!(enclosing_breakables.stack.len() == index + 1);
5699 enclosing_breakables.by_id.remove(&id).expect("missing breakable context");
5700 enclosing_breakables.stack.pop().expect("missing breakable context")
5705 /// Instantiate a QueryResponse in a probe context, without a
5706 /// good ObligationCause.
5707 fn probe_instantiate_query_response(
5710 original_values: &OriginalQueryValues<'tcx>,
5711 query_result: &Canonical<'tcx, QueryResponse<'tcx, Ty<'tcx>>>,
5712 ) -> InferResult<'tcx, Ty<'tcx>>
5714 self.instantiate_query_response_and_region_obligations(
5715 &traits::ObligationCause::misc(span, self.body_id),
5721 /// Returns `true` if an expression is contained inside the LHS of an assignment expression.
5722 fn expr_in_place(&self, mut expr_id: hir::HirId) -> bool {
5723 let mut contained_in_place = false;
5725 while let hir::Node::Expr(parent_expr) =
5726 self.tcx.hir().get_by_hir_id(self.tcx.hir().get_parent_node_by_hir_id(expr_id))
5728 match &parent_expr.node {
5729 hir::ExprKind::Assign(lhs, ..) | hir::ExprKind::AssignOp(_, lhs, ..) => {
5730 if lhs.hir_id == expr_id {
5731 contained_in_place = true;
5737 expr_id = parent_expr.hir_id;
5744 pub fn check_bounds_are_used<'tcx>(tcx: TyCtxt<'tcx>, generics: &ty::Generics, ty: Ty<'tcx>) {
5745 let own_counts = generics.own_counts();
5747 "check_bounds_are_used(n_tys={}, n_cts={}, ty={:?})",
5753 if own_counts.types == 0 {
5757 // Make a vector of booleans initially false, set to true when used.
5758 let mut types_used = vec![false; own_counts.types];
5760 for leaf_ty in ty.walk() {
5761 if let ty::Param(ty::ParamTy { index, .. }) = leaf_ty.sty {
5762 debug!("Found use of ty param num {}", index);
5763 types_used[index as usize - own_counts.lifetimes] = true;
5764 } else if let ty::Error = leaf_ty.sty {
5765 // If there is already another error, do not emit
5766 // an error for not using a type Parameter.
5767 assert!(tcx.sess.err_count() > 0);
5772 let types = generics.params.iter().filter(|param| match param.kind {
5773 ty::GenericParamDefKind::Type { .. } => true,
5776 for (&used, param) in types_used.iter().zip(types) {
5778 let id = tcx.hir().as_local_hir_id(param.def_id).unwrap();
5779 let span = tcx.hir().span_by_hir_id(id);
5780 struct_span_err!(tcx.sess, span, E0091, "type parameter `{}` is unused", param.name)
5781 .span_label(span, "unused type parameter")
5787 fn fatally_break_rust(sess: &Session) {
5788 let handler = sess.diagnostic();
5789 handler.span_bug_no_panic(
5791 "It looks like you're trying to break rust; would you like some ICE?",
5793 handler.note_without_error("the compiler expectedly panicked. this is a feature.");
5794 handler.note_without_error(
5795 "we would appreciate a joke overview: \
5796 https://github.com/rust-lang/rust/issues/43162#issuecomment-320764675"
5798 handler.note_without_error(&format!("rustc {} running on {}",
5799 option_env!("CFG_VERSION").unwrap_or("unknown_version"),
5800 crate::session::config::host_triple(),
5804 fn potentially_plural_count(count: usize, word: &str) -> String {
5805 format!("{} {}{}", count, word, if count == 1 { "" } else { "s" })