1 // Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
2 // file at the top-level directory of this distribution and at
3 // http://rust-lang.org/COPYRIGHT.
5 // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6 // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7 // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8 // option. This file may not be copied, modified, or distributed
9 // except according to those terms.
15 Within the check phase of type check, we check each item one at a time
16 (bodies of function expressions are checked as part of the containing
17 function). Inference is used to supply types wherever they are
20 By far the most complex case is checking the body of a function. This
21 can be broken down into several distinct phases:
23 - gather: creates type variables to represent the type of each local
24 variable and pattern binding.
26 - main: the main pass does the lion's share of the work: it
27 determines the types of all expressions, resolves
28 methods, checks for most invalid conditions, and so forth. In
29 some cases, where a type is unknown, it may create a type or region
30 variable and use that as the type of an expression.
32 In the process of checking, various constraints will be placed on
33 these type variables through the subtyping relationships requested
34 through the `demand` module. The `infer` module is in charge
35 of resolving those constraints.
37 - regionck: after main is complete, the regionck pass goes over all
38 types looking for regions and making sure that they did not escape
39 into places they are not in scope. This may also influence the
40 final assignments of the various region variables if there is some
43 - vtable: find and records the impls to use for each trait bound that
44 appears on a type parameter.
46 - writeback: writes the final types within a function body, replacing
47 type variables with their final inferred types. These final types
48 are written into the `tcx.node_types` table, which should *never* contain
49 any reference to a type variable.
53 While type checking a function, the intermediate types for the
54 expressions, blocks, and so forth contained within the function are
55 stored in `fcx.node_types` and `fcx.node_substs`. These types
56 may contain unresolved type variables. After type checking is
57 complete, the functions in the writeback module are used to take the
58 types from this table, resolve them, and then write them into their
59 permanent home in the type context `tcx`.
61 This means that during inferencing you should use `fcx.write_ty()`
62 and `fcx.expr_ty()` / `fcx.node_ty()` to write/obtain the types of
63 nodes within the function.
65 The types of top-level items, which never contain unbound type
66 variables, are stored directly into the `tcx` tables.
68 n.b.: A type variable is not the same thing as a type parameter. A
69 type variable is rather an "instance" of a type parameter: that is,
70 given a generic function `fn foo<T>(t: T)`: while checking the
71 function `foo`, the type `ty_param(0)` refers to the type `T`, which
72 is treated in abstract. When `foo()` is called, however, `T` will be
73 substituted for a fresh type variable `N`. This variable will
74 eventually be resolved to some concrete type (which might itself be
79 pub use self::Expectation::*;
80 use self::autoderef::Autoderef;
81 use self::callee::DeferredCallResolution;
82 use self::coercion::{CoerceMany, DynamicCoerceMany};
83 pub use self::compare_method::{compare_impl_method, compare_const_impl};
84 use self::method::MethodCallee;
85 use self::TupleArgumentsFlag::*;
88 use hir::def::{Def, CtorKind};
89 use hir::def_id::{CrateNum, DefId, LOCAL_CRATE};
90 use rustc_back::slice::ref_slice;
91 use namespace::Namespace;
92 use rustc::infer::{self, InferCtxt, InferOk, RegionVariableOrigin};
93 use rustc::infer::type_variable::{TypeVariableOrigin};
94 use rustc::middle::region;
95 use rustc::ty::subst::{Kind, Subst, Substs};
96 use rustc::traits::{self, FulfillmentContext, ObligationCause, ObligationCauseCode};
97 use rustc::ty::{ParamTy, LvaluePreference, NoPreference, PreferMutLvalue};
98 use rustc::ty::{self, Ty, TyCtxt, Visibility};
99 use rustc::ty::adjustment::{Adjust, Adjustment, AutoBorrow};
100 use rustc::ty::fold::{BottomUpFolder, TypeFoldable};
101 use rustc::ty::maps::Providers;
102 use rustc::ty::util::{Representability, IntTypeExt};
103 use errors::{DiagnosticBuilder, DiagnosticId};
104 use require_c_abi_if_variadic;
105 use session::{CompileIncomplete, Session};
108 use util::common::{ErrorReported, indenter};
109 use util::nodemap::{DefIdMap, DefIdSet, FxHashMap, NodeMap};
111 use std::cell::{Cell, RefCell, Ref, RefMut};
113 use std::collections::hash_map::Entry;
115 use std::fmt::Display;
116 use std::mem::replace;
117 use std::ops::{self, Deref};
118 use syntax::abi::Abi;
120 use syntax::codemap::{self, original_sp, Spanned};
121 use syntax::feature_gate::{GateIssue, emit_feature_err};
123 use syntax::symbol::{Symbol, InternedString, keywords};
124 use syntax::util::lev_distance::find_best_match_for_name;
125 use syntax_pos::{self, BytePos, Span, MultiSpan};
127 use rustc::hir::intravisit::{self, Visitor, NestedVisitorMap};
128 use rustc::hir::itemlikevisit::ItemLikeVisitor;
129 use rustc::hir::map::Node;
130 use rustc::hir::{self, PatKind};
131 use rustc::middle::lang_items;
132 use rustc_back::slice;
133 use rustc_const_math::ConstInt;
140 mod regionck_implied_bounds;
150 mod generator_interior;
154 /// A wrapper for InferCtxt's `in_progress_tables` field.
155 #[derive(Copy, Clone)]
156 struct MaybeInProgressTables<'a, 'tcx: 'a> {
157 maybe_tables: Option<&'a RefCell<ty::TypeckTables<'tcx>>>,
160 impl<'a, 'tcx> MaybeInProgressTables<'a, 'tcx> {
161 fn borrow(self) -> Ref<'a, ty::TypeckTables<'tcx>> {
162 match self.maybe_tables {
163 Some(tables) => tables.borrow(),
165 bug!("MaybeInProgressTables: inh/fcx.tables.borrow() with no tables")
170 fn borrow_mut(self) -> RefMut<'a, ty::TypeckTables<'tcx>> {
171 match self.maybe_tables {
172 Some(tables) => tables.borrow_mut(),
174 bug!("MaybeInProgressTables: inh/fcx.tables.borrow_mut() with no tables")
181 /// closures defined within the function. For example:
184 /// bar(move|| { ... })
187 /// Here, the function `foo()` and the closure passed to
188 /// `bar()` will each have their own `FnCtxt`, but they will
189 /// share the inherited fields.
190 pub struct Inherited<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
191 infcx: InferCtxt<'a, 'gcx, 'tcx>,
193 tables: MaybeInProgressTables<'a, 'tcx>,
195 locals: RefCell<NodeMap<Ty<'tcx>>>,
197 fulfillment_cx: RefCell<traits::FulfillmentContext<'tcx>>,
199 // When we process a call like `c()` where `c` is a closure type,
200 // we may not have decided yet whether `c` is a `Fn`, `FnMut`, or
201 // `FnOnce` closure. In that case, we defer full resolution of the
202 // call until upvar inference can kick in and make the
203 // decision. We keep these deferred resolutions grouped by the
204 // def-id of the closure, so that once we decide, we can easily go
205 // back and process them.
206 deferred_call_resolutions: RefCell<DefIdMap<Vec<DeferredCallResolution<'gcx, 'tcx>>>>,
208 deferred_cast_checks: RefCell<Vec<cast::CastCheck<'tcx>>>,
210 deferred_generator_interiors: RefCell<Vec<(hir::BodyId, Ty<'tcx>)>>,
212 // Anonymized types found in explicit return types and their
213 // associated fresh inference variable. Writeback resolves these
214 // variables to get the concrete type, which can be used to
215 // deanonymize TyAnon, after typeck is done with all functions.
216 anon_types: RefCell<NodeMap<Ty<'tcx>>>,
218 /// Each type parameter has an implicit region bound that
219 /// indicates it must outlive at least the function body (the user
220 /// may specify stronger requirements). This field indicates the
221 /// region of the callee. If it is `None`, then the parameter
222 /// environment is for an item or something where the "callee" is
224 implicit_region_bound: Option<ty::Region<'tcx>>,
226 body_id: Option<hir::BodyId>,
229 impl<'a, 'gcx, 'tcx> Deref for Inherited<'a, 'gcx, 'tcx> {
230 type Target = InferCtxt<'a, 'gcx, 'tcx>;
231 fn deref(&self) -> &Self::Target {
236 /// When type-checking an expression, we propagate downward
237 /// whatever type hint we are able in the form of an `Expectation`.
238 #[derive(Copy, Clone, Debug)]
239 pub enum Expectation<'tcx> {
240 /// We know nothing about what type this expression should have.
243 /// This expression is an `if` condition, it must resolve to `bool`.
246 /// This expression should have the type given (or some subtype)
247 ExpectHasType(Ty<'tcx>),
249 /// This expression will be cast to the `Ty`
250 ExpectCastableToType(Ty<'tcx>),
252 /// This rvalue expression will be wrapped in `&` or `Box` and coerced
253 /// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
254 ExpectRvalueLikeUnsized(Ty<'tcx>),
257 impl<'a, 'gcx, 'tcx> Expectation<'tcx> {
258 // Disregard "castable to" expectations because they
259 // can lead us astray. Consider for example `if cond
260 // {22} else {c} as u8` -- if we propagate the
261 // "castable to u8" constraint to 22, it will pick the
262 // type 22u8, which is overly constrained (c might not
263 // be a u8). In effect, the problem is that the
264 // "castable to" expectation is not the tightest thing
265 // we can say, so we want to drop it in this case.
266 // The tightest thing we can say is "must unify with
267 // else branch". Note that in the case of a "has type"
268 // constraint, this limitation does not hold.
270 // If the expected type is just a type variable, then don't use
271 // an expected type. Otherwise, we might write parts of the type
272 // when checking the 'then' block which are incompatible with the
274 fn adjust_for_branches(&self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
276 ExpectHasType(ety) => {
277 let ety = fcx.shallow_resolve(ety);
278 if !ety.is_ty_var() {
284 ExpectRvalueLikeUnsized(ety) => {
285 ExpectRvalueLikeUnsized(ety)
291 /// Provide an expectation for an rvalue expression given an *optional*
292 /// hint, which is not required for type safety (the resulting type might
293 /// be checked higher up, as is the case with `&expr` and `box expr`), but
294 /// is useful in determining the concrete type.
296 /// The primary use case is where the expected type is a fat pointer,
297 /// like `&[isize]`. For example, consider the following statement:
299 /// let x: &[isize] = &[1, 2, 3];
301 /// In this case, the expected type for the `&[1, 2, 3]` expression is
302 /// `&[isize]`. If however we were to say that `[1, 2, 3]` has the
303 /// expectation `ExpectHasType([isize])`, that would be too strong --
304 /// `[1, 2, 3]` does not have the type `[isize]` but rather `[isize; 3]`.
305 /// It is only the `&[1, 2, 3]` expression as a whole that can be coerced
306 /// to the type `&[isize]`. Therefore, we propagate this more limited hint,
307 /// which still is useful, because it informs integer literals and the like.
308 /// See the test case `test/run-pass/coerce-expect-unsized.rs` and #20169
309 /// for examples of where this comes up,.
310 fn rvalue_hint(fcx: &FnCtxt<'a, 'gcx, 'tcx>, ty: Ty<'tcx>) -> Expectation<'tcx> {
311 match fcx.tcx.struct_tail(ty).sty {
312 ty::TySlice(_) | ty::TyStr | ty::TyDynamic(..) => {
313 ExpectRvalueLikeUnsized(ty)
315 _ => ExpectHasType(ty)
319 // Resolves `expected` by a single level if it is a variable. If
320 // there is no expected type or resolution is not possible (e.g.,
321 // no constraints yet present), just returns `None`.
322 fn resolve(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
324 NoExpectation => NoExpectation,
325 ExpectIfCondition => ExpectIfCondition,
326 ExpectCastableToType(t) => {
327 ExpectCastableToType(fcx.resolve_type_vars_if_possible(&t))
329 ExpectHasType(t) => {
330 ExpectHasType(fcx.resolve_type_vars_if_possible(&t))
332 ExpectRvalueLikeUnsized(t) => {
333 ExpectRvalueLikeUnsized(fcx.resolve_type_vars_if_possible(&t))
338 fn to_option(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Option<Ty<'tcx>> {
339 match self.resolve(fcx) {
340 NoExpectation => None,
341 ExpectIfCondition => Some(fcx.tcx.types.bool),
342 ExpectCastableToType(ty) |
344 ExpectRvalueLikeUnsized(ty) => Some(ty),
348 /// It sometimes happens that we want to turn an expectation into
349 /// a **hard constraint** (i.e., something that must be satisfied
350 /// for the program to type-check). `only_has_type` will return
351 /// such a constraint, if it exists.
352 fn only_has_type(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Option<Ty<'tcx>> {
353 match self.resolve(fcx) {
354 ExpectHasType(ty) => Some(ty),
355 ExpectIfCondition => Some(fcx.tcx.types.bool),
356 NoExpectation | ExpectCastableToType(_) | ExpectRvalueLikeUnsized(_) => None,
360 /// Like `only_has_type`, but instead of returning `None` if no
361 /// hard constraint exists, creates a fresh type variable.
362 fn coercion_target_type(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>, span: Span) -> Ty<'tcx> {
363 self.only_has_type(fcx)
364 .unwrap_or_else(|| fcx.next_ty_var(TypeVariableOrigin::MiscVariable(span)))
368 #[derive(Copy, Clone)]
369 pub struct UnsafetyState {
370 pub def: ast::NodeId,
371 pub unsafety: hir::Unsafety,
372 pub unsafe_push_count: u32,
377 pub fn function(unsafety: hir::Unsafety, def: ast::NodeId) -> UnsafetyState {
378 UnsafetyState { def: def, unsafety: unsafety, unsafe_push_count: 0, from_fn: true }
381 pub fn recurse(&mut self, blk: &hir::Block) -> UnsafetyState {
382 match self.unsafety {
383 // If this unsafe, then if the outer function was already marked as
384 // unsafe we shouldn't attribute the unsafe'ness to the block. This
385 // way the block can be warned about instead of ignoring this
386 // extraneous block (functions are never warned about).
387 hir::Unsafety::Unsafe if self.from_fn => *self,
390 let (unsafety, def, count) = match blk.rules {
391 hir::PushUnsafeBlock(..) =>
392 (unsafety, blk.id, self.unsafe_push_count.checked_add(1).unwrap()),
393 hir::PopUnsafeBlock(..) =>
394 (unsafety, blk.id, self.unsafe_push_count.checked_sub(1).unwrap()),
395 hir::UnsafeBlock(..) =>
396 (hir::Unsafety::Unsafe, blk.id, self.unsafe_push_count),
398 (unsafety, self.def, self.unsafe_push_count),
402 unsafe_push_count: count,
409 #[derive(Debug, Copy, Clone)]
415 /// Tracks whether executing a node may exit normally (versus
416 /// return/break/panic, which "diverge", leaving dead code in their
417 /// wake). Tracked semi-automatically (through type variables marked
418 /// as diverging), with some manual adjustments for control-flow
419 /// primitives (approximating a CFG).
420 #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord)]
422 /// Potentially unknown, some cases converge,
423 /// others require a CFG to determine them.
426 /// Definitely known to diverge and therefore
427 /// not reach the next sibling or its parent.
430 /// Same as `Always` but with a reachability
431 /// warning already emitted
435 // Convenience impls for combinig `Diverges`.
437 impl ops::BitAnd for Diverges {
439 fn bitand(self, other: Self) -> Self {
440 cmp::min(self, other)
444 impl ops::BitOr for Diverges {
446 fn bitor(self, other: Self) -> Self {
447 cmp::max(self, other)
451 impl ops::BitAndAssign for Diverges {
452 fn bitand_assign(&mut self, other: Self) {
453 *self = *self & other;
457 impl ops::BitOrAssign for Diverges {
458 fn bitor_assign(&mut self, other: Self) {
459 *self = *self | other;
464 fn always(self) -> bool {
465 self >= Diverges::Always
469 pub struct BreakableCtxt<'gcx: 'tcx, 'tcx> {
472 // this is `null` for loops where break with a value is illegal,
473 // such as `while`, `for`, and `while let`
474 coerce: Option<DynamicCoerceMany<'gcx, 'tcx>>,
477 pub struct EnclosingBreakables<'gcx: 'tcx, 'tcx> {
478 stack: Vec<BreakableCtxt<'gcx, 'tcx>>,
479 by_id: NodeMap<usize>,
482 impl<'gcx, 'tcx> EnclosingBreakables<'gcx, 'tcx> {
483 fn find_breakable(&mut self, target_id: ast::NodeId) -> &mut BreakableCtxt<'gcx, 'tcx> {
484 let ix = *self.by_id.get(&target_id).unwrap_or_else(|| {
485 bug!("could not find enclosing breakable with id {}", target_id);
491 pub struct FnCtxt<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
492 body_id: ast::NodeId,
494 /// The parameter environment used for proving trait obligations
495 /// in this function. This can change when we descend into
496 /// closures (as they bring new things into scope), hence it is
497 /// not part of `Inherited` (as of the time of this writing,
498 /// closures do not yet change the environment, but they will
500 param_env: ty::ParamEnv<'tcx>,
502 // Number of errors that had been reported when we started
503 // checking this function. On exit, if we find that *more* errors
504 // have been reported, we will skip regionck and other work that
505 // expects the types within the function to be consistent.
506 err_count_on_creation: usize,
508 ret_coercion: Option<RefCell<DynamicCoerceMany<'gcx, 'tcx>>>,
510 yield_ty: Option<Ty<'tcx>>,
512 ps: RefCell<UnsafetyState>,
514 /// Whether the last checked node generates a divergence (e.g.,
515 /// `return` will set this to Always). In general, when entering
516 /// an expression or other node in the tree, the initial value
517 /// indicates whether prior parts of the containing expression may
518 /// have diverged. It is then typically set to `Maybe` (and the
519 /// old value remembered) for processing the subparts of the
520 /// current expression. As each subpart is processed, they may set
521 /// the flag to `Always` etc. Finally, at the end, we take the
522 /// result and "union" it with the original value, so that when we
523 /// return the flag indicates if any subpart of the the parent
524 /// expression (up to and including this part) has diverged. So,
525 /// if you read it after evaluating a subexpression `X`, the value
526 /// you get indicates whether any subexpression that was
527 /// evaluating up to and including `X` diverged.
529 /// We use this flag for two purposes:
531 /// - To warn about unreachable code: if, after processing a
532 /// sub-expression but before we have applied the effects of the
533 /// current node, we see that the flag is set to `Always`, we
534 /// can issue a warning. This corresponds to something like
535 /// `foo(return)`; we warn on the `foo()` expression. (We then
536 /// update the flag to `WarnedAlways` to suppress duplicate
537 /// reports.) Similarly, if we traverse to a fresh statement (or
538 /// tail expression) from a `Always` setting, we will issue a
539 /// warning. This corresponds to something like `{return;
540 /// foo();}` or `{return; 22}`, where we would warn on the
543 /// - To permit assignment into a local variable or other lvalue
544 /// (including the "return slot") of type `!`. This is allowed
545 /// if **either** the type of value being assigned is `!`, which
546 /// means the current code is dead, **or** the expression's
547 /// diverging flag is true, which means that a diverging value was
548 /// wrapped (e.g., `let x: ! = foo(return)`).
550 /// To repeat the last point: an expression represents dead-code
551 /// if, after checking it, **either** its type is `!` OR the
552 /// diverges flag is set to something other than `Maybe`.
553 diverges: Cell<Diverges>,
555 /// Whether any child nodes have any type errors.
556 has_errors: Cell<bool>,
558 enclosing_breakables: RefCell<EnclosingBreakables<'gcx, 'tcx>>,
560 inh: &'a Inherited<'a, 'gcx, 'tcx>,
563 impl<'a, 'gcx, 'tcx> Deref for FnCtxt<'a, 'gcx, 'tcx> {
564 type Target = Inherited<'a, 'gcx, 'tcx>;
565 fn deref(&self) -> &Self::Target {
570 /// Helper type of a temporary returned by Inherited::build(...).
571 /// Necessary because we can't write the following bound:
572 /// F: for<'b, 'tcx> where 'gcx: 'tcx FnOnce(Inherited<'b, 'gcx, 'tcx>).
573 pub struct InheritedBuilder<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
574 infcx: infer::InferCtxtBuilder<'a, 'gcx, 'tcx>,
578 impl<'a, 'gcx, 'tcx> Inherited<'a, 'gcx, 'tcx> {
579 pub fn build(tcx: TyCtxt<'a, 'gcx, 'gcx>, def_id: DefId)
580 -> InheritedBuilder<'a, 'gcx, 'tcx> {
581 let hir_id_root = if def_id.is_local() {
582 let node_id = tcx.hir.as_local_node_id(def_id).unwrap();
583 let hir_id = tcx.hir.definitions().node_to_hir_id(node_id);
584 DefId::local(hir_id.owner)
590 infcx: tcx.infer_ctxt().with_fresh_in_progress_tables(hir_id_root),
596 impl<'a, 'gcx, 'tcx> InheritedBuilder<'a, 'gcx, 'tcx> {
597 fn enter<F, R>(&'tcx mut self, f: F) -> R
598 where F: for<'b> FnOnce(Inherited<'b, 'gcx, 'tcx>) -> R
600 let def_id = self.def_id;
601 self.infcx.enter(|infcx| f(Inherited::new(infcx, def_id)))
605 impl<'a, 'gcx, 'tcx> Inherited<'a, 'gcx, 'tcx> {
606 fn new(infcx: InferCtxt<'a, 'gcx, 'tcx>, def_id: DefId) -> Self {
608 let item_id = tcx.hir.as_local_node_id(def_id);
609 let body_id = item_id.and_then(|id| tcx.hir.maybe_body_owned_by(id));
610 let implicit_region_bound = body_id.map(|body_id| {
611 let body = tcx.hir.body(body_id);
612 tcx.mk_region(ty::ReScope(region::Scope::CallSite(body.value.hir_id.local_id)))
616 tables: MaybeInProgressTables {
617 maybe_tables: infcx.in_progress_tables,
620 fulfillment_cx: RefCell::new(traits::FulfillmentContext::new()),
621 locals: RefCell::new(NodeMap()),
622 deferred_call_resolutions: RefCell::new(DefIdMap()),
623 deferred_cast_checks: RefCell::new(Vec::new()),
624 deferred_generator_interiors: RefCell::new(Vec::new()),
625 anon_types: RefCell::new(NodeMap()),
626 implicit_region_bound,
631 fn register_predicate(&self, obligation: traits::PredicateObligation<'tcx>) {
632 debug!("register_predicate({:?})", obligation);
633 if obligation.has_escaping_regions() {
634 span_bug!(obligation.cause.span, "escaping regions in predicate {:?}",
639 .register_predicate_obligation(self, obligation);
642 fn register_predicates<I>(&self, obligations: I)
643 where I: IntoIterator<Item = traits::PredicateObligation<'tcx>> {
644 for obligation in obligations {
645 self.register_predicate(obligation);
649 fn register_infer_ok_obligations<T>(&self, infer_ok: InferOk<'tcx, T>) -> T {
650 self.register_predicates(infer_ok.obligations);
654 fn normalize_associated_types_in<T>(&self,
656 body_id: ast::NodeId,
657 param_env: ty::ParamEnv<'tcx>,
659 where T : TypeFoldable<'tcx>
661 let ok = self.partially_normalize_associated_types_in(span, body_id, param_env, value);
662 self.register_infer_ok_obligations(ok)
665 /// Replace any late-bound regions bound in `value` with
666 /// free variants attached to `all_outlive_scope`.
667 fn liberate_late_bound_regions<T>(&self,
668 all_outlive_scope: DefId,
669 value: &ty::Binder<T>)
671 where T: TypeFoldable<'tcx>
673 self.tcx.replace_late_bound_regions(value, |br| {
674 self.tcx.mk_region(ty::ReFree(ty::FreeRegion {
675 scope: all_outlive_scope,
682 struct CheckItemTypesVisitor<'a, 'tcx: 'a> { tcx: TyCtxt<'a, 'tcx, 'tcx> }
684 impl<'a, 'tcx> ItemLikeVisitor<'tcx> for CheckItemTypesVisitor<'a, 'tcx> {
685 fn visit_item(&mut self, i: &'tcx hir::Item) {
686 check_item_type(self.tcx, i);
688 fn visit_trait_item(&mut self, _: &'tcx hir::TraitItem) { }
689 fn visit_impl_item(&mut self, _: &'tcx hir::ImplItem) { }
692 pub fn check_wf_new<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Result<(), ErrorReported> {
693 tcx.sess.track_errors(|| {
694 let mut visit = wfcheck::CheckTypeWellFormedVisitor::new(tcx);
695 tcx.hir.krate().visit_all_item_likes(&mut visit.as_deep_visitor());
699 pub fn check_item_types<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Result<(), ErrorReported> {
700 tcx.sess.track_errors(|| {
701 tcx.hir.krate().visit_all_item_likes(&mut CheckItemTypesVisitor { tcx });
705 pub fn check_item_bodies<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>) -> Result<(), CompileIncomplete> {
706 tcx.typeck_item_bodies(LOCAL_CRATE)
709 fn typeck_item_bodies<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, crate_num: CrateNum)
710 -> Result<(), CompileIncomplete>
712 debug_assert!(crate_num == LOCAL_CRATE);
713 Ok(tcx.sess.track_errors(|| {
714 for body_owner_def_id in tcx.body_owners() {
715 ty::maps::queries::typeck_tables_of::ensure(tcx, body_owner_def_id);
720 pub fn provide(providers: &mut Providers) {
721 *providers = Providers {
733 fn generator_sig<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
735 -> Option<ty::PolyGenSig<'tcx>> {
736 let node_id = tcx.hir.as_local_node_id(def_id).unwrap();
737 let hir_id = tcx.hir.node_to_hir_id(node_id);
738 tcx.typeck_tables_of(def_id).generator_sigs()[hir_id].map(|s| ty::Binder(s))
741 fn closure_kind<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
744 let node_id = tcx.hir.as_local_node_id(def_id).unwrap();
745 let hir_id = tcx.hir.node_to_hir_id(node_id);
746 tcx.typeck_tables_of(def_id).closure_kinds()[hir_id].0
749 fn adt_destructor<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
751 -> Option<ty::Destructor> {
752 tcx.calculate_dtor(def_id, &mut dropck::check_drop_impl)
755 /// If this def-id is a "primary tables entry", returns `Some((body_id, decl))`
756 /// with information about it's body-id and fn-decl (if any). Otherwise,
759 /// If this function returns "some", then `typeck_tables(def_id)` will
760 /// succeed; if it returns `None`, then `typeck_tables(def_id)` may or
761 /// may not succeed. In some cases where this function returns `None`
762 /// (notably closures), `typeck_tables(def_id)` would wind up
763 /// redirecting to the owning function.
764 fn primary_body_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
766 -> Option<(hir::BodyId, Option<&'tcx hir::FnDecl>)>
768 match tcx.hir.get(id) {
769 hir::map::NodeItem(item) => {
771 hir::ItemConst(_, body) |
772 hir::ItemStatic(_, _, body) =>
774 hir::ItemFn(ref decl, .., body) =>
775 Some((body, Some(decl))),
780 hir::map::NodeTraitItem(item) => {
782 hir::TraitItemKind::Const(_, Some(body)) =>
784 hir::TraitItemKind::Method(ref sig, hir::TraitMethod::Provided(body)) =>
785 Some((body, Some(&sig.decl))),
790 hir::map::NodeImplItem(item) => {
792 hir::ImplItemKind::Const(_, body) =>
794 hir::ImplItemKind::Method(ref sig, body) =>
795 Some((body, Some(&sig.decl))),
800 hir::map::NodeExpr(expr) => {
801 // FIXME(eddyb) Closures should have separate
802 // function definition IDs and expression IDs.
803 // Type-checking should not let closures get
804 // this far in a constant position.
805 // Assume that everything other than closures
806 // is a constant "initializer" expression.
808 hir::ExprClosure(..) =>
811 Some((hir::BodyId { node_id: expr.id }, None)),
818 fn has_typeck_tables<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
821 // Closures' tables come from their outermost function,
822 // as they are part of the same "inference environment".
823 let outer_def_id = tcx.closure_base_def_id(def_id);
824 if outer_def_id != def_id {
825 return tcx.has_typeck_tables(outer_def_id);
828 let id = tcx.hir.as_local_node_id(def_id).unwrap();
829 primary_body_of(tcx, id).is_some()
832 fn used_trait_imports<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
835 tcx.typeck_tables_of(def_id).used_trait_imports.clone()
838 fn typeck_tables_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
840 -> &'tcx ty::TypeckTables<'tcx> {
841 // Closures' tables come from their outermost function,
842 // as they are part of the same "inference environment".
843 let outer_def_id = tcx.closure_base_def_id(def_id);
844 if outer_def_id != def_id {
845 return tcx.typeck_tables_of(outer_def_id);
848 let id = tcx.hir.as_local_node_id(def_id).unwrap();
849 let span = tcx.hir.span(id);
851 // Figure out what primary body this item has.
852 let (body_id, fn_decl) = primary_body_of(tcx, id).unwrap_or_else(|| {
853 span_bug!(span, "can't type-check body of {:?}", def_id);
855 let body = tcx.hir.body(body_id);
857 let tables = Inherited::build(tcx, def_id).enter(|inh| {
858 let param_env = tcx.param_env(def_id);
859 let fcx = if let Some(decl) = fn_decl {
860 let fn_sig = tcx.fn_sig(def_id);
862 check_abi(tcx, span, fn_sig.abi());
864 // Compute the fty from point of view of inside fn.
866 inh.liberate_late_bound_regions(def_id, &fn_sig);
868 inh.normalize_associated_types_in(body.value.span,
873 check_fn(&inh, param_env, fn_sig, decl, id, body, false).0
875 let fcx = FnCtxt::new(&inh, param_env, body.value.id);
876 let expected_type = tcx.type_of(def_id);
877 let expected_type = fcx.normalize_associated_types_in(body.value.span, &expected_type);
878 fcx.require_type_is_sized(expected_type, body.value.span, traits::ConstSized);
880 // Gather locals in statics (because of block expressions).
881 // This is technically unnecessary because locals in static items are forbidden,
882 // but prevents type checking from blowing up before const checking can properly
884 GatherLocalsVisitor { fcx: &fcx }.visit_body(body);
886 fcx.check_expr_coercable_to_type(&body.value, expected_type);
891 fcx.select_all_obligations_and_apply_defaults();
892 fcx.closure_analyze(body);
893 fcx.select_obligations_where_possible();
895 fcx.resolve_generator_interiors(def_id);
896 fcx.select_all_obligations_or_error();
898 if fn_decl.is_some() {
899 fcx.regionck_fn(id, body);
901 fcx.regionck_expr(body);
904 fcx.resolve_type_vars_in_body(body)
907 // Consistency check our TypeckTables instance can hold all ItemLocalIds
908 // it will need to hold.
909 assert_eq!(tables.local_id_root,
910 Some(DefId::local(tcx.hir.definitions().node_to_hir_id(id).owner)));
914 fn check_abi<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, span: Span, abi: Abi) {
915 if !tcx.sess.target.target.is_abi_supported(abi) {
916 struct_span_err!(tcx.sess, span, E0570,
917 "The ABI `{}` is not supported for the current target", abi).emit()
921 struct GatherLocalsVisitor<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
922 fcx: &'a FnCtxt<'a, 'gcx, 'tcx>
925 impl<'a, 'gcx, 'tcx> GatherLocalsVisitor<'a, 'gcx, 'tcx> {
926 fn assign(&mut self, span: Span, nid: ast::NodeId, ty_opt: Option<Ty<'tcx>>) -> Ty<'tcx> {
929 // infer the variable's type
930 let var_ty = self.fcx.next_ty_var(TypeVariableOrigin::TypeInference(span));
931 self.fcx.locals.borrow_mut().insert(nid, var_ty);
935 // take type that the user specified
936 self.fcx.locals.borrow_mut().insert(nid, typ);
943 impl<'a, 'gcx, 'tcx> Visitor<'gcx> for GatherLocalsVisitor<'a, 'gcx, 'tcx> {
944 fn nested_visit_map<'this>(&'this mut self) -> NestedVisitorMap<'this, 'gcx> {
945 NestedVisitorMap::None
948 // Add explicitly-declared locals.
949 fn visit_local(&mut self, local: &'gcx hir::Local) {
950 let o_ty = match local.ty {
951 Some(ref ty) => Some(self.fcx.to_ty(&ty)),
954 self.assign(local.span, local.id, o_ty);
955 debug!("Local variable {:?} is assigned type {}",
957 self.fcx.ty_to_string(
958 self.fcx.locals.borrow().get(&local.id).unwrap().clone()));
959 intravisit::walk_local(self, local);
962 // Add pattern bindings.
963 fn visit_pat(&mut self, p: &'gcx hir::Pat) {
964 if let PatKind::Binding(_, _, ref path1, _) = p.node {
965 let var_ty = self.assign(p.span, p.id, None);
967 self.fcx.require_type_is_sized(var_ty, p.span,
968 traits::VariableType(p.id));
970 debug!("Pattern binding {} is assigned to {} with type {:?}",
972 self.fcx.ty_to_string(
973 self.fcx.locals.borrow().get(&p.id).unwrap().clone()),
976 intravisit::walk_pat(self, p);
979 // Don't descend into the bodies of nested closures
980 fn visit_fn(&mut self, _: intravisit::FnKind<'gcx>, _: &'gcx hir::FnDecl,
981 _: hir::BodyId, _: Span, _: ast::NodeId) { }
984 /// Helper used for fns and closures. Does the grungy work of checking a function
985 /// body and returns the function context used for that purpose, since in the case of a fn item
986 /// there is still a bit more to do.
989 /// * inherited: other fields inherited from the enclosing fn (if any)
990 fn check_fn<'a, 'gcx, 'tcx>(inherited: &'a Inherited<'a, 'gcx, 'tcx>,
991 param_env: ty::ParamEnv<'tcx>,
992 fn_sig: ty::FnSig<'tcx>,
993 decl: &'gcx hir::FnDecl,
995 body: &'gcx hir::Body,
996 can_be_generator: bool)
997 -> (FnCtxt<'a, 'gcx, 'tcx>, Option<ty::GeneratorInterior<'tcx>>)
999 let mut fn_sig = fn_sig.clone();
1001 debug!("check_fn(sig={:?}, fn_id={}, param_env={:?})", fn_sig, fn_id, param_env);
1003 // Create the function context. This is either derived from scratch or,
1004 // in the case of function expressions, based on the outer context.
1005 let mut fcx = FnCtxt::new(inherited, param_env, body.value.id);
1006 *fcx.ps.borrow_mut() = UnsafetyState::function(fn_sig.unsafety, fn_id);
1008 let ret_ty = fn_sig.output();
1009 fcx.require_type_is_sized(ret_ty, decl.output.span(), traits::SizedReturnType);
1010 let ret_ty = fcx.instantiate_anon_types(&ret_ty);
1011 fcx.ret_coercion = Some(RefCell::new(CoerceMany::new(ret_ty)));
1012 fn_sig = fcx.tcx.mk_fn_sig(
1013 fn_sig.inputs().iter().cloned(),
1020 let span = body.value.span;
1022 if body.is_generator && can_be_generator {
1023 fcx.yield_ty = Some(fcx.next_ty_var(TypeVariableOrigin::TypeInference(span)));
1026 GatherLocalsVisitor { fcx: &fcx, }.visit_body(body);
1028 // Add formal parameters.
1029 for (arg_ty, arg) in fn_sig.inputs().iter().zip(&body.arguments) {
1030 // Check the pattern.
1031 fcx.check_pat_walk(&arg.pat, arg_ty,
1032 ty::BindingMode::BindByValue(hir::Mutability::MutImmutable), true);
1034 // Check that argument is Sized.
1035 // The check for a non-trivial pattern is a hack to avoid duplicate warnings
1036 // for simple cases like `fn foo(x: Trait)`,
1037 // where we would error once on the parameter as a whole, and once on the binding `x`.
1038 if arg.pat.simple_name().is_none() {
1039 fcx.require_type_is_sized(arg_ty, decl.output.span(), traits::MiscObligation);
1042 fcx.write_ty(arg.hir_id, arg_ty);
1045 let fn_hir_id = fcx.tcx.hir.node_to_hir_id(fn_id);
1046 let gen_ty = if can_be_generator && body.is_generator {
1047 let gen_sig = ty::GenSig {
1048 yield_ty: fcx.yield_ty.unwrap(),
1051 inherited.tables.borrow_mut().generator_sigs_mut().insert(fn_hir_id, Some(gen_sig));
1053 let witness = fcx.next_ty_var(TypeVariableOrigin::MiscVariable(span));
1054 fcx.deferred_generator_interiors.borrow_mut().push((body.id(), witness));
1055 let interior = ty::GeneratorInterior::new(witness);
1057 inherited.tables.borrow_mut().generator_interiors_mut().insert(fn_hir_id, interior);
1061 inherited.tables.borrow_mut().generator_sigs_mut().insert(fn_hir_id, None);
1064 inherited.tables.borrow_mut().liberated_fn_sigs_mut().insert(fn_hir_id, fn_sig);
1066 fcx.check_return_expr(&body.value);
1068 // Finalize the return check by taking the LUB of the return types
1069 // we saw and assigning it to the expected return type. This isn't
1070 // really expected to fail, since the coercions would have failed
1071 // earlier when trying to find a LUB.
1073 // However, the behavior around `!` is sort of complex. In the
1074 // event that the `actual_return_ty` comes back as `!`, that
1075 // indicates that the fn either does not return or "returns" only
1076 // values of type `!`. In this case, if there is an expected
1077 // return type that is *not* `!`, that should be ok. But if the
1078 // return type is being inferred, we want to "fallback" to `!`:
1080 // let x = move || panic!();
1082 // To allow for that, I am creating a type variable with diverging
1083 // fallback. This was deemed ever so slightly better than unifying
1084 // the return value with `!` because it allows for the caller to
1085 // make more assumptions about the return type (e.g., they could do
1087 // let y: Option<u32> = Some(x());
1089 // which would then cause this return type to become `u32`, not
1091 let coercion = fcx.ret_coercion.take().unwrap().into_inner();
1092 let mut actual_return_ty = coercion.complete(&fcx);
1093 if actual_return_ty.is_never() {
1094 actual_return_ty = fcx.next_diverging_ty_var(
1095 TypeVariableOrigin::DivergingFn(span));
1097 fcx.demand_suptype(span, ret_ty, actual_return_ty);
1102 fn check_struct<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1105 let def_id = tcx.hir.local_def_id(id);
1106 let def = tcx.adt_def(def_id);
1107 def.destructor(tcx); // force the destructor to be evaluated
1108 check_representable(tcx, span, def_id);
1110 if def.repr.simd() {
1111 check_simd(tcx, span, def_id);
1114 check_packed(tcx, span, def_id);
1117 fn check_union<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1120 let def_id = tcx.hir.local_def_id(id);
1121 let def = tcx.adt_def(def_id);
1122 def.destructor(tcx); // force the destructor to be evaluated
1123 check_representable(tcx, span, def_id);
1125 check_packed(tcx, span, def_id);
1128 pub fn check_item_type<'a,'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, it: &'tcx hir::Item) {
1129 debug!("check_item_type(it.id={}, it.name={})",
1131 tcx.item_path_str(tcx.hir.local_def_id(it.id)));
1132 let _indenter = indenter();
1134 // Consts can play a role in type-checking, so they are included here.
1135 hir::ItemStatic(..) |
1136 hir::ItemConst(..) => {
1137 tcx.typeck_tables_of(tcx.hir.local_def_id(it.id));
1139 hir::ItemEnum(ref enum_definition, _) => {
1142 &enum_definition.variants,
1145 hir::ItemFn(..) => {} // entirely within check_item_body
1146 hir::ItemImpl(.., ref impl_item_refs) => {
1147 debug!("ItemImpl {} with id {}", it.name, it.id);
1148 let impl_def_id = tcx.hir.local_def_id(it.id);
1149 if let Some(impl_trait_ref) = tcx.impl_trait_ref(impl_def_id) {
1150 check_impl_items_against_trait(tcx,
1155 let trait_def_id = impl_trait_ref.def_id;
1156 check_on_unimplemented(tcx, trait_def_id, it);
1159 hir::ItemTrait(..) => {
1160 let def_id = tcx.hir.local_def_id(it.id);
1161 check_on_unimplemented(tcx, def_id, it);
1163 hir::ItemStruct(..) => {
1164 check_struct(tcx, it.id, it.span);
1166 hir::ItemUnion(..) => {
1167 check_union(tcx, it.id, it.span);
1169 hir::ItemTy(_, ref generics) => {
1170 let def_id = tcx.hir.local_def_id(it.id);
1171 let pty_ty = tcx.type_of(def_id);
1172 check_bounds_are_used(tcx, generics, pty_ty);
1174 hir::ItemForeignMod(ref m) => {
1175 check_abi(tcx, it.span, m.abi);
1177 if m.abi == Abi::RustIntrinsic {
1178 for item in &m.items {
1179 intrinsic::check_intrinsic_type(tcx, item);
1181 } else if m.abi == Abi::PlatformIntrinsic {
1182 for item in &m.items {
1183 intrinsic::check_platform_intrinsic_type(tcx, item);
1186 for item in &m.items {
1187 let generics = tcx.generics_of(tcx.hir.local_def_id(item.id));
1188 if !generics.types.is_empty() {
1189 let mut err = struct_span_err!(tcx.sess, item.span, E0044,
1190 "foreign items may not have type parameters");
1191 span_help!(&mut err, item.span,
1192 "consider using specialization instead of \
1197 if let hir::ForeignItemFn(ref fn_decl, _, _) = item.node {
1198 require_c_abi_if_variadic(tcx, fn_decl, m.abi, item.span);
1203 _ => {/* nothing to do */ }
1207 fn check_on_unimplemented<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1208 trait_def_id: DefId,
1210 let item_def_id = tcx.hir.local_def_id(item.id);
1211 // an error would be reported if this fails.
1212 let _ = traits::OnUnimplementedDirective::of_item(tcx, trait_def_id, item_def_id);
1215 fn report_forbidden_specialization<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1216 impl_item: &hir::ImplItem,
1219 let mut err = struct_span_err!(
1220 tcx.sess, impl_item.span, E0520,
1221 "`{}` specializes an item from a parent `impl`, but \
1222 that item is not marked `default`",
1224 err.span_label(impl_item.span, format!("cannot specialize default item `{}`",
1227 match tcx.span_of_impl(parent_impl) {
1229 err.span_label(span, "parent `impl` is here");
1230 err.note(&format!("to specialize, `{}` in the parent `impl` must be marked `default`",
1234 err.note(&format!("parent implementation is in crate `{}`", cname));
1241 fn check_specialization_validity<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1242 trait_def: &ty::TraitDef,
1243 trait_item: &ty::AssociatedItem,
1245 impl_item: &hir::ImplItem)
1247 let ancestors = trait_def.ancestors(tcx, impl_id);
1249 let kind = match impl_item.node {
1250 hir::ImplItemKind::Const(..) => ty::AssociatedKind::Const,
1251 hir::ImplItemKind::Method(..) => ty::AssociatedKind::Method,
1252 hir::ImplItemKind::Type(_) => ty::AssociatedKind::Type
1255 let parent = ancestors.defs(tcx, trait_item.name, kind, trait_def.def_id).skip(1).next()
1256 .map(|node_item| node_item.map(|parent| parent.defaultness));
1258 if let Some(parent) = parent {
1259 if tcx.impl_item_is_final(&parent) {
1260 report_forbidden_specialization(tcx, impl_item, parent.node.def_id());
1266 fn check_impl_items_against_trait<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1269 impl_trait_ref: ty::TraitRef<'tcx>,
1270 impl_item_refs: &[hir::ImplItemRef]) {
1271 // If the trait reference itself is erroneous (so the compilation is going
1272 // to fail), skip checking the items here -- the `impl_item` table in `tcx`
1273 // isn't populated for such impls.
1274 if impl_trait_ref.references_error() { return; }
1276 // Locate trait definition and items
1277 let trait_def = tcx.trait_def(impl_trait_ref.def_id);
1278 let mut overridden_associated_type = None;
1280 let impl_items = || impl_item_refs.iter().map(|iiref| tcx.hir.impl_item(iiref.id));
1282 // Check existing impl methods to see if they are both present in trait
1283 // and compatible with trait signature
1284 for impl_item in impl_items() {
1285 let ty_impl_item = tcx.associated_item(tcx.hir.local_def_id(impl_item.id));
1286 let ty_trait_item = tcx.associated_items(impl_trait_ref.def_id)
1287 .find(|ac| Namespace::from(&impl_item.node) == Namespace::from(ac.kind) &&
1288 tcx.hygienic_eq(ty_impl_item.name, ac.name, impl_trait_ref.def_id))
1290 // Not compatible, but needed for the error message
1291 tcx.associated_items(impl_trait_ref.def_id)
1292 .find(|ac| tcx.hygienic_eq(ty_impl_item.name, ac.name, impl_trait_ref.def_id))
1295 // Check that impl definition matches trait definition
1296 if let Some(ty_trait_item) = ty_trait_item {
1297 match impl_item.node {
1298 hir::ImplItemKind::Const(..) => {
1299 // Find associated const definition.
1300 if ty_trait_item.kind == ty::AssociatedKind::Const {
1301 compare_const_impl(tcx,
1307 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0323,
1308 "item `{}` is an associated const, \
1309 which doesn't match its trait `{}`",
1312 err.span_label(impl_item.span, "does not match trait");
1313 // We can only get the spans from local trait definition
1314 // Same for E0324 and E0325
1315 if let Some(trait_span) = tcx.hir.span_if_local(ty_trait_item.def_id) {
1316 err.span_label(trait_span, "item in trait");
1321 hir::ImplItemKind::Method(..) => {
1322 let trait_span = tcx.hir.span_if_local(ty_trait_item.def_id);
1323 if ty_trait_item.kind == ty::AssociatedKind::Method {
1324 compare_impl_method(tcx,
1331 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0324,
1332 "item `{}` is an associated method, \
1333 which doesn't match its trait `{}`",
1336 err.span_label(impl_item.span, "does not match trait");
1337 if let Some(trait_span) = tcx.hir.span_if_local(ty_trait_item.def_id) {
1338 err.span_label(trait_span, "item in trait");
1343 hir::ImplItemKind::Type(_) => {
1344 if ty_trait_item.kind == ty::AssociatedKind::Type {
1345 if ty_trait_item.defaultness.has_value() {
1346 overridden_associated_type = Some(impl_item);
1349 let mut err = struct_span_err!(tcx.sess, impl_item.span, E0325,
1350 "item `{}` is an associated type, \
1351 which doesn't match its trait `{}`",
1354 err.span_label(impl_item.span, "does not match trait");
1355 if let Some(trait_span) = tcx.hir.span_if_local(ty_trait_item.def_id) {
1356 err.span_label(trait_span, "item in trait");
1363 check_specialization_validity(tcx, trait_def, &ty_trait_item, impl_id, impl_item);
1367 // Check for missing items from trait
1368 let mut missing_items = Vec::new();
1369 let mut invalidated_items = Vec::new();
1370 let associated_type_overridden = overridden_associated_type.is_some();
1371 for trait_item in tcx.associated_items(impl_trait_ref.def_id) {
1372 let is_implemented = trait_def.ancestors(tcx, impl_id)
1373 .defs(tcx, trait_item.name, trait_item.kind, impl_trait_ref.def_id)
1375 .map(|node_item| !node_item.node.is_from_trait())
1378 if !is_implemented {
1379 if !trait_item.defaultness.has_value() {
1380 missing_items.push(trait_item);
1381 } else if associated_type_overridden {
1382 invalidated_items.push(trait_item.name);
1387 if !missing_items.is_empty() {
1388 let mut err = struct_span_err!(tcx.sess, impl_span, E0046,
1389 "not all trait items implemented, missing: `{}`",
1390 missing_items.iter()
1391 .map(|trait_item| trait_item.name.to_string())
1392 .collect::<Vec<_>>().join("`, `"));
1393 err.span_label(impl_span, format!("missing `{}` in implementation",
1394 missing_items.iter()
1395 .map(|trait_item| trait_item.name.to_string())
1396 .collect::<Vec<_>>().join("`, `")));
1397 for trait_item in missing_items {
1398 if let Some(span) = tcx.hir.span_if_local(trait_item.def_id) {
1399 err.span_label(span, format!("`{}` from trait", trait_item.name));
1401 err.note_trait_signature(trait_item.name.to_string(),
1402 trait_item.signature(&tcx));
1408 if !invalidated_items.is_empty() {
1409 let invalidator = overridden_associated_type.unwrap();
1410 span_err!(tcx.sess, invalidator.span, E0399,
1411 "the following trait items need to be reimplemented \
1412 as `{}` was overridden: `{}`",
1414 invalidated_items.iter()
1415 .map(|name| name.to_string())
1416 .collect::<Vec<_>>().join("`, `"))
1420 /// Checks whether a type can be represented in memory. In particular, it
1421 /// identifies types that contain themselves without indirection through a
1422 /// pointer, which would mean their size is unbounded.
1423 fn check_representable<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1427 let rty = tcx.type_of(item_def_id);
1429 // Check that it is possible to represent this type. This call identifies
1430 // (1) types that contain themselves and (2) types that contain a different
1431 // recursive type. It is only necessary to throw an error on those that
1432 // contain themselves. For case 2, there must be an inner type that will be
1433 // caught by case 1.
1434 match rty.is_representable(tcx, sp) {
1435 Representability::SelfRecursive(spans) => {
1436 let mut err = tcx.recursive_type_with_infinite_size_error(item_def_id);
1438 err.span_label(span, "recursive without indirection");
1443 Representability::Representable | Representability::ContainsRecursive => (),
1448 pub fn check_simd<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, sp: Span, def_id: DefId) {
1449 let t = tcx.type_of(def_id);
1451 ty::TyAdt(def, substs) if def.is_struct() => {
1452 let fields = &def.struct_variant().fields;
1453 if fields.is_empty() {
1454 span_err!(tcx.sess, sp, E0075, "SIMD vector cannot be empty");
1457 let e = fields[0].ty(tcx, substs);
1458 if !fields.iter().all(|f| f.ty(tcx, substs) == e) {
1459 struct_span_err!(tcx.sess, sp, E0076, "SIMD vector should be homogeneous")
1460 .span_label(sp, "SIMD elements must have the same type")
1465 ty::TyParam(_) => { /* struct<T>(T, T, T, T) is ok */ }
1466 _ if e.is_machine() => { /* struct(u8, u8, u8, u8) is ok */ }
1468 span_err!(tcx.sess, sp, E0077,
1469 "SIMD vector element type should be machine type");
1478 fn check_packed<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, sp: Span, def_id: DefId) {
1479 if tcx.adt_def(def_id).repr.packed() {
1480 if tcx.adt_def(def_id).repr.align > 0 {
1481 struct_span_err!(tcx.sess, sp, E0587,
1482 "type has conflicting packed and align representation hints").emit();
1484 else if check_packed_inner(tcx, def_id, &mut Vec::new()) {
1485 struct_span_err!(tcx.sess, sp, E0588,
1486 "packed type cannot transitively contain a `[repr(align)]` type").emit();
1491 fn check_packed_inner<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1493 stack: &mut Vec<DefId>) -> bool {
1494 let t = tcx.type_of(def_id);
1495 if stack.contains(&def_id) {
1496 debug!("check_packed_inner: {:?} is recursive", t);
1500 ty::TyAdt(def, substs) if def.is_struct() || def.is_union() => {
1501 if tcx.adt_def(def.did).repr.align > 0 {
1504 // push struct def_id before checking fields
1506 for field in &def.struct_variant().fields {
1507 let f = field.ty(tcx, substs);
1509 ty::TyAdt(def, _) => {
1510 if check_packed_inner(tcx, def.did, stack) {
1517 // only need to pop if not early out
1525 #[allow(trivial_numeric_casts)]
1526 pub fn check_enum<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1528 vs: &'tcx [hir::Variant],
1530 let def_id = tcx.hir.local_def_id(id);
1531 let def = tcx.adt_def(def_id);
1532 def.destructor(tcx); // force the destructor to be evaluated
1534 if vs.is_empty() && tcx.has_attr(def_id, "repr") {
1536 tcx.sess, sp, E0084,
1537 "unsupported representation for zero-variant enum")
1538 .span_label(sp, "unsupported enum representation")
1542 let repr_type_ty = def.repr.discr_type().to_ty(tcx);
1543 if repr_type_ty == tcx.types.i128 || repr_type_ty == tcx.types.u128 {
1544 if !tcx.sess.features.borrow().repr128 {
1545 emit_feature_err(&tcx.sess.parse_sess,
1548 GateIssue::Language,
1549 "repr with 128-bit type is unstable");
1554 if let Some(e) = v.node.disr_expr {
1555 tcx.typeck_tables_of(tcx.hir.local_def_id(e.node_id));
1559 let mut disr_vals: Vec<ConstInt> = Vec::new();
1560 for (discr, v) in def.discriminants(tcx).zip(vs) {
1561 // Check for duplicate discriminant values
1562 if let Some(i) = disr_vals.iter().position(|&x| x == discr) {
1563 let variant_i_node_id = tcx.hir.as_local_node_id(def.variants[i].did).unwrap();
1564 let variant_i = tcx.hir.expect_variant(variant_i_node_id);
1565 let i_span = match variant_i.node.disr_expr {
1566 Some(expr) => tcx.hir.span(expr.node_id),
1567 None => tcx.hir.span(variant_i_node_id)
1569 let span = match v.node.disr_expr {
1570 Some(expr) => tcx.hir.span(expr.node_id),
1573 struct_span_err!(tcx.sess, span, E0081,
1574 "discriminant value `{}` already exists", disr_vals[i])
1575 .span_label(i_span, format!("first use of `{}`", disr_vals[i]))
1576 .span_label(span , format!("enum already has `{}`", disr_vals[i]))
1579 disr_vals.push(discr);
1582 check_representable(tcx, sp, def_id);
1585 impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> {
1586 fn tcx<'b>(&'b self) -> TyCtxt<'b, 'gcx, 'tcx> { self.tcx }
1588 fn get_type_parameter_bounds(&self, _: Span, def_id: DefId)
1589 -> ty::GenericPredicates<'tcx>
1592 let node_id = tcx.hir.as_local_node_id(def_id).unwrap();
1593 let item_id = tcx.hir.ty_param_owner(node_id);
1594 let item_def_id = tcx.hir.local_def_id(item_id);
1595 let generics = tcx.generics_of(item_def_id);
1596 let index = generics.type_param_to_index[&def_id.index];
1597 ty::GenericPredicates {
1599 predicates: self.param_env.caller_bounds.iter().filter(|predicate| {
1601 ty::Predicate::Trait(ref data) => {
1602 data.0.self_ty().is_param(index)
1606 }).cloned().collect()
1610 fn re_infer(&self, span: Span, def: Option<&ty::RegionParameterDef>)
1611 -> Option<ty::Region<'tcx>> {
1613 Some(def) => infer::EarlyBoundRegion(span, def.name),
1614 None => infer::MiscVariable(span)
1616 Some(self.next_region_var(v))
1619 fn ty_infer(&self, span: Span) -> Ty<'tcx> {
1620 self.next_ty_var(TypeVariableOrigin::TypeInference(span))
1623 fn ty_infer_for_def(&self,
1624 ty_param_def: &ty::TypeParameterDef,
1625 substs: &[Kind<'tcx>],
1626 span: Span) -> Ty<'tcx> {
1627 self.type_var_for_def(span, ty_param_def, substs)
1630 fn projected_ty_from_poly_trait_ref(&self,
1633 poly_trait_ref: ty::PolyTraitRef<'tcx>)
1636 let (trait_ref, _) =
1637 self.replace_late_bound_regions_with_fresh_var(
1639 infer::LateBoundRegionConversionTime::AssocTypeProjection(item_def_id),
1642 self.tcx().mk_projection(item_def_id, trait_ref.substs)
1645 fn normalize_ty(&self, span: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
1646 if ty.has_escaping_regions() {
1647 ty // FIXME: normalization and escaping regions
1649 self.normalize_associated_types_in(span, &ty)
1653 fn set_tainted_by_errors(&self) {
1654 self.infcx.set_tainted_by_errors()
1657 fn record_ty(&self, hir_id: hir::HirId, ty: Ty<'tcx>, _span: Span) {
1658 self.write_ty(hir_id, ty)
1662 /// Controls whether the arguments are tupled. This is used for the call
1665 /// Tupling means that all call-side arguments are packed into a tuple and
1666 /// passed as a single parameter. For example, if tupling is enabled, this
1669 /// fn f(x: (isize, isize))
1671 /// Can be called as:
1678 #[derive(Clone, Eq, PartialEq)]
1679 enum TupleArgumentsFlag {
1684 impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
1685 pub fn new(inh: &'a Inherited<'a, 'gcx, 'tcx>,
1686 param_env: ty::ParamEnv<'tcx>,
1687 body_id: ast::NodeId)
1688 -> FnCtxt<'a, 'gcx, 'tcx> {
1692 err_count_on_creation: inh.tcx.sess.err_count(),
1695 ps: RefCell::new(UnsafetyState::function(hir::Unsafety::Normal,
1696 ast::CRATE_NODE_ID)),
1697 diverges: Cell::new(Diverges::Maybe),
1698 has_errors: Cell::new(false),
1699 enclosing_breakables: RefCell::new(EnclosingBreakables {
1707 pub fn sess(&self) -> &Session {
1711 pub fn err_count_since_creation(&self) -> usize {
1712 self.tcx.sess.err_count() - self.err_count_on_creation
1715 /// Produce warning on the given node, if the current point in the
1716 /// function is unreachable, and there hasn't been another warning.
1717 fn warn_if_unreachable(&self, id: ast::NodeId, span: Span, kind: &str) {
1718 if self.diverges.get() == Diverges::Always {
1719 self.diverges.set(Diverges::WarnedAlways);
1721 debug!("warn_if_unreachable: id={:?} span={:?} kind={}", id, span, kind);
1723 self.tcx().lint_node(
1724 lint::builtin::UNREACHABLE_CODE,
1726 &format!("unreachable {}", kind));
1732 code: ObligationCauseCode<'tcx>)
1733 -> ObligationCause<'tcx> {
1734 ObligationCause::new(span, self.body_id, code)
1737 pub fn misc(&self, span: Span) -> ObligationCause<'tcx> {
1738 self.cause(span, ObligationCauseCode::MiscObligation)
1741 /// Resolves type variables in `ty` if possible. Unlike the infcx
1742 /// version (resolve_type_vars_if_possible), this version will
1743 /// also select obligations if it seems useful, in an effort
1744 /// to get more type information.
1745 fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
1746 debug!("resolve_type_vars_with_obligations(ty={:?})", ty);
1748 // No TyInfer()? Nothing needs doing.
1749 if !ty.has_infer_types() {
1750 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
1754 // If `ty` is a type variable, see whether we already know what it is.
1755 ty = self.resolve_type_vars_if_possible(&ty);
1756 if !ty.has_infer_types() {
1757 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
1761 // If not, try resolving pending obligations as much as
1762 // possible. This can help substantially when there are
1763 // indirect dependencies that don't seem worth tracking
1765 self.select_obligations_where_possible();
1766 ty = self.resolve_type_vars_if_possible(&ty);
1768 debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
1772 fn record_deferred_call_resolution(&self,
1773 closure_def_id: DefId,
1774 r: DeferredCallResolution<'gcx, 'tcx>) {
1775 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
1776 deferred_call_resolutions.entry(closure_def_id).or_insert(vec![]).push(r);
1779 fn remove_deferred_call_resolutions(&self,
1780 closure_def_id: DefId)
1781 -> Vec<DeferredCallResolution<'gcx, 'tcx>>
1783 let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
1784 deferred_call_resolutions.remove(&closure_def_id).unwrap_or(vec![])
1787 pub fn tag(&self) -> String {
1788 let self_ptr: *const FnCtxt = self;
1789 format!("{:?}", self_ptr)
1792 pub fn local_ty(&self, span: Span, nid: ast::NodeId) -> Ty<'tcx> {
1793 match self.locals.borrow().get(&nid) {
1796 span_bug!(span, "no type for local variable {}",
1797 self.tcx.hir.node_to_string(nid));
1803 pub fn write_ty(&self, id: hir::HirId, ty: Ty<'tcx>) {
1804 debug!("write_ty({:?}, {:?}) in fcx {}",
1805 id, self.resolve_type_vars_if_possible(&ty), self.tag());
1806 self.tables.borrow_mut().node_types_mut().insert(id, ty);
1808 if ty.references_error() {
1809 self.has_errors.set(true);
1810 self.set_tainted_by_errors();
1814 // The NodeId and the ItemLocalId must identify the same item. We just pass
1815 // both of them for consistency checking.
1816 pub fn write_method_call(&self,
1818 method: MethodCallee<'tcx>) {
1821 .type_dependent_defs_mut()
1822 .insert(hir_id, Def::Method(method.def_id));
1823 self.write_substs(hir_id, method.substs);
1826 pub fn write_substs(&self, node_id: hir::HirId, substs: &'tcx Substs<'tcx>) {
1827 if !substs.is_noop() {
1828 debug!("write_substs({:?}, {:?}) in fcx {}",
1833 self.tables.borrow_mut().node_substs_mut().insert(node_id, substs);
1837 pub fn apply_adjustments(&self, expr: &hir::Expr, adj: Vec<Adjustment<'tcx>>) {
1838 debug!("apply_adjustments(expr={:?}, adj={:?})", expr, adj);
1844 match self.tables.borrow_mut().adjustments_mut().entry(expr.hir_id) {
1845 Entry::Vacant(entry) => { entry.insert(adj); },
1846 Entry::Occupied(mut entry) => {
1847 debug!(" - composing on top of {:?}", entry.get());
1848 match (&entry.get()[..], &adj[..]) {
1849 // Applying any adjustment on top of a NeverToAny
1850 // is a valid NeverToAny adjustment, because it can't
1852 (&[Adjustment { kind: Adjust::NeverToAny, .. }], _) => return,
1854 Adjustment { kind: Adjust::Deref(_), .. },
1855 Adjustment { kind: Adjust::Borrow(AutoBorrow::Ref(..)), .. },
1857 Adjustment { kind: Adjust::Deref(_), .. },
1858 .. // Any following adjustments are allowed.
1860 // A reborrow has no effect before a dereference.
1862 // FIXME: currently we never try to compose autoderefs
1863 // and ReifyFnPointer/UnsafeFnPointer, but we could.
1865 bug!("while adjusting {:?}, can't compose {:?} and {:?}",
1866 expr, entry.get(), adj)
1868 *entry.get_mut() = adj;
1873 /// Basically whenever we are converting from a type scheme into
1874 /// the fn body space, we always want to normalize associated
1875 /// types as well. This function combines the two.
1876 fn instantiate_type_scheme<T>(&self,
1878 substs: &Substs<'tcx>,
1881 where T : TypeFoldable<'tcx>
1883 let value = value.subst(self.tcx, substs);
1884 let result = self.normalize_associated_types_in(span, &value);
1885 debug!("instantiate_type_scheme(value={:?}, substs={:?}) = {:?}",
1892 /// As `instantiate_type_scheme`, but for the bounds found in a
1893 /// generic type scheme.
1894 fn instantiate_bounds(&self, span: Span, def_id: DefId, substs: &Substs<'tcx>)
1895 -> ty::InstantiatedPredicates<'tcx> {
1896 let bounds = self.tcx.predicates_of(def_id);
1897 let result = bounds.instantiate(self.tcx, substs);
1898 let result = self.normalize_associated_types_in(span, &result);
1899 debug!("instantiate_bounds(bounds={:?}, substs={:?}) = {:?}",
1906 /// Replace all anonymized types with fresh inference variables
1907 /// and record them for writeback.
1908 fn instantiate_anon_types<T: TypeFoldable<'tcx>>(&self, value: &T) -> T {
1909 value.fold_with(&mut BottomUpFolder { tcx: self.tcx, fldop: |ty| {
1910 if let ty::TyAnon(def_id, substs) = ty.sty {
1911 // Use the same type variable if the exact same TyAnon appears more
1912 // than once in the return type (e.g. if it's passed to a type alias).
1913 let id = self.tcx.hir.as_local_node_id(def_id).unwrap();
1914 if let Some(ty_var) = self.anon_types.borrow().get(&id) {
1917 let span = self.tcx.def_span(def_id);
1918 let ty_var = self.next_ty_var(TypeVariableOrigin::TypeInference(span));
1919 self.anon_types.borrow_mut().insert(id, ty_var);
1921 let predicates_of = self.tcx.predicates_of(def_id);
1922 let bounds = predicates_of.instantiate(self.tcx, substs);
1924 for predicate in bounds.predicates {
1925 // Change the predicate to refer to the type variable,
1926 // which will be the concrete type, instead of the TyAnon.
1927 // This also instantiates nested `impl Trait`.
1928 let predicate = self.instantiate_anon_types(&predicate);
1930 // Require that the predicate holds for the concrete type.
1931 let cause = traits::ObligationCause::new(span, self.body_id,
1932 traits::SizedReturnType);
1933 self.register_predicate(traits::Obligation::new(cause,
1945 fn normalize_associated_types_in<T>(&self, span: Span, value: &T) -> T
1946 where T : TypeFoldable<'tcx>
1948 self.inh.normalize_associated_types_in(span, self.body_id, self.param_env, value)
1951 fn normalize_associated_types_in_as_infer_ok<T>(&self, span: Span, value: &T)
1953 where T : TypeFoldable<'tcx>
1955 self.inh.partially_normalize_associated_types_in(span,
1961 pub fn require_type_meets(&self,
1964 code: traits::ObligationCauseCode<'tcx>,
1967 self.register_bound(
1970 traits::ObligationCause::new(span, self.body_id, code));
1973 pub fn require_type_is_sized(&self,
1976 code: traits::ObligationCauseCode<'tcx>)
1978 let lang_item = self.tcx.require_lang_item(lang_items::SizedTraitLangItem);
1979 self.require_type_meets(ty, span, code, lang_item);
1982 pub fn register_bound(&self,
1985 cause: traits::ObligationCause<'tcx>)
1987 self.fulfillment_cx.borrow_mut()
1988 .register_bound(self, self.param_env, ty, def_id, cause);
1991 pub fn to_ty(&self, ast_t: &hir::Ty) -> Ty<'tcx> {
1992 let t = AstConv::ast_ty_to_ty(self, ast_t);
1993 self.register_wf_obligation(t, ast_t.span, traits::MiscObligation);
1997 pub fn node_ty(&self, id: hir::HirId) -> Ty<'tcx> {
1998 match self.tables.borrow().node_types().get(id) {
2000 None if self.is_tainted_by_errors() => self.tcx.types.err,
2002 let node_id = self.tcx.hir.definitions().find_node_for_hir_id(id);
2003 bug!("no type for node {}: {} in fcx {}",
2004 node_id, self.tcx.hir.node_to_string(node_id),
2010 /// Registers an obligation for checking later, during regionck, that the type `ty` must
2011 /// outlive the region `r`.
2012 pub fn register_wf_obligation(&self,
2015 code: traits::ObligationCauseCode<'tcx>)
2017 // WF obligations never themselves fail, so no real need to give a detailed cause:
2018 let cause = traits::ObligationCause::new(span, self.body_id, code);
2019 self.register_predicate(traits::Obligation::new(cause,
2021 ty::Predicate::WellFormed(ty)));
2024 /// Registers obligations that all types appearing in `substs` are well-formed.
2025 pub fn add_wf_bounds(&self, substs: &Substs<'tcx>, expr: &hir::Expr)
2027 for ty in substs.types() {
2028 self.register_wf_obligation(ty, expr.span, traits::MiscObligation);
2032 /// Given a fully substituted set of bounds (`generic_bounds`), and the values with which each
2033 /// type/region parameter was instantiated (`substs`), creates and registers suitable
2034 /// trait/region obligations.
2036 /// For example, if there is a function:
2039 /// fn foo<'a,T:'a>(...)
2042 /// and a reference:
2048 /// Then we will create a fresh region variable `'$0` and a fresh type variable `$1` for `'a`
2049 /// and `T`. This routine will add a region obligation `$1:'$0` and register it locally.
2050 pub fn add_obligations_for_parameters(&self,
2051 cause: traits::ObligationCause<'tcx>,
2052 predicates: &ty::InstantiatedPredicates<'tcx>)
2054 assert!(!predicates.has_escaping_regions());
2056 debug!("add_obligations_for_parameters(predicates={:?})",
2059 for obligation in traits::predicates_for_generics(cause, self.param_env, predicates) {
2060 self.register_predicate(obligation);
2064 // FIXME(arielb1): use this instead of field.ty everywhere
2065 // Only for fields! Returns <none> for methods>
2066 // Indifferent to privacy flags
2067 pub fn field_ty(&self,
2069 field: &'tcx ty::FieldDef,
2070 substs: &Substs<'tcx>)
2073 self.normalize_associated_types_in(span,
2074 &field.ty(self.tcx, substs))
2077 fn check_casts(&self) {
2078 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
2079 for cast in deferred_cast_checks.drain(..) {
2084 fn resolve_generator_interiors(&self, def_id: DefId) {
2085 let mut deferred_generator_interiors = self.deferred_generator_interiors.borrow_mut();
2086 for (body_id, witness) in deferred_generator_interiors.drain(..) {
2087 generator_interior::resolve_interior(self, def_id, body_id, witness);
2091 /// Apply "fallbacks" to some types
2092 /// unconstrained types get replaced with ! or () (depending on whether
2093 /// feature(never_type) is enabled), unconstrained ints with i32, and
2094 /// unconstrained floats with f64.
2095 fn default_type_parameters(&self) {
2096 use rustc::ty::error::UnconstrainedNumeric::Neither;
2097 use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedInt, UnconstrainedFloat};
2099 // Defaulting inference variables becomes very dubious if we have
2100 // encountered type-checking errors. Therefore, if we think we saw
2101 // some errors in this function, just resolve all uninstanted type
2102 // varibles to TyError.
2103 if self.is_tainted_by_errors() {
2104 for ty in &self.unsolved_variables() {
2105 if let ty::TyInfer(_) = self.shallow_resolve(ty).sty {
2106 debug!("default_type_parameters: defaulting `{:?}` to error", ty);
2107 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx().types.err);
2113 for ty in &self.unsolved_variables() {
2114 let resolved = self.resolve_type_vars_if_possible(ty);
2115 if self.type_var_diverges(resolved) {
2116 debug!("default_type_parameters: defaulting `{:?}` to `!` because it diverges",
2118 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty,
2119 self.tcx.mk_diverging_default());
2121 match self.type_is_unconstrained_numeric(resolved) {
2122 UnconstrainedInt => {
2123 debug!("default_type_parameters: defaulting `{:?}` to `i32`",
2125 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.i32)
2127 UnconstrainedFloat => {
2128 debug!("default_type_parameters: defaulting `{:?}` to `f32`",
2130 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.f64)
2138 // Implements type inference fallback algorithm
2139 fn select_all_obligations_and_apply_defaults(&self) {
2140 self.select_obligations_where_possible();
2141 self.default_type_parameters();
2142 self.select_obligations_where_possible();
2145 fn select_all_obligations_or_error(&self) {
2146 debug!("select_all_obligations_or_error");
2148 // upvar inference should have ensured that all deferred call
2149 // resolutions are handled by now.
2150 assert!(self.deferred_call_resolutions.borrow().is_empty());
2152 self.select_all_obligations_and_apply_defaults();
2154 let mut fulfillment_cx = self.fulfillment_cx.borrow_mut();
2156 match fulfillment_cx.select_all_or_error(self) {
2158 Err(errors) => { self.report_fulfillment_errors(&errors, self.inh.body_id); }
2162 /// Select as many obligations as we can at present.
2163 fn select_obligations_where_possible(&self) {
2164 match self.fulfillment_cx.borrow_mut().select_where_possible(self) {
2166 Err(errors) => { self.report_fulfillment_errors(&errors, self.inh.body_id); }
2170 /// For the overloaded lvalue expressions (`*x`, `x[3]`), the trait
2171 /// returns a type of `&T`, but the actual type we assign to the
2172 /// *expression* is `T`. So this function just peels off the return
2173 /// type by one layer to yield `T`.
2174 fn make_overloaded_lvalue_return_type(&self,
2175 method: MethodCallee<'tcx>)
2176 -> ty::TypeAndMut<'tcx>
2178 // extract method return type, which will be &T;
2179 let ret_ty = method.sig.output();
2181 // method returns &T, but the type as visible to user is T, so deref
2182 ret_ty.builtin_deref(true, NoPreference).unwrap()
2185 fn lookup_indexing(&self,
2187 base_expr: &'gcx hir::Expr,
2190 lvalue_pref: LvaluePreference)
2191 -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)>
2193 // FIXME(#18741) -- this is almost but not quite the same as the
2194 // autoderef that normal method probing does. They could likely be
2197 let mut autoderef = self.autoderef(base_expr.span, base_ty);
2198 let mut result = None;
2199 while result.is_none() && autoderef.next().is_some() {
2200 result = self.try_index_step(expr, base_expr, &autoderef, lvalue_pref, idx_ty);
2202 autoderef.finalize();
2206 /// To type-check `base_expr[index_expr]`, we progressively autoderef
2207 /// (and otherwise adjust) `base_expr`, looking for a type which either
2208 /// supports builtin indexing or overloaded indexing.
2209 /// This loop implements one step in that search; the autoderef loop
2210 /// is implemented by `lookup_indexing`.
2211 fn try_index_step(&self,
2213 base_expr: &hir::Expr,
2214 autoderef: &Autoderef<'a, 'gcx, 'tcx>,
2215 lvalue_pref: LvaluePreference,
2217 -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)>
2219 let adjusted_ty = autoderef.unambiguous_final_ty();
2220 debug!("try_index_step(expr={:?}, base_expr={:?}, adjusted_ty={:?}, \
2227 // First, try built-in indexing.
2228 match (adjusted_ty.builtin_index(), &index_ty.sty) {
2229 (Some(ty), &ty::TyUint(ast::UintTy::Us)) | (Some(ty), &ty::TyInfer(ty::IntVar(_))) => {
2230 debug!("try_index_step: success, using built-in indexing");
2231 let adjustments = autoderef.adjust_steps(lvalue_pref);
2232 self.apply_adjustments(base_expr, adjustments);
2233 return Some((self.tcx.types.usize, ty));
2238 for &unsize in &[false, true] {
2239 let mut self_ty = adjusted_ty;
2241 // We only unsize arrays here.
2242 if let ty::TyArray(element_ty, _) = adjusted_ty.sty {
2243 self_ty = self.tcx.mk_slice(element_ty);
2249 // If some lookup succeeds, write callee into table and extract index/element
2250 // type from the method signature.
2251 // If some lookup succeeded, install method in table
2252 let input_ty = self.next_ty_var(TypeVariableOrigin::AutoDeref(base_expr.span));
2253 let method = self.try_overloaded_lvalue_op(
2254 expr.span, self_ty, &[input_ty], lvalue_pref, LvalueOp::Index);
2256 let result = method.map(|ok| {
2257 debug!("try_index_step: success, using overloaded indexing");
2258 let method = self.register_infer_ok_obligations(ok);
2260 let mut adjustments = autoderef.adjust_steps(lvalue_pref);
2261 if let ty::TyRef(region, mt) = method.sig.inputs()[0].sty {
2262 adjustments.push(Adjustment {
2263 kind: Adjust::Borrow(AutoBorrow::Ref(region, mt.mutbl)),
2264 target: self.tcx.mk_ref(region, ty::TypeAndMut {
2271 adjustments.push(Adjustment {
2272 kind: Adjust::Unsize,
2273 target: method.sig.inputs()[0]
2276 self.apply_adjustments(base_expr, adjustments);
2278 self.write_method_call(expr.hir_id, method);
2279 (input_ty, self.make_overloaded_lvalue_return_type(method).ty)
2281 if result.is_some() {
2289 fn resolve_lvalue_op(&self, op: LvalueOp, is_mut: bool) -> (Option<DefId>, Symbol) {
2290 let (tr, name) = match (op, is_mut) {
2291 (LvalueOp::Deref, false) =>
2292 (self.tcx.lang_items().deref_trait(), "deref"),
2293 (LvalueOp::Deref, true) =>
2294 (self.tcx.lang_items().deref_mut_trait(), "deref_mut"),
2295 (LvalueOp::Index, false) =>
2296 (self.tcx.lang_items().index_trait(), "index"),
2297 (LvalueOp::Index, true) =>
2298 (self.tcx.lang_items().index_mut_trait(), "index_mut"),
2300 (tr, Symbol::intern(name))
2303 fn try_overloaded_lvalue_op(&self,
2306 arg_tys: &[Ty<'tcx>],
2307 lvalue_pref: LvaluePreference,
2309 -> Option<InferOk<'tcx, MethodCallee<'tcx>>>
2311 debug!("try_overloaded_lvalue_op({:?},{:?},{:?},{:?})",
2317 // Try Mut first, if preferred.
2318 let (mut_tr, mut_op) = self.resolve_lvalue_op(op, true);
2319 let method = match (lvalue_pref, mut_tr) {
2320 (PreferMutLvalue, Some(trait_did)) => {
2321 self.lookup_method_in_trait(span, mut_op, trait_did, base_ty, Some(arg_tys))
2326 // Otherwise, fall back to the immutable version.
2327 let (imm_tr, imm_op) = self.resolve_lvalue_op(op, false);
2328 let method = match (method, imm_tr) {
2329 (None, Some(trait_did)) => {
2330 self.lookup_method_in_trait(span, imm_op, trait_did, base_ty, Some(arg_tys))
2332 (method, _) => method,
2338 fn check_method_argument_types(&self,
2341 method: Result<MethodCallee<'tcx>, ()>,
2342 args_no_rcvr: &'gcx [hir::Expr],
2343 tuple_arguments: TupleArgumentsFlag,
2344 expected: Expectation<'tcx>)
2346 let has_error = match method {
2348 method.substs.references_error() || method.sig.references_error()
2353 let err_inputs = self.err_args(args_no_rcvr.len());
2355 let err_inputs = match tuple_arguments {
2356 DontTupleArguments => err_inputs,
2357 TupleArguments => vec![self.tcx.intern_tup(&err_inputs[..], false)],
2360 self.check_argument_types(sp, expr_sp, &err_inputs[..], &[], args_no_rcvr,
2361 false, tuple_arguments, None);
2362 return self.tcx.types.err;
2365 let method = method.unwrap();
2366 // HACK(eddyb) ignore self in the definition (see above).
2367 let expected_arg_tys = self.expected_inputs_for_expected_output(
2370 method.sig.output(),
2371 &method.sig.inputs()[1..]
2373 self.check_argument_types(sp, expr_sp, &method.sig.inputs()[1..], &expected_arg_tys[..],
2374 args_no_rcvr, method.sig.variadic, tuple_arguments,
2375 self.tcx.hir.span_if_local(method.def_id));
2379 /// Generic function that factors out common logic from function calls,
2380 /// method calls and overloaded operators.
2381 fn check_argument_types(&self,
2384 fn_inputs: &[Ty<'tcx>],
2385 expected_arg_tys: &[Ty<'tcx>],
2386 args: &'gcx [hir::Expr],
2388 tuple_arguments: TupleArgumentsFlag,
2389 def_span: Option<Span>) {
2392 // Grab the argument types, supplying fresh type variables
2393 // if the wrong number of arguments were supplied
2394 let supplied_arg_count = if tuple_arguments == DontTupleArguments {
2400 // All the input types from the fn signature must outlive the call
2401 // so as to validate implied bounds.
2402 for &fn_input_ty in fn_inputs {
2403 self.register_wf_obligation(fn_input_ty, sp, traits::MiscObligation);
2406 let mut expected_arg_tys = expected_arg_tys;
2407 let expected_arg_count = fn_inputs.len();
2409 let sp_args = if args.len() > 0 {
2410 let (first, args) = args.split_at(1);
2411 let mut sp_tmp = first[0].span;
2413 let sp_opt = self.sess().codemap().merge_spans(sp_tmp, arg.span);
2414 if ! sp_opt.is_some() {
2417 sp_tmp = sp_opt.unwrap();
2424 fn parameter_count_error<'tcx>(sess: &Session,
2427 expected_count: usize,
2431 def_span: Option<Span>,
2433 let mut err = sess.struct_span_err_with_code(sp,
2434 &format!("this function takes {}{} parameter{} but {} parameter{} supplied",
2435 if variadic {"at least "} else {""},
2437 if expected_count == 1 {""} else {"s"},
2439 if arg_count == 1 {" was"} else {"s were"}),
2440 DiagnosticId::Error(error_code.to_owned()));
2442 if let Some(def_s) = def_span {
2443 err.span_label(def_s, "defined here");
2446 let sugg_span = expr_sp.end_point();
2447 // remove closing `)` from the span
2448 let sugg_span = sugg_span.with_hi(sugg_span.lo());
2449 err.span_suggestion(
2451 "expected the unit value `()`; create it with empty parentheses",
2452 String::from("()"));
2454 err.span_label(sp, format!("expected {}{} parameter{}",
2455 if variadic {"at least "} else {""},
2457 if expected_count == 1 {""} else {"s"}));
2462 let formal_tys = if tuple_arguments == TupleArguments {
2463 let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
2464 match tuple_type.sty {
2465 ty::TyTuple(arg_types, _) if arg_types.len() != args.len() => {
2466 parameter_count_error(tcx.sess, sp_args, expr_sp, arg_types.len(), args.len(),
2467 "E0057", false, def_span, false);
2468 expected_arg_tys = &[];
2469 self.err_args(args.len())
2471 ty::TyTuple(arg_types, _) => {
2472 expected_arg_tys = match expected_arg_tys.get(0) {
2473 Some(&ty) => match ty.sty {
2474 ty::TyTuple(ref tys, _) => &tys,
2482 span_err!(tcx.sess, sp, E0059,
2483 "cannot use call notation; the first type parameter \
2484 for the function trait is neither a tuple nor unit");
2485 expected_arg_tys = &[];
2486 self.err_args(args.len())
2489 } else if expected_arg_count == supplied_arg_count {
2491 } else if variadic {
2492 if supplied_arg_count >= expected_arg_count {
2495 parameter_count_error(tcx.sess, sp_args, expr_sp, expected_arg_count,
2496 supplied_arg_count, "E0060", true, def_span, false);
2497 expected_arg_tys = &[];
2498 self.err_args(supplied_arg_count)
2501 // is the missing argument of type `()`?
2502 let sugg_unit = if expected_arg_tys.len() == 1 && supplied_arg_count == 0 {
2503 self.resolve_type_vars_if_possible(&expected_arg_tys[0]).is_nil()
2504 } else if fn_inputs.len() == 1 && supplied_arg_count == 0 {
2505 self.resolve_type_vars_if_possible(&fn_inputs[0]).is_nil()
2509 parameter_count_error(tcx.sess, sp_args, expr_sp, expected_arg_count,
2510 supplied_arg_count, "E0061", false, def_span, sugg_unit);
2511 expected_arg_tys = &[];
2512 self.err_args(supplied_arg_count)
2515 debug!("check_argument_types: formal_tys={:?}",
2516 formal_tys.iter().map(|t| self.ty_to_string(*t)).collect::<Vec<String>>());
2518 // Check the arguments.
2519 // We do this in a pretty awful way: first we typecheck any arguments
2520 // that are not closures, then we typecheck the closures. This is so
2521 // that we have more information about the types of arguments when we
2522 // typecheck the functions. This isn't really the right way to do this.
2523 for &check_closures in &[false, true] {
2524 debug!("check_closures={}", check_closures);
2526 // More awful hacks: before we check argument types, try to do
2527 // an "opportunistic" vtable resolution of any trait bounds on
2528 // the call. This helps coercions.
2530 self.select_obligations_where_possible();
2533 // For variadic functions, we don't have a declared type for all of
2534 // the arguments hence we only do our usual type checking with
2535 // the arguments who's types we do know.
2536 let t = if variadic {
2538 } else if tuple_arguments == TupleArguments {
2543 for (i, arg) in args.iter().take(t).enumerate() {
2544 // Warn only for the first loop (the "no closures" one).
2545 // Closure arguments themselves can't be diverging, but
2546 // a previous argument can, e.g. `foo(panic!(), || {})`.
2547 if !check_closures {
2548 self.warn_if_unreachable(arg.id, arg.span, "expression");
2551 let is_closure = match arg.node {
2552 hir::ExprClosure(..) => true,
2556 if is_closure != check_closures {
2560 debug!("checking the argument");
2561 let formal_ty = formal_tys[i];
2563 // The special-cased logic below has three functions:
2564 // 1. Provide as good of an expected type as possible.
2565 let expected = expected_arg_tys.get(i).map(|&ty| {
2566 Expectation::rvalue_hint(self, ty)
2569 let checked_ty = self.check_expr_with_expectation(
2571 expected.unwrap_or(ExpectHasType(formal_ty)));
2573 // 2. Coerce to the most detailed type that could be coerced
2574 // to, which is `expected_ty` if `rvalue_hint` returns an
2575 // `ExpectHasType(expected_ty)`, or the `formal_ty` otherwise.
2576 let coerce_ty = expected.and_then(|e| e.only_has_type(self));
2577 self.demand_coerce(&arg, checked_ty, coerce_ty.unwrap_or(formal_ty));
2579 // 3. Relate the expected type and the formal one,
2580 // if the expected type was used for the coercion.
2581 coerce_ty.map(|ty| self.demand_suptype(arg.span, formal_ty, ty));
2585 // We also need to make sure we at least write the ty of the other
2586 // arguments which we skipped above.
2588 fn variadic_error<'tcx>(s: &Session, span: Span, t: Ty<'tcx>, cast_ty: &str) {
2589 type_error_struct!(s, span, t, E0617,
2590 "can't pass `{}` to variadic function, cast to `{}`",
2594 for arg in args.iter().skip(expected_arg_count) {
2595 let arg_ty = self.check_expr(&arg);
2597 // There are a few types which get autopromoted when passed via varargs
2598 // in C but we just error out instead and require explicit casts.
2599 let arg_ty = self.structurally_resolved_type(arg.span, arg_ty);
2601 ty::TyFloat(ast::FloatTy::F32) => {
2602 variadic_error(tcx.sess, arg.span, arg_ty, "c_double");
2604 ty::TyInt(ast::IntTy::I8) | ty::TyInt(ast::IntTy::I16) | ty::TyBool => {
2605 variadic_error(tcx.sess, arg.span, arg_ty, "c_int");
2607 ty::TyUint(ast::UintTy::U8) | ty::TyUint(ast::UintTy::U16) => {
2608 variadic_error(tcx.sess, arg.span, arg_ty, "c_uint");
2610 ty::TyFnDef(..) => {
2611 let ptr_ty = self.tcx.mk_fn_ptr(arg_ty.fn_sig(self.tcx));
2612 let ptr_ty = self.resolve_type_vars_if_possible(&ptr_ty);
2613 variadic_error(tcx.sess, arg.span, arg_ty, &format!("{}", ptr_ty));
2621 fn err_args(&self, len: usize) -> Vec<Ty<'tcx>> {
2622 (0..len).map(|_| self.tcx.types.err).collect()
2625 // AST fragment checking
2628 expected: Expectation<'tcx>)
2634 ast::LitKind::Str(..) => tcx.mk_static_str(),
2635 ast::LitKind::ByteStr(ref v) => {
2636 tcx.mk_imm_ref(tcx.types.re_static,
2637 tcx.mk_array(tcx.types.u8, v.len() as u64))
2639 ast::LitKind::Byte(_) => tcx.types.u8,
2640 ast::LitKind::Char(_) => tcx.types.char,
2641 ast::LitKind::Int(_, ast::LitIntType::Signed(t)) => tcx.mk_mach_int(t),
2642 ast::LitKind::Int(_, ast::LitIntType::Unsigned(t)) => tcx.mk_mach_uint(t),
2643 ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
2644 let opt_ty = expected.to_option(self).and_then(|ty| {
2646 ty::TyInt(_) | ty::TyUint(_) => Some(ty),
2647 ty::TyChar => Some(tcx.types.u8),
2648 ty::TyRawPtr(..) => Some(tcx.types.usize),
2649 ty::TyFnDef(..) | ty::TyFnPtr(_) => Some(tcx.types.usize),
2653 opt_ty.unwrap_or_else(
2654 || tcx.mk_int_var(self.next_int_var_id()))
2656 ast::LitKind::Float(_, t) => tcx.mk_mach_float(t),
2657 ast::LitKind::FloatUnsuffixed(_) => {
2658 let opt_ty = expected.to_option(self).and_then(|ty| {
2660 ty::TyFloat(_) => Some(ty),
2664 opt_ty.unwrap_or_else(
2665 || tcx.mk_float_var(self.next_float_var_id()))
2667 ast::LitKind::Bool(_) => tcx.types.bool
2671 fn check_expr_eq_type(&self,
2672 expr: &'gcx hir::Expr,
2673 expected: Ty<'tcx>) {
2674 let ty = self.check_expr_with_hint(expr, expected);
2675 self.demand_eqtype(expr.span, expected, ty);
2678 pub fn check_expr_has_type_or_error(&self,
2679 expr: &'gcx hir::Expr,
2680 expected: Ty<'tcx>) -> Ty<'tcx> {
2681 self.check_expr_meets_expectation_or_error(expr, ExpectHasType(expected))
2684 fn check_expr_meets_expectation_or_error(&self,
2685 expr: &'gcx hir::Expr,
2686 expected: Expectation<'tcx>) -> Ty<'tcx> {
2687 let expected_ty = expected.to_option(&self).unwrap_or(self.tcx.types.bool);
2688 let mut ty = self.check_expr_with_expectation(expr, expected);
2690 // While we don't allow *arbitrary* coercions here, we *do* allow
2691 // coercions from ! to `expected`.
2693 assert!(!self.tables.borrow().adjustments().contains_key(expr.hir_id),
2694 "expression with never type wound up being adjusted");
2695 let adj_ty = self.next_diverging_ty_var(
2696 TypeVariableOrigin::AdjustmentType(expr.span));
2697 self.apply_adjustments(expr, vec![Adjustment {
2698 kind: Adjust::NeverToAny,
2704 if let Some(mut err) = self.demand_suptype_diag(expr.span, expected_ty, ty) {
2705 // Add help to type error if this is an `if` condition with an assignment
2706 match (expected, &expr.node) {
2707 (ExpectIfCondition, &hir::ExprAssign(ref lhs, ref rhs)) => {
2708 let msg = "try comparing for equality";
2709 if let (Ok(left), Ok(right)) = (
2710 self.tcx.sess.codemap().span_to_snippet(lhs.span),
2711 self.tcx.sess.codemap().span_to_snippet(rhs.span))
2713 err.span_suggestion(expr.span, msg, format!("{} == {}", left, right));
2725 fn check_expr_coercable_to_type(&self,
2726 expr: &'gcx hir::Expr,
2727 expected: Ty<'tcx>) -> Ty<'tcx> {
2728 self.check_expr_coercable_to_type_with_lvalue_pref(expr, expected, NoPreference)
2731 fn check_expr_coercable_to_type_with_lvalue_pref(&self,
2732 expr: &'gcx hir::Expr,
2734 lvalue_pref: LvaluePreference)
2736 let ty = self.check_expr_with_expectation_and_lvalue_pref(
2738 ExpectHasType(expected),
2740 self.demand_coerce(expr, ty, expected)
2743 fn check_expr_with_hint(&self, expr: &'gcx hir::Expr,
2744 expected: Ty<'tcx>) -> Ty<'tcx> {
2745 self.check_expr_with_expectation(expr, ExpectHasType(expected))
2748 fn check_expr_with_expectation(&self,
2749 expr: &'gcx hir::Expr,
2750 expected: Expectation<'tcx>) -> Ty<'tcx> {
2751 self.check_expr_with_expectation_and_lvalue_pref(expr, expected, NoPreference)
2754 fn check_expr(&self, expr: &'gcx hir::Expr) -> Ty<'tcx> {
2755 self.check_expr_with_expectation(expr, NoExpectation)
2758 fn check_expr_with_lvalue_pref(&self, expr: &'gcx hir::Expr,
2759 lvalue_pref: LvaluePreference) -> Ty<'tcx> {
2760 self.check_expr_with_expectation_and_lvalue_pref(expr, NoExpectation, lvalue_pref)
2763 // determine the `self` type, using fresh variables for all variables
2764 // declared on the impl declaration e.g., `impl<A,B> for Vec<(A,B)>`
2765 // would return ($0, $1) where $0 and $1 are freshly instantiated type
2767 pub fn impl_self_ty(&self,
2768 span: Span, // (potential) receiver for this impl
2770 -> TypeAndSubsts<'tcx> {
2771 let ity = self.tcx.type_of(did);
2772 debug!("impl_self_ty: ity={:?}", ity);
2774 let substs = self.fresh_substs_for_item(span, did);
2775 let substd_ty = self.instantiate_type_scheme(span, &substs, &ity);
2777 TypeAndSubsts { substs: substs, ty: substd_ty }
2780 /// Unifies the output type with the expected type early, for more coercions
2781 /// and forward type information on the input expressions.
2782 fn expected_inputs_for_expected_output(&self,
2784 expected_ret: Expectation<'tcx>,
2785 formal_ret: Ty<'tcx>,
2786 formal_args: &[Ty<'tcx>])
2788 let formal_ret = self.resolve_type_vars_with_obligations(formal_ret);
2789 let expected_args = expected_ret.only_has_type(self).and_then(|ret_ty| {
2790 self.fudge_regions_if_ok(&RegionVariableOrigin::Coercion(call_span), || {
2791 // Attempt to apply a subtyping relationship between the formal
2792 // return type (likely containing type variables if the function
2793 // is polymorphic) and the expected return type.
2794 // No argument expectations are produced if unification fails.
2795 let origin = self.misc(call_span);
2796 let ures = self.at(&origin, self.param_env).sup(ret_ty, formal_ret);
2798 // FIXME(#15760) can't use try! here, FromError doesn't default
2799 // to identity so the resulting type is not constrained.
2802 // Process any obligations locally as much as
2803 // we can. We don't care if some things turn
2804 // out unconstrained or ambiguous, as we're
2805 // just trying to get hints here.
2806 let result = self.save_and_restore_in_snapshot_flag(|_| {
2807 let mut fulfill = FulfillmentContext::new();
2808 let ok = ok; // FIXME(#30046)
2809 for obligation in ok.obligations {
2810 fulfill.register_predicate_obligation(self, obligation);
2812 fulfill.select_where_possible(self)
2817 Err(_) => return Err(()),
2820 Err(_) => return Err(()),
2823 // Record all the argument types, with the substitutions
2824 // produced from the above subtyping unification.
2825 Ok(formal_args.iter().map(|ty| {
2826 self.resolve_type_vars_if_possible(ty)
2829 }).unwrap_or(vec![]);
2830 debug!("expected_inputs_for_expected_output(formal={:?} -> {:?}, expected={:?} -> {:?})",
2831 formal_args, formal_ret,
2832 expected_args, expected_ret);
2836 // Checks a method call.
2837 fn check_method_call(&self,
2838 expr: &'gcx hir::Expr,
2839 segment: &hir::PathSegment,
2841 args: &'gcx [hir::Expr],
2842 expected: Expectation<'tcx>,
2843 lvalue_pref: LvaluePreference) -> Ty<'tcx> {
2844 let rcvr = &args[0];
2845 let rcvr_t = self.check_expr_with_lvalue_pref(&rcvr, lvalue_pref);
2846 // no need to check for bot/err -- callee does that
2847 let rcvr_t = self.structurally_resolved_type(expr.span, rcvr_t);
2849 let method = match self.lookup_method(rcvr_t,
2855 self.write_method_call(expr.hir_id, method);
2859 if segment.name != keywords::Invalid.name() {
2860 self.report_method_error(span,
2871 // Call the generic checker.
2872 self.check_method_argument_types(span,
2880 fn check_return_expr(&self, return_expr: &'gcx hir::Expr) {
2884 .unwrap_or_else(|| span_bug!(return_expr.span,
2885 "check_return_expr called outside fn body"));
2887 let ret_ty = ret_coercion.borrow().expected_ty();
2888 let return_expr_ty = self.check_expr_with_hint(return_expr, ret_ty.clone());
2889 ret_coercion.borrow_mut()
2891 &self.cause(return_expr.span,
2892 ObligationCauseCode::ReturnType(return_expr.id)),
2895 self.diverges.get());
2899 // A generic function for checking the then and else in an if
2901 fn check_then_else(&self,
2902 cond_expr: &'gcx hir::Expr,
2903 then_expr: &'gcx hir::Expr,
2904 opt_else_expr: Option<&'gcx hir::Expr>,
2906 expected: Expectation<'tcx>) -> Ty<'tcx> {
2907 let cond_ty = self.check_expr_meets_expectation_or_error(cond_expr, ExpectIfCondition);
2908 let cond_diverges = self.diverges.get();
2909 self.diverges.set(Diverges::Maybe);
2911 let expected = expected.adjust_for_branches(self);
2912 let then_ty = self.check_expr_with_expectation(then_expr, expected);
2913 let then_diverges = self.diverges.get();
2914 self.diverges.set(Diverges::Maybe);
2916 // We've already taken the expected type's preferences
2917 // into account when typing the `then` branch. To figure
2918 // out the initial shot at a LUB, we thus only consider
2919 // `expected` if it represents a *hard* constraint
2920 // (`only_has_type`); otherwise, we just go with a
2921 // fresh type variable.
2922 let coerce_to_ty = expected.coercion_target_type(self, sp);
2923 let mut coerce: DynamicCoerceMany = CoerceMany::new(coerce_to_ty);
2925 let if_cause = self.cause(sp, ObligationCauseCode::IfExpression);
2926 coerce.coerce(self, &if_cause, then_expr, then_ty, then_diverges);
2928 if let Some(else_expr) = opt_else_expr {
2929 let else_ty = self.check_expr_with_expectation(else_expr, expected);
2930 let else_diverges = self.diverges.get();
2932 coerce.coerce(self, &if_cause, else_expr, else_ty, else_diverges);
2934 // We won't diverge unless both branches do (or the condition does).
2935 self.diverges.set(cond_diverges | then_diverges & else_diverges);
2937 let else_cause = self.cause(sp, ObligationCauseCode::IfExpressionWithNoElse);
2938 coerce.coerce_forced_unit(self, &else_cause, &mut |_| (), true);
2940 // If the condition is false we can't diverge.
2941 self.diverges.set(cond_diverges);
2944 let result_ty = coerce.complete(self);
2945 if cond_ty.references_error() {
2952 // Check field access expressions
2953 fn check_field(&self,
2954 expr: &'gcx hir::Expr,
2955 lvalue_pref: LvaluePreference,
2956 base: &'gcx hir::Expr,
2957 field: &Spanned<ast::Name>) -> Ty<'tcx> {
2958 let expr_t = self.check_expr_with_lvalue_pref(base, lvalue_pref);
2959 let expr_t = self.structurally_resolved_type(expr.span,
2961 let mut private_candidate = None;
2962 let mut autoderef = self.autoderef(expr.span, expr_t);
2963 while let Some((base_t, _)) = autoderef.next() {
2965 ty::TyAdt(base_def, substs) if !base_def.is_enum() => {
2966 debug!("struct named {:?}", base_t);
2967 let (ident, def_scope) =
2968 self.tcx.adjust(field.node, base_def.did, self.body_id);
2969 let fields = &base_def.struct_variant().fields;
2970 if let Some(field) = fields.iter().find(|f| f.name.to_ident() == ident) {
2971 let field_ty = self.field_ty(expr.span, field, substs);
2972 if field.vis.is_accessible_from(def_scope, self.tcx) {
2973 let adjustments = autoderef.adjust_steps(lvalue_pref);
2974 self.apply_adjustments(base, adjustments);
2975 autoderef.finalize();
2977 self.tcx.check_stability(field.did, expr.id, expr.span);
2981 private_candidate = Some((base_def.did, field_ty));
2987 autoderef.unambiguous_final_ty();
2989 if let Some((did, field_ty)) = private_candidate {
2990 let struct_path = self.tcx().item_path_str(did);
2991 let mut err = struct_span_err!(self.tcx().sess, expr.span, E0616,
2992 "field `{}` of struct `{}` is private",
2993 field.node, struct_path);
2994 // Also check if an accessible method exists, which is often what is meant.
2995 if self.method_exists(field.span, field.node, expr_t, expr.id, false) {
2996 err.note(&format!("a method `{}` also exists, perhaps you wish to call it",
3001 } else if field.node == keywords::Invalid.name() {
3002 self.tcx().types.err
3003 } else if self.method_exists(field.span, field.node, expr_t, expr.id, true) {
3004 type_error_struct!(self.tcx().sess, field.span, expr_t, E0615,
3005 "attempted to take value of method `{}` on type `{}`",
3007 .help("maybe a `()` to call it is missing?")
3009 self.tcx().types.err
3011 if !expr_t.is_primitive_ty() {
3012 let mut err = self.no_such_field_err(field.span, &field.node, expr_t);
3015 ty::TyAdt(def, _) if !def.is_enum() => {
3016 if let Some(suggested_field_name) =
3017 Self::suggest_field_name(def.struct_variant(), field, vec![]) {
3018 err.span_label(field.span,
3019 format!("did you mean `{}`?", suggested_field_name));
3021 err.span_label(field.span, "unknown field");
3022 let struct_variant_def = def.struct_variant();
3023 let field_names = self.available_field_names(struct_variant_def);
3024 if !field_names.is_empty() {
3025 err.note(&format!("available fields are: {}",
3026 self.name_series_display(field_names)));
3030 ty::TyRawPtr(..) => {
3031 err.note(&format!("`{0}` is a native pointer; perhaps you need to deref \
3033 self.tcx.hir.node_to_pretty_string(base.id),
3040 type_error_struct!(self.tcx().sess, field.span, expr_t, E0610,
3041 "`{}` is a primitive type and therefore doesn't have fields",
3044 self.tcx().types.err
3048 // Return an hint about the closest match in field names
3049 fn suggest_field_name(variant: &'tcx ty::VariantDef,
3050 field: &Spanned<ast::Name>,
3051 skip: Vec<InternedString>)
3053 let name = field.node.as_str();
3054 let names = variant.fields.iter().filter_map(|field| {
3055 // ignore already set fields and private fields from non-local crates
3056 if skip.iter().any(|x| *x == field.name.as_str()) ||
3057 (variant.did.krate != LOCAL_CRATE && field.vis != Visibility::Public) {
3064 find_best_match_for_name(names, &name, None)
3067 fn available_field_names(&self, variant: &'tcx ty::VariantDef) -> Vec<ast::Name> {
3068 let mut available = Vec::new();
3069 for field in variant.fields.iter() {
3070 let (_, def_scope) = self.tcx.adjust(field.name, variant.did, self.body_id);
3071 if field.vis.is_accessible_from(def_scope, self.tcx) {
3072 available.push(field.name);
3078 fn name_series_display(&self, names: Vec<ast::Name>) -> String {
3079 // dynamic limit, to never omit just one field
3080 let limit = if names.len() == 6 { 6 } else { 5 };
3081 let mut display = names.iter().take(limit)
3082 .map(|n| format!("`{}`", n)).collect::<Vec<_>>().join(", ");
3083 if names.len() > limit {
3084 display = format!("{} ... and {} others", display, names.len() - limit);
3089 // Check tuple index expressions
3090 fn check_tup_field(&self,
3091 expr: &'gcx hir::Expr,
3092 lvalue_pref: LvaluePreference,
3093 base: &'gcx hir::Expr,
3094 idx: codemap::Spanned<usize>) -> Ty<'tcx> {
3095 let expr_t = self.check_expr_with_lvalue_pref(base, lvalue_pref);
3096 let expr_t = self.structurally_resolved_type(expr.span,
3098 let mut private_candidate = None;
3099 let mut tuple_like = false;
3100 let mut autoderef = self.autoderef(expr.span, expr_t);
3101 while let Some((base_t, _)) = autoderef.next() {
3102 let field = match base_t.sty {
3103 ty::TyAdt(base_def, substs) if base_def.is_struct() => {
3104 tuple_like = base_def.struct_variant().ctor_kind == CtorKind::Fn;
3105 if !tuple_like { continue }
3107 debug!("tuple struct named {:?}", base_t);
3108 let ident = ast::Ident {
3109 name: Symbol::intern(&idx.node.to_string()),
3110 ctxt: idx.span.ctxt().modern(),
3112 let (ident, def_scope) =
3113 self.tcx.adjust_ident(ident, base_def.did, self.body_id);
3114 let fields = &base_def.struct_variant().fields;
3115 if let Some(field) = fields.iter().find(|f| f.name.to_ident() == ident) {
3116 let field_ty = self.field_ty(expr.span, field, substs);
3117 if field.vis.is_accessible_from(def_scope, self.tcx) {
3118 self.tcx.check_stability(field.did, expr.id, expr.span);
3121 private_candidate = Some((base_def.did, field_ty));
3128 ty::TyTuple(ref v, _) => {
3130 v.get(idx.node).cloned()
3135 if let Some(field_ty) = field {
3136 let adjustments = autoderef.adjust_steps(lvalue_pref);
3137 self.apply_adjustments(base, adjustments);
3138 autoderef.finalize();
3142 autoderef.unambiguous_final_ty();
3144 if let Some((did, field_ty)) = private_candidate {
3145 let struct_path = self.tcx().item_path_str(did);
3146 struct_span_err!(self.tcx().sess, expr.span, E0611,
3147 "field `{}` of tuple-struct `{}` is private",
3148 idx.node, struct_path).emit();
3153 type_error_struct!(self.tcx().sess, expr.span, expr_t, E0612,
3154 "attempted out-of-bounds tuple index `{}` on type `{}`",
3155 idx.node, expr_t).emit();
3157 self.no_such_field_err(expr.span, idx.node, expr_t).emit();
3160 self.tcx().types.err
3163 fn no_such_field_err<T: Display>(&self, span: Span, field: T, expr_t: &ty::TyS)
3164 -> DiagnosticBuilder {
3165 type_error_struct!(self.tcx().sess, span, expr_t, E0609,
3166 "no field `{}` on type `{}`",
3170 fn report_unknown_field(&self,
3172 variant: &'tcx ty::VariantDef,
3174 skip_fields: &[hir::Field],
3176 let mut err = self.type_error_struct_with_diag(
3178 |actual| match ty.sty {
3179 ty::TyAdt(adt, ..) if adt.is_enum() => {
3180 struct_span_err!(self.tcx.sess, field.name.span, E0559,
3181 "{} `{}::{}` has no field named `{}`",
3182 kind_name, actual, variant.name, field.name.node)
3185 struct_span_err!(self.tcx.sess, field.name.span, E0560,
3186 "{} `{}` has no field named `{}`",
3187 kind_name, actual, field.name.node)
3191 // prevent all specified fields from being suggested
3192 let skip_fields = skip_fields.iter().map(|ref x| x.name.node.as_str());
3193 if let Some(field_name) = Self::suggest_field_name(variant,
3195 skip_fields.collect()) {
3196 err.span_label(field.name.span,
3197 format!("field does not exist - did you mean `{}`?", field_name));
3200 ty::TyAdt(adt, ..) => {
3202 err.span_label(field.name.span,
3203 format!("`{}::{}` does not have this field",
3206 err.span_label(field.name.span,
3207 format!("`{}` does not have this field", ty));
3209 let available_field_names = self.available_field_names(variant);
3210 if !available_field_names.is_empty() {
3211 err.note(&format!("available fields are: {}",
3212 self.name_series_display(available_field_names)));
3215 _ => bug!("non-ADT passed to report_unknown_field")
3221 fn check_expr_struct_fields(&self,
3223 expected: Expectation<'tcx>,
3224 expr_id: ast::NodeId,
3226 variant: &'tcx ty::VariantDef,
3227 ast_fields: &'gcx [hir::Field],
3228 check_completeness: bool) {
3232 self.expected_inputs_for_expected_output(span, expected, adt_ty, &[adt_ty])
3233 .get(0).cloned().unwrap_or(adt_ty);
3234 // re-link the regions that EIfEO can erase.
3235 self.demand_eqtype(span, adt_ty_hint, adt_ty);
3237 let (substs, adt_kind, kind_name) = match &adt_ty.sty{
3238 &ty::TyAdt(adt, substs) => {
3239 (substs, adt.adt_kind(), adt.variant_descr())
3241 _ => span_bug!(span, "non-ADT passed to check_expr_struct_fields")
3244 let mut remaining_fields = FxHashMap();
3245 for field in &variant.fields {
3246 remaining_fields.insert(field.name.to_ident(), field);
3249 let mut seen_fields = FxHashMap();
3251 let mut error_happened = false;
3253 // Typecheck each field.
3254 for field in ast_fields {
3255 let ident = tcx.adjust(field.name.node, variant.did, self.body_id).0;
3256 let field_type = if let Some(v_field) = remaining_fields.remove(&ident) {
3257 seen_fields.insert(field.name.node, field.span);
3259 // we don't look at stability attributes on
3260 // struct-like enums (yet...), but it's definitely not
3261 // a bug to have construct one.
3262 if adt_kind != ty::AdtKind::Enum {
3263 tcx.check_stability(v_field.did, expr_id, field.span);
3266 self.field_ty(field.span, v_field, substs)
3268 error_happened = true;
3269 if let Some(_) = variant.find_field_named(field.name.node) {
3270 let mut err = struct_span_err!(self.tcx.sess,
3273 "field `{}` specified more than once",
3276 err.span_label(field.name.span, "used more than once");
3278 if let Some(prev_span) = seen_fields.get(&field.name.node) {
3279 err.span_label(*prev_span, format!("first use of `{}`", field.name.node));
3284 self.report_unknown_field(adt_ty, variant, field, ast_fields, kind_name);
3290 // Make sure to give a type to the field even if there's
3291 // an error, so we can continue typechecking
3292 self.check_expr_coercable_to_type(&field.expr, field_type);
3295 // Make sure the programmer specified correct number of fields.
3296 if kind_name == "union" {
3297 if ast_fields.len() != 1 {
3298 tcx.sess.span_err(span, "union expressions should have exactly one field");
3300 } else if check_completeness && !error_happened && !remaining_fields.is_empty() {
3301 let len = remaining_fields.len();
3303 let mut displayable_field_names = remaining_fields
3305 .map(|ident| ident.name.as_str())
3306 .collect::<Vec<_>>();
3308 displayable_field_names.sort();
3310 let truncated_fields_error = if len <= 3 {
3313 format!(" and {} other field{}", (len - 3), if len - 3 == 1 {""} else {"s"})
3316 let remaining_fields_names = displayable_field_names.iter().take(3)
3317 .map(|n| format!("`{}`", n))
3318 .collect::<Vec<_>>()
3321 struct_span_err!(tcx.sess, span, E0063,
3322 "missing field{} {}{} in initializer of `{}`",
3323 if remaining_fields.len() == 1 { "" } else { "s" },
3324 remaining_fields_names,
3325 truncated_fields_error,
3327 .span_label(span, format!("missing {}{}",
3328 remaining_fields_names,
3329 truncated_fields_error))
3334 fn check_struct_fields_on_error(&self,
3335 fields: &'gcx [hir::Field],
3336 base_expr: &'gcx Option<P<hir::Expr>>) {
3337 for field in fields {
3338 self.check_expr(&field.expr);
3342 self.check_expr(&base);
3348 pub fn check_struct_path(&self,
3350 node_id: ast::NodeId)
3351 -> Option<(&'tcx ty::VariantDef, Ty<'tcx>)> {
3352 let path_span = match *qpath {
3353 hir::QPath::Resolved(_, ref path) => path.span,
3354 hir::QPath::TypeRelative(ref qself, _) => qself.span
3356 let (def, ty) = self.finish_resolving_struct_path(qpath, path_span, node_id);
3357 let variant = match def {
3359 self.set_tainted_by_errors();
3362 Def::Variant(..) => {
3364 ty::TyAdt(adt, substs) => {
3365 Some((adt.variant_of_def(def), adt.did, substs))
3367 _ => bug!("unexpected type: {:?}", ty.sty)
3370 Def::Struct(..) | Def::Union(..) | Def::TyAlias(..) |
3371 Def::AssociatedTy(..) | Def::SelfTy(..) => {
3373 ty::TyAdt(adt, substs) if !adt.is_enum() => {
3374 Some((adt.struct_variant(), adt.did, substs))
3379 _ => bug!("unexpected definition: {:?}", def)
3382 if let Some((variant, did, substs)) = variant {
3383 // Check bounds on type arguments used in the path.
3384 let bounds = self.instantiate_bounds(path_span, did, substs);
3385 let cause = traits::ObligationCause::new(path_span, self.body_id,
3386 traits::ItemObligation(did));
3387 self.add_obligations_for_parameters(cause, &bounds);
3391 struct_span_err!(self.tcx.sess, path_span, E0071,
3392 "expected struct, variant or union type, found {}",
3393 ty.sort_string(self.tcx))
3394 .span_label(path_span, "not a struct")
3400 fn check_expr_struct(&self,
3402 expected: Expectation<'tcx>,
3404 fields: &'gcx [hir::Field],
3405 base_expr: &'gcx Option<P<hir::Expr>>) -> Ty<'tcx>
3407 // Find the relevant variant
3408 let (variant, struct_ty) =
3409 if let Some(variant_ty) = self.check_struct_path(qpath, expr.id) {
3412 self.check_struct_fields_on_error(fields, base_expr);
3413 return self.tcx.types.err;
3416 let path_span = match *qpath {
3417 hir::QPath::Resolved(_, ref path) => path.span,
3418 hir::QPath::TypeRelative(ref qself, _) => qself.span
3421 // Prohibit struct expressions when non exhaustive flag is set.
3422 if let ty::TyAdt(adt, _) = struct_ty.sty {
3423 if !adt.did.is_local() && adt.is_non_exhaustive() {
3424 span_err!(self.tcx.sess, expr.span, E0639,
3425 "cannot create non-exhaustive {} using struct expression",
3426 adt.variant_descr());
3430 self.check_expr_struct_fields(struct_ty, expected, expr.id, path_span, variant, fields,
3431 base_expr.is_none());
3432 if let &Some(ref base_expr) = base_expr {
3433 self.check_expr_has_type_or_error(base_expr, struct_ty);
3434 match struct_ty.sty {
3435 ty::TyAdt(adt, substs) if adt.is_struct() => {
3436 let fru_field_types = adt.struct_variant().fields.iter().map(|f| {
3437 self.normalize_associated_types_in(expr.span, &f.ty(self.tcx, substs))
3442 .fru_field_types_mut()
3443 .insert(expr.hir_id, fru_field_types);
3446 span_err!(self.tcx.sess, base_expr.span, E0436,
3447 "functional record update syntax requires a struct");
3451 self.require_type_is_sized(struct_ty, expr.span, traits::StructInitializerSized);
3457 /// If an expression has any sub-expressions that result in a type error,
3458 /// inspecting that expression's type with `ty.references_error()` will return
3459 /// true. Likewise, if an expression is known to diverge, inspecting its
3460 /// type with `ty::type_is_bot` will return true (n.b.: since Rust is
3461 /// strict, _|_ can appear in the type of an expression that does not,
3462 /// itself, diverge: for example, fn() -> _|_.)
3463 /// Note that inspecting a type's structure *directly* may expose the fact
3464 /// that there are actually multiple representations for `TyError`, so avoid
3465 /// that when err needs to be handled differently.
3466 fn check_expr_with_expectation_and_lvalue_pref(&self,
3467 expr: &'gcx hir::Expr,
3468 expected: Expectation<'tcx>,
3469 lvalue_pref: LvaluePreference) -> Ty<'tcx> {
3470 debug!(">> typechecking: expr={:?} expected={:?}",
3473 // Warn for expressions after diverging siblings.
3474 self.warn_if_unreachable(expr.id, expr.span, "expression");
3476 // Hide the outer diverging and has_errors flags.
3477 let old_diverges = self.diverges.get();
3478 let old_has_errors = self.has_errors.get();
3479 self.diverges.set(Diverges::Maybe);
3480 self.has_errors.set(false);
3482 let ty = self.check_expr_kind(expr, expected, lvalue_pref);
3484 // Warn for non-block expressions with diverging children.
3487 hir::ExprLoop(..) | hir::ExprWhile(..) |
3488 hir::ExprIf(..) | hir::ExprMatch(..) => {}
3490 _ => self.warn_if_unreachable(expr.id, expr.span, "expression")
3493 // Any expression that produces a value of type `!` must have diverged
3495 self.diverges.set(self.diverges.get() | Diverges::Always);
3498 // Record the type, which applies it effects.
3499 // We need to do this after the warning above, so that
3500 // we don't warn for the diverging expression itself.
3501 self.write_ty(expr.hir_id, ty);
3503 // Combine the diverging and has_error flags.
3504 self.diverges.set(self.diverges.get() | old_diverges);
3505 self.has_errors.set(self.has_errors.get() | old_has_errors);
3507 debug!("type of {} is...", self.tcx.hir.node_to_string(expr.id));
3508 debug!("... {:?}, expected is {:?}", ty, expected);
3513 fn check_expr_kind(&self,
3514 expr: &'gcx hir::Expr,
3515 expected: Expectation<'tcx>,
3516 lvalue_pref: LvaluePreference) -> Ty<'tcx> {
3520 hir::ExprBox(ref subexpr) => {
3521 let expected_inner = expected.to_option(self).map_or(NoExpectation, |ty| {
3523 ty::TyAdt(def, _) if def.is_box()
3524 => Expectation::rvalue_hint(self, ty.boxed_ty()),
3528 let referent_ty = self.check_expr_with_expectation(subexpr, expected_inner);
3529 tcx.mk_box(referent_ty)
3532 hir::ExprLit(ref lit) => {
3533 self.check_lit(&lit, expected)
3535 hir::ExprBinary(op, ref lhs, ref rhs) => {
3536 self.check_binop(expr, op, lhs, rhs)
3538 hir::ExprAssignOp(op, ref lhs, ref rhs) => {
3539 self.check_binop_assign(expr, op, lhs, rhs)
3541 hir::ExprUnary(unop, ref oprnd) => {
3542 let expected_inner = match unop {
3543 hir::UnNot | hir::UnNeg => {
3550 let lvalue_pref = match unop {
3551 hir::UnDeref => lvalue_pref,
3554 let mut oprnd_t = self.check_expr_with_expectation_and_lvalue_pref(&oprnd,
3558 if !oprnd_t.references_error() {
3559 oprnd_t = self.structurally_resolved_type(expr.span, oprnd_t);
3562 if let Some(mt) = oprnd_t.builtin_deref(true, NoPreference) {
3564 } else if let Some(ok) = self.try_overloaded_deref(
3565 expr.span, oprnd_t, lvalue_pref) {
3566 let method = self.register_infer_ok_obligations(ok);
3567 if let ty::TyRef(region, mt) = method.sig.inputs()[0].sty {
3568 self.apply_adjustments(oprnd, vec![Adjustment {
3569 kind: Adjust::Borrow(AutoBorrow::Ref(region, mt.mutbl)),
3570 target: method.sig.inputs()[0]
3573 oprnd_t = self.make_overloaded_lvalue_return_type(method).ty;
3574 self.write_method_call(expr.hir_id, method);
3576 type_error_struct!(tcx.sess, expr.span, oprnd_t, E0614,
3577 "type `{}` cannot be dereferenced",
3579 oprnd_t = tcx.types.err;
3583 let result = self.check_user_unop(expr, oprnd_t, unop);
3584 // If it's builtin, we can reuse the type, this helps inference.
3585 if !(oprnd_t.is_integral() || oprnd_t.sty == ty::TyBool) {
3590 let result = self.check_user_unop(expr, oprnd_t, unop);
3591 // If it's builtin, we can reuse the type, this helps inference.
3592 if !(oprnd_t.is_integral() || oprnd_t.is_fp()) {
3600 hir::ExprAddrOf(mutbl, ref oprnd) => {
3601 let hint = expected.only_has_type(self).map_or(NoExpectation, |ty| {
3603 ty::TyRef(_, ref mt) | ty::TyRawPtr(ref mt) => {
3604 if self.tcx.expr_is_lval(&oprnd) {
3605 // Lvalues may legitimately have unsized types.
3606 // For example, dereferences of a fat pointer and
3607 // the last field of a struct can be unsized.
3608 ExpectHasType(mt.ty)
3610 Expectation::rvalue_hint(self, mt.ty)
3616 let lvalue_pref = LvaluePreference::from_mutbl(mutbl);
3617 let ty = self.check_expr_with_expectation_and_lvalue_pref(&oprnd, hint, lvalue_pref);
3619 let tm = ty::TypeAndMut { ty: ty, mutbl: mutbl };
3620 if tm.ty.references_error() {
3623 // Note: at this point, we cannot say what the best lifetime
3624 // is to use for resulting pointer. We want to use the
3625 // shortest lifetime possible so as to avoid spurious borrowck
3626 // errors. Moreover, the longest lifetime will depend on the
3627 // precise details of the value whose address is being taken
3628 // (and how long it is valid), which we don't know yet until type
3629 // inference is complete.
3631 // Therefore, here we simply generate a region variable. The
3632 // region inferencer will then select the ultimate value.
3633 // Finally, borrowck is charged with guaranteeing that the
3634 // value whose address was taken can actually be made to live
3635 // as long as it needs to live.
3636 let region = self.next_region_var(infer::AddrOfRegion(expr.span));
3637 tcx.mk_ref(region, tm)
3640 hir::ExprPath(ref qpath) => {
3641 let (def, opt_ty, segments) = self.resolve_ty_and_def_ufcs(qpath,
3642 expr.id, expr.span);
3643 let ty = if def != Def::Err {
3644 self.instantiate_value_path(segments, opt_ty, def, expr.span, id)
3646 self.set_tainted_by_errors();
3650 // We always require that the type provided as the value for
3651 // a type parameter outlives the moment of instantiation.
3652 let substs = self.tables.borrow().node_substs(expr.hir_id);
3653 self.add_wf_bounds(substs, expr);
3657 hir::ExprInlineAsm(_, ref outputs, ref inputs) => {
3658 for output in outputs {
3659 self.check_expr(output);
3661 for input in inputs {
3662 self.check_expr(input);
3666 hir::ExprBreak(destination, ref expr_opt) => {
3667 if let Some(target_id) = destination.target_id.opt_id() {
3668 let (e_ty, e_diverges, cause);
3669 if let Some(ref e) = *expr_opt {
3670 // If this is a break with a value, we need to type-check
3671 // the expression. Get an expected type from the loop context.
3672 let opt_coerce_to = {
3673 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
3674 enclosing_breakables.find_breakable(target_id)
3677 .map(|coerce| coerce.expected_ty())
3680 // If the loop context is not a `loop { }`, then break with
3681 // a value is illegal, and `opt_coerce_to` will be `None`.
3682 // Just set expectation to error in that case.
3683 let coerce_to = opt_coerce_to.unwrap_or(tcx.types.err);
3685 // Recurse without `enclosing_breakables` borrowed.
3686 e_ty = self.check_expr_with_hint(e, coerce_to);
3687 e_diverges = self.diverges.get();
3688 cause = self.misc(e.span);
3690 // Otherwise, this is a break *without* a value. That's
3691 // always legal, and is equivalent to `break ()`.
3692 e_ty = tcx.mk_nil();
3693 e_diverges = Diverges::Maybe;
3694 cause = self.misc(expr.span);
3697 // Now that we have type-checked `expr_opt`, borrow
3698 // the `enclosing_loops` field and let's coerce the
3699 // type of `expr_opt` into what is expected.
3700 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
3701 let ctxt = enclosing_breakables.find_breakable(target_id);
3702 if let Some(ref mut coerce) = ctxt.coerce {
3703 if let Some(ref e) = *expr_opt {
3704 coerce.coerce(self, &cause, e, e_ty, e_diverges);
3706 assert!(e_ty.is_nil());
3707 coerce.coerce_forced_unit(self, &cause, &mut |_| (), true);
3710 // If `ctxt.coerce` is `None`, we can just ignore
3711 // the type of the expresison. This is because
3712 // either this was a break *without* a value, in
3713 // which case it is always a legal type (`()`), or
3714 // else an error would have been flagged by the
3715 // `loops` pass for using break with an expression
3716 // where you are not supposed to.
3717 assert!(expr_opt.is_none() || self.tcx.sess.err_count() > 0);
3720 ctxt.may_break = true;
3722 // Otherwise, we failed to find the enclosing loop;
3723 // this can only happen if the `break` was not
3724 // inside a loop at all, which is caught by the
3725 // loop-checking pass.
3726 assert!(self.tcx.sess.err_count() > 0);
3728 // We still need to assign a type to the inner expression to
3729 // prevent the ICE in #43162.
3730 if let Some(ref e) = *expr_opt {
3731 self.check_expr_with_hint(e, tcx.types.err);
3733 // ... except when we try to 'break rust;'.
3734 // ICE this expression in particular (see #43162).
3735 if let hir::ExprPath(hir::QPath::Resolved(_, ref path)) = e.node {
3736 if path.segments.len() == 1 && path.segments[0].name == "rust" {
3737 fatally_break_rust(self.tcx.sess);
3743 // the type of a `break` is always `!`, since it diverges
3746 hir::ExprAgain(_) => { tcx.types.never }
3747 hir::ExprRet(ref expr_opt) => {
3748 if self.ret_coercion.is_none() {
3749 struct_span_err!(self.tcx.sess, expr.span, E0572,
3750 "return statement outside of function body").emit();
3751 } else if let Some(ref e) = *expr_opt {
3752 self.check_return_expr(e);
3754 let mut coercion = self.ret_coercion.as_ref().unwrap().borrow_mut();
3755 let cause = self.cause(expr.span, ObligationCauseCode::ReturnNoExpression);
3756 coercion.coerce_forced_unit(self, &cause, &mut |_| (), true);
3760 hir::ExprAssign(ref lhs, ref rhs) => {
3761 let lhs_ty = self.check_expr_with_lvalue_pref(&lhs, PreferMutLvalue);
3763 let rhs_ty = self.check_expr_coercable_to_type(&rhs, lhs_ty);
3766 ExpectIfCondition => {
3767 self.tcx.sess.delay_span_bug(lhs.span, "invalid lhs expression in if;\
3768 expected error elsehwere");
3771 // Only check this if not in an `if` condition, as the
3772 // mistyped comparison help is more appropriate.
3773 if !self.tcx.expr_is_lval(&lhs) {
3774 struct_span_err!(self.tcx.sess, expr.span, E0070,
3775 "invalid left-hand side expression")
3776 .span_label(expr.span, "left-hand of expression not valid")
3782 self.require_type_is_sized(lhs_ty, lhs.span, traits::AssignmentLhsSized);
3784 if lhs_ty.references_error() || rhs_ty.references_error() {
3790 hir::ExprIf(ref cond, ref then_expr, ref opt_else_expr) => {
3791 self.check_then_else(&cond, then_expr, opt_else_expr.as_ref().map(|e| &**e),
3792 expr.span, expected)
3794 hir::ExprWhile(ref cond, ref body, _) => {
3795 let ctxt = BreakableCtxt {
3796 // cannot use break with a value from a while loop
3801 self.with_breakable_ctxt(expr.id, ctxt, || {
3802 self.check_expr_has_type_or_error(&cond, tcx.types.bool);
3803 let cond_diverging = self.diverges.get();
3804 self.check_block_no_value(&body);
3806 // We may never reach the body so it diverging means nothing.
3807 self.diverges.set(cond_diverging);
3812 hir::ExprLoop(ref body, _, source) => {
3813 let coerce = match source {
3814 // you can only use break with a value from a normal `loop { }`
3815 hir::LoopSource::Loop => {
3816 let coerce_to = expected.coercion_target_type(self, body.span);
3817 Some(CoerceMany::new(coerce_to))
3820 hir::LoopSource::WhileLet |
3821 hir::LoopSource::ForLoop => {
3826 let ctxt = BreakableCtxt {
3828 may_break: false, // will get updated if/when we find a `break`
3831 let (ctxt, ()) = self.with_breakable_ctxt(expr.id, ctxt, || {
3832 self.check_block_no_value(&body);
3836 // No way to know whether it's diverging because
3837 // of a `break` or an outer `break` or `return.
3838 self.diverges.set(Diverges::Maybe);
3841 // If we permit break with a value, then result type is
3842 // the LUB of the breaks (possibly ! if none); else, it
3843 // is nil. This makes sense because infinite loops
3844 // (which would have type !) are only possible iff we
3845 // permit break with a value [1].
3846 assert!(ctxt.coerce.is_some() || ctxt.may_break); // [1]
3847 ctxt.coerce.map(|c| c.complete(self)).unwrap_or(self.tcx.mk_nil())
3849 hir::ExprMatch(ref discrim, ref arms, match_src) => {
3850 self.check_match(expr, &discrim, arms, expected, match_src)
3852 hir::ExprClosure(capture, ref decl, body_id, _, _) => {
3853 self.check_expr_closure(expr, capture, &decl, body_id, expected)
3855 hir::ExprBlock(ref body) => {
3856 self.check_block_with_expected(&body, expected)
3858 hir::ExprCall(ref callee, ref args) => {
3859 self.check_call(expr, &callee, args, expected)
3861 hir::ExprMethodCall(ref segment, span, ref args) => {
3862 self.check_method_call(expr, segment, span, args, expected, lvalue_pref)
3864 hir::ExprCast(ref e, ref t) => {
3865 // Find the type of `e`. Supply hints based on the type we are casting to,
3867 let t_cast = self.to_ty(t);
3868 let t_cast = self.resolve_type_vars_if_possible(&t_cast);
3869 let t_expr = self.check_expr_with_expectation(e, ExpectCastableToType(t_cast));
3870 let t_cast = self.resolve_type_vars_if_possible(&t_cast);
3871 let diverges = self.diverges.get();
3873 // Eagerly check for some obvious errors.
3874 if t_expr.references_error() || t_cast.references_error() {
3877 // Defer other checks until we're done type checking.
3878 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
3879 match cast::CastCheck::new(self, e, t_expr, diverges, t_cast, t.span, expr.span) {
3881 deferred_cast_checks.push(cast_check);
3884 Err(ErrorReported) => {
3890 hir::ExprType(ref e, ref t) => {
3891 let typ = self.to_ty(&t);
3892 self.check_expr_eq_type(&e, typ);
3895 hir::ExprArray(ref args) => {
3896 let uty = expected.to_option(self).and_then(|uty| {
3898 ty::TyArray(ty, _) | ty::TySlice(ty) => Some(ty),
3903 let element_ty = if !args.is_empty() {
3904 let coerce_to = uty.unwrap_or_else(
3905 || self.next_ty_var(TypeVariableOrigin::TypeInference(expr.span)));
3906 let mut coerce = CoerceMany::with_coercion_sites(coerce_to, args);
3907 assert_eq!(self.diverges.get(), Diverges::Maybe);
3909 let e_ty = self.check_expr_with_hint(e, coerce_to);
3910 let cause = self.misc(e.span);
3911 coerce.coerce(self, &cause, e, e_ty, self.diverges.get());
3913 coerce.complete(self)
3915 self.next_ty_var(TypeVariableOrigin::TypeInference(expr.span))
3917 tcx.mk_array(element_ty, args.len() as u64)
3919 hir::ExprRepeat(ref element, count) => {
3920 let count_def_id = tcx.hir.body_owner_def_id(count);
3921 let param_env = ty::ParamEnv::empty(traits::Reveal::UserFacing);
3922 let substs = Substs::identity_for_item(tcx.global_tcx(), count_def_id);
3923 let count = tcx.const_eval(param_env.and((count_def_id, substs)));
3925 if let Err(ref err) = count {
3926 err.report(tcx, tcx.def_span(count_def_id), "constant expression");
3929 let uty = match expected {
3930 ExpectHasType(uty) => {
3932 ty::TyArray(ty, _) | ty::TySlice(ty) => Some(ty),
3939 let (element_ty, t) = match uty {
3941 self.check_expr_coercable_to_type(&element, uty);
3945 let t: Ty = self.next_ty_var(TypeVariableOrigin::MiscVariable(element.span));
3946 let element_ty = self.check_expr_has_type_or_error(&element, t);
3951 if let Ok(count) = count {
3952 let zero_or_one = count.val.to_const_int().and_then(|count| {
3953 count.to_u64().map(|count| count <= 1)
3954 }).unwrap_or(false);
3956 // For [foo, ..n] where n > 1, `foo` must have
3958 let lang_item = self.tcx.require_lang_item(lang_items::CopyTraitLangItem);
3959 self.require_type_meets(t, expr.span, traits::RepeatVec, lang_item);
3963 if element_ty.references_error() {
3965 } else if let Ok(count) = count {
3966 tcx.mk_ty(ty::TyArray(t, count))
3971 hir::ExprTup(ref elts) => {
3972 let flds = expected.only_has_type(self).and_then(|ty| {
3973 let ty = self.resolve_type_vars_with_obligations(ty);
3975 ty::TyTuple(ref flds, _) => Some(&flds[..]),
3980 let elt_ts_iter = elts.iter().enumerate().map(|(i, e)| {
3981 let t = match flds {
3982 Some(ref fs) if i < fs.len() => {
3984 self.check_expr_coercable_to_type(&e, ety);
3988 self.check_expr_with_expectation(&e, NoExpectation)
3993 let tuple = tcx.mk_tup(elt_ts_iter, false);
3994 if tuple.references_error() {
3997 self.require_type_is_sized(tuple, expr.span, traits::TupleInitializerSized);
4001 hir::ExprStruct(ref qpath, ref fields, ref base_expr) => {
4002 self.check_expr_struct(expr, expected, qpath, fields, base_expr)
4004 hir::ExprField(ref base, ref field) => {
4005 self.check_field(expr, lvalue_pref, &base, field)
4007 hir::ExprTupField(ref base, idx) => {
4008 self.check_tup_field(expr, lvalue_pref, &base, idx)
4010 hir::ExprIndex(ref base, ref idx) => {
4011 let base_t = self.check_expr_with_lvalue_pref(&base, lvalue_pref);
4012 let idx_t = self.check_expr(&idx);
4014 if base_t.references_error() {
4016 } else if idx_t.references_error() {
4019 let base_t = self.structurally_resolved_type(expr.span, base_t);
4020 match self.lookup_indexing(expr, base, base_t, idx_t, lvalue_pref) {
4021 Some((index_ty, element_ty)) => {
4022 self.demand_coerce(idx, idx_t, index_ty);
4026 let mut err = type_error_struct!(tcx.sess, expr.span, base_t, E0608,
4027 "cannot index into a value of type `{}`",
4029 // Try to give some advice about indexing tuples.
4030 if let ty::TyTuple(..) = base_t.sty {
4031 let mut needs_note = true;
4032 // If the index is an integer, we can show the actual
4033 // fixed expression:
4034 if let hir::ExprLit(ref lit) = idx.node {
4035 if let ast::LitKind::Int(i,
4036 ast::LitIntType::Unsuffixed) = lit.node {
4037 let snip = tcx.sess.codemap().span_to_snippet(base.span);
4038 if let Ok(snip) = snip {
4039 err.span_suggestion(expr.span,
4040 "to access tuple elements, use",
4041 format!("{}.{}", snip, i));
4047 err.help("to access tuple elements, use tuple indexing \
4048 syntax (e.g. `tuple.0`)");
4057 hir::ExprYield(ref value) => {
4058 match self.yield_ty {
4060 self.check_expr_coercable_to_type(&value, ty);
4063 struct_span_err!(self.tcx.sess, expr.span, E0627,
4064 "yield statement outside of generator literal").emit();
4072 // Finish resolving a path in a struct expression or pattern `S::A { .. }` if necessary.
4073 // The newly resolved definition is written into `type_dependent_defs`.
4074 fn finish_resolving_struct_path(&self,
4077 node_id: ast::NodeId)
4081 hir::QPath::Resolved(ref maybe_qself, ref path) => {
4082 let opt_self_ty = maybe_qself.as_ref().map(|qself| self.to_ty(qself));
4083 let ty = AstConv::def_to_ty(self, opt_self_ty, path, true);
4086 hir::QPath::TypeRelative(ref qself, ref segment) => {
4087 let ty = self.to_ty(qself);
4089 let def = if let hir::TyPath(hir::QPath::Resolved(_, ref path)) = qself.node {
4094 let (ty, def) = AstConv::associated_path_def_to_ty(self, node_id, path_span,
4097 // Write back the new resolution.
4098 let hir_id = self.tcx.hir.node_to_hir_id(node_id);
4099 self.tables.borrow_mut().type_dependent_defs_mut().insert(hir_id, def);
4106 // Resolve associated value path into a base type and associated constant or method definition.
4107 // The newly resolved definition is written into `type_dependent_defs`.
4108 pub fn resolve_ty_and_def_ufcs<'b>(&self,
4109 qpath: &'b hir::QPath,
4110 node_id: ast::NodeId,
4112 -> (Def, Option<Ty<'tcx>>, &'b [hir::PathSegment])
4114 let (ty, item_segment) = match *qpath {
4115 hir::QPath::Resolved(ref opt_qself, ref path) => {
4117 opt_qself.as_ref().map(|qself| self.to_ty(qself)),
4118 &path.segments[..]);
4120 hir::QPath::TypeRelative(ref qself, ref segment) => {
4121 (self.to_ty(qself), segment)
4124 let hir_id = self.tcx.hir.node_to_hir_id(node_id);
4125 if let Some(cached_def) = self.tables.borrow().type_dependent_defs().get(hir_id) {
4126 // Return directly on cache hit. This is useful to avoid doubly reporting
4127 // errors with default match binding modes. See #44614.
4128 return (*cached_def, Some(ty), slice::ref_slice(&**item_segment))
4130 let item_name = item_segment.name;
4131 let def = match self.resolve_ufcs(span, item_name, ty, node_id) {
4134 let def = match error {
4135 method::MethodError::PrivateMatch(def, _) => def,
4138 if item_name != keywords::Invalid.name() {
4139 self.report_method_error(span, ty, item_name, None, error, None);
4145 // Write back the new resolution.
4146 self.tables.borrow_mut().type_dependent_defs_mut().insert(hir_id, def);
4147 (def, Some(ty), slice::ref_slice(&**item_segment))
4150 pub fn check_decl_initializer(&self,
4151 local: &'gcx hir::Local,
4152 init: &'gcx hir::Expr) -> Ty<'tcx>
4154 // FIXME(tschottdorf): contains_explicit_ref_binding() must be removed
4155 // for #42640 (default match binding modes).
4158 let ref_bindings = local.pat.contains_explicit_ref_binding();
4160 let local_ty = self.local_ty(init.span, local.id);
4161 if let Some(m) = ref_bindings {
4162 // Somewhat subtle: if we have a `ref` binding in the pattern,
4163 // we want to avoid introducing coercions for the RHS. This is
4164 // both because it helps preserve sanity and, in the case of
4165 // ref mut, for soundness (issue #23116). In particular, in
4166 // the latter case, we need to be clear that the type of the
4167 // referent for the reference that results is *equal to* the
4168 // type of the lvalue it is referencing, and not some
4169 // supertype thereof.
4170 let init_ty = self.check_expr_with_lvalue_pref(init, LvaluePreference::from_mutbl(m));
4171 self.demand_eqtype(init.span, init_ty, local_ty);
4174 self.check_expr_coercable_to_type(init, local_ty)
4178 pub fn check_decl_local(&self, local: &'gcx hir::Local) {
4179 let t = self.local_ty(local.span, local.id);
4180 self.write_ty(local.hir_id, t);
4182 if let Some(ref init) = local.init {
4183 let init_ty = self.check_decl_initializer(local, &init);
4184 if init_ty.references_error() {
4185 self.write_ty(local.hir_id, init_ty);
4189 self.check_pat_walk(&local.pat, t,
4190 ty::BindingMode::BindByValue(hir::Mutability::MutImmutable),
4192 let pat_ty = self.node_ty(local.pat.hir_id);
4193 if pat_ty.references_error() {
4194 self.write_ty(local.hir_id, pat_ty);
4198 pub fn check_stmt(&self, stmt: &'gcx hir::Stmt) {
4199 // Don't do all the complex logic below for DeclItem.
4201 hir::StmtDecl(ref decl, _) => {
4203 hir::DeclLocal(_) => {}
4204 hir::DeclItem(_) => {
4209 hir::StmtExpr(..) | hir::StmtSemi(..) => {}
4212 self.warn_if_unreachable(stmt.node.id(), stmt.span, "statement");
4214 // Hide the outer diverging and has_errors flags.
4215 let old_diverges = self.diverges.get();
4216 let old_has_errors = self.has_errors.get();
4217 self.diverges.set(Diverges::Maybe);
4218 self.has_errors.set(false);
4221 hir::StmtDecl(ref decl, _) => {
4223 hir::DeclLocal(ref l) => {
4224 self.check_decl_local(&l);
4226 hir::DeclItem(_) => {/* ignore for now */}
4229 hir::StmtExpr(ref expr, _) => {
4230 // Check with expected type of ()
4231 self.check_expr_has_type_or_error(&expr, self.tcx.mk_nil());
4233 hir::StmtSemi(ref expr, _) => {
4234 self.check_expr(&expr);
4238 // Combine the diverging and has_error flags.
4239 self.diverges.set(self.diverges.get() | old_diverges);
4240 self.has_errors.set(self.has_errors.get() | old_has_errors);
4243 pub fn check_block_no_value(&self, blk: &'gcx hir::Block) {
4244 let unit = self.tcx.mk_nil();
4245 let ty = self.check_block_with_expected(blk, ExpectHasType(unit));
4247 // if the block produces a `!` value, that can always be
4248 // (effectively) coerced to unit.
4250 self.demand_suptype(blk.span, unit, ty);
4254 fn check_block_with_expected(&self,
4255 blk: &'gcx hir::Block,
4256 expected: Expectation<'tcx>) -> Ty<'tcx> {
4258 let mut fcx_ps = self.ps.borrow_mut();
4259 let unsafety_state = fcx_ps.recurse(blk);
4260 replace(&mut *fcx_ps, unsafety_state)
4263 // In some cases, blocks have just one exit, but other blocks
4264 // can be targeted by multiple breaks. This cannot happen in
4265 // normal Rust syntax today, but it can happen when we desugar
4266 // a `do catch { ... }` expression.
4270 // 'a: { if true { break 'a Err(()); } Ok(()) }
4272 // Here we would wind up with two coercions, one from
4273 // `Err(())` and the other from the tail expression
4274 // `Ok(())`. If the tail expression is omitted, that's a
4275 // "forced unit" -- unless the block diverges, in which
4276 // case we can ignore the tail expression (e.g., `'a: {
4277 // break 'a 22; }` would not force the type of the block
4279 let tail_expr = blk.expr.as_ref();
4280 let coerce_to_ty = expected.coercion_target_type(self, blk.span);
4281 let coerce = if blk.targeted_by_break {
4282 CoerceMany::new(coerce_to_ty)
4284 let tail_expr: &[P<hir::Expr>] = match tail_expr {
4285 Some(e) => ref_slice(e),
4288 CoerceMany::with_coercion_sites(coerce_to_ty, tail_expr)
4291 let prev_diverges = self.diverges.get();
4292 let ctxt = BreakableCtxt {
4293 coerce: Some(coerce),
4297 let (ctxt, ()) = self.with_breakable_ctxt(blk.id, ctxt, || {
4298 for s in &blk.stmts {
4302 // check the tail expression **without** holding the
4303 // `enclosing_breakables` lock below.
4304 let tail_expr_ty = tail_expr.map(|t| self.check_expr_with_expectation(t, expected));
4306 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4307 let ctxt = enclosing_breakables.find_breakable(blk.id);
4308 let coerce = ctxt.coerce.as_mut().unwrap();
4309 if let Some(tail_expr_ty) = tail_expr_ty {
4310 let tail_expr = tail_expr.unwrap();
4311 let cause = self.cause(tail_expr.span,
4312 ObligationCauseCode::BlockTailExpression(blk.id));
4317 self.diverges.get());
4319 // Subtle: if there is no explicit tail expression,
4320 // that is typically equivalent to a tail expression
4321 // of `()` -- except if the block diverges. In that
4322 // case, there is no value supplied from the tail
4323 // expression (assuming there are no other breaks,
4324 // this implies that the type of the block will be
4327 // #41425 -- label the implicit `()` as being the
4328 // "found type" here, rather than the "expected type".
4329 if !self.diverges.get().always() {
4330 coerce.coerce_forced_unit(self, &self.misc(blk.span), &mut |err| {
4331 if let Some(expected_ty) = expected.only_has_type(self) {
4332 self.consider_hint_about_removing_semicolon(blk,
4342 // If we can break from the block, then the block's exit is always reachable
4343 // (... as long as the entry is reachable) - regardless of the tail of the block.
4344 self.diverges.set(prev_diverges);
4347 let mut ty = ctxt.coerce.unwrap().complete(self);
4349 if self.has_errors.get() || ty.references_error() {
4350 ty = self.tcx.types.err
4353 self.write_ty(blk.hir_id, ty);
4355 *self.ps.borrow_mut() = prev;
4359 /// Given a `NodeId`, return the `FnDecl` of the method it is enclosed by and whether a
4360 /// suggestion can be made, `None` otherwise.
4361 pub fn get_fn_decl(&self, blk_id: ast::NodeId) -> Option<(hir::FnDecl, bool)> {
4362 // Get enclosing Fn, if it is a function or a trait method, unless there's a `loop` or
4363 // `while` before reaching it, as block tail returns are not available in them.
4364 if let Some(fn_id) = self.tcx.hir.get_return_block(blk_id) {
4365 let parent = self.tcx.hir.get(fn_id);
4367 if let Node::NodeItem(&hir::Item {
4368 name, node: hir::ItemFn(ref decl, ..), ..
4370 decl.clone().and_then(|decl| {
4371 // This is less than ideal, it will not suggest a return type span on any
4372 // method called `main`, regardless of whether it is actually the entry point,
4373 // but it will still present it as the reason for the expected type.
4374 Some((decl, name != Symbol::intern("main")))
4376 } else if let Node::NodeTraitItem(&hir::TraitItem {
4377 node: hir::TraitItemKind::Method(hir::MethodSig {
4381 decl.clone().and_then(|decl| {
4384 } else if let Node::NodeImplItem(&hir::ImplItem {
4385 node: hir::ImplItemKind::Method(hir::MethodSig {
4389 decl.clone().and_then(|decl| {
4400 /// On implicit return expressions with mismatched types, provide the following suggestions:
4402 /// - Point out the method's return type as the reason for the expected type
4403 /// - Possible missing semicolon
4404 /// - Possible missing return type if the return type is the default, and not `fn main()`
4405 pub fn suggest_mismatched_types_on_tail(&self,
4406 err: &mut DiagnosticBuilder<'tcx>,
4407 expression: &'gcx hir::Expr,
4411 blk_id: ast::NodeId) {
4412 self.suggest_missing_semicolon(err, expression, expected, cause_span);
4414 if let Some((fn_decl, can_suggest)) = self.get_fn_decl(blk_id) {
4415 self.suggest_missing_return_type(err, &fn_decl, expected, found, can_suggest);
4419 /// A common error is to forget to add a semicolon at the end of a block:
4423 /// bar_that_returns_u32()
4427 /// This routine checks if the return expression in a block would make sense on its own as a
4428 /// statement and the return type has been left as default or has been specified as `()`. If so,
4429 /// it suggests adding a semicolon.
4430 fn suggest_missing_semicolon(&self,
4431 err: &mut DiagnosticBuilder<'tcx>,
4432 expression: &'gcx hir::Expr,
4435 if expected.is_nil() {
4436 // `BlockTailExpression` only relevant if the tail expr would be
4437 // useful on its own.
4438 match expression.node {
4440 hir::ExprMethodCall(..) |
4442 hir::ExprWhile(..) |
4444 hir::ExprMatch(..) |
4445 hir::ExprBlock(..) => {
4446 let sp = cause_span.next_point();
4447 err.span_suggestion(sp,
4448 "try adding a semicolon",
4457 /// A possible error is to forget to add a return type that is needed:
4461 /// bar_that_returns_u32()
4465 /// This routine checks if the return type is left as default, the method is not part of an
4466 /// `impl` block and that it isn't the `main` method. If so, it suggests setting the return
4468 fn suggest_missing_return_type(&self,
4469 err: &mut DiagnosticBuilder<'tcx>,
4470 fn_decl: &hir::FnDecl,
4473 can_suggest: bool) {
4474 // Only suggest changing the return type for methods that
4475 // haven't set a return type at all (and aren't `fn main()` or an impl).
4476 match (&fn_decl.output, found.is_suggestable(), can_suggest) {
4477 (&hir::FunctionRetTy::DefaultReturn(span), true, true) => {
4478 err.span_suggestion(span,
4479 "try adding a return type",
4480 format!("-> {} ", found));
4482 (&hir::FunctionRetTy::DefaultReturn(span), false, true) => {
4483 err.span_label(span, "possibly return type missing here?");
4485 (&hir::FunctionRetTy::DefaultReturn(span), _, _) => {
4486 // `fn main()` must return `()`, do not suggest changing return type
4487 err.span_label(span, "expected `()` because of default return type");
4489 (&hir::FunctionRetTy::Return(ref ty), _, _) => {
4490 // Only point to return type if the expected type is the return type, as if they
4491 // are not, the expectation must have been caused by something else.
4492 debug!("suggest_missing_return_type: return type {:?} node {:?}", ty, ty.node);
4494 let ty = AstConv::ast_ty_to_ty(self, ty);
4495 debug!("suggest_missing_return_type: return type sty {:?}", ty.sty);
4496 debug!("suggest_missing_return_type: expected type sty {:?}", ty.sty);
4497 if ty.sty == expected.sty {
4498 err.span_label(sp, format!("expected `{}` because of return type",
4506 /// A common error is to add an extra semicolon:
4509 /// fn foo() -> usize {
4514 /// This routine checks if the final statement in a block is an
4515 /// expression with an explicit semicolon whose type is compatible
4516 /// with `expected_ty`. If so, it suggests removing the semicolon.
4517 fn consider_hint_about_removing_semicolon(&self,
4518 blk: &'gcx hir::Block,
4519 expected_ty: Ty<'tcx>,
4520 err: &mut DiagnosticBuilder) {
4521 // Be helpful when the user wrote `{... expr;}` and
4522 // taking the `;` off is enough to fix the error.
4523 let last_stmt = match blk.stmts.last() {
4527 let last_expr = match last_stmt.node {
4528 hir::StmtSemi(ref e, _) => e,
4531 let last_expr_ty = self.node_ty(last_expr.hir_id);
4532 if self.can_sub(self.param_env, last_expr_ty, expected_ty).is_err() {
4535 let original_span = original_sp(last_stmt.span, blk.span);
4536 let span_semi = original_span.with_lo(original_span.hi() - BytePos(1));
4537 err.span_suggestion(span_semi, "consider removing this semicolon", "".to_string());
4540 // Instantiates the given path, which must refer to an item with the given
4541 // number of type parameters and type.
4542 pub fn instantiate_value_path(&self,
4543 segments: &[hir::PathSegment],
4544 opt_self_ty: Option<Ty<'tcx>>,
4547 node_id: ast::NodeId)
4549 debug!("instantiate_value_path(path={:?}, def={:?}, node_id={})",
4554 // We need to extract the type parameters supplied by the user in
4555 // the path `path`. Due to the current setup, this is a bit of a
4556 // tricky-process; the problem is that resolve only tells us the
4557 // end-point of the path resolution, and not the intermediate steps.
4558 // Luckily, we can (at least for now) deduce the intermediate steps
4559 // just from the end-point.
4561 // There are basically four cases to consider:
4563 // 1. Reference to a constructor of enum variant or struct:
4565 // struct Foo<T>(...)
4566 // enum E<T> { Foo(...) }
4568 // In these cases, the parameters are declared in the type
4571 // 2. Reference to a fn item or a free constant:
4575 // In this case, the path will again always have the form
4576 // `a::b::foo::<T>` where only the final segment should have
4577 // type parameters. However, in this case, those parameters are
4578 // declared on a value, and hence are in the `FnSpace`.
4580 // 3. Reference to a method or an associated constant:
4582 // impl<A> SomeStruct<A> {
4586 // Here we can have a path like
4587 // `a::b::SomeStruct::<A>::foo::<B>`, in which case parameters
4588 // may appear in two places. The penultimate segment,
4589 // `SomeStruct::<A>`, contains parameters in TypeSpace, and the
4590 // final segment, `foo::<B>` contains parameters in fn space.
4592 // 4. Reference to a local variable
4594 // Local variables can't have any type parameters.
4596 // The first step then is to categorize the segments appropriately.
4598 assert!(!segments.is_empty());
4600 let mut ufcs_associated = None;
4601 let mut type_segment = None;
4602 let mut fn_segment = None;
4604 // Case 1. Reference to a struct/variant constructor.
4605 Def::StructCtor(def_id, ..) |
4606 Def::VariantCtor(def_id, ..) => {
4607 // Everything but the final segment should have no
4608 // parameters at all.
4609 let mut generics = self.tcx.generics_of(def_id);
4610 if let Some(def_id) = generics.parent {
4611 // Variant and struct constructors use the
4612 // generics of their parent type definition.
4613 generics = self.tcx.generics_of(def_id);
4615 type_segment = Some((segments.last().unwrap(), generics));
4618 // Case 2. Reference to a top-level value.
4620 Def::Const(def_id) |
4621 Def::Static(def_id, _) => {
4622 fn_segment = Some((segments.last().unwrap(),
4623 self.tcx.generics_of(def_id)));
4626 // Case 3. Reference to a method or associated const.
4627 Def::Method(def_id) |
4628 Def::AssociatedConst(def_id) => {
4629 let container = self.tcx.associated_item(def_id).container;
4631 ty::TraitContainer(trait_did) => {
4632 callee::check_legal_trait_for_method_call(self.tcx, span, trait_did)
4634 ty::ImplContainer(_) => {}
4637 let generics = self.tcx.generics_of(def_id);
4638 if segments.len() >= 2 {
4639 let parent_generics = self.tcx.generics_of(generics.parent.unwrap());
4640 type_segment = Some((&segments[segments.len() - 2], parent_generics));
4642 // `<T>::assoc` will end up here, and so can `T::assoc`.
4643 let self_ty = opt_self_ty.expect("UFCS sugared assoc missing Self");
4644 ufcs_associated = Some((container, self_ty));
4646 fn_segment = Some((segments.last().unwrap(), generics));
4649 // Case 4. Local variable, no generics.
4650 Def::Local(..) | Def::Upvar(..) => {}
4652 _ => bug!("unexpected definition: {:?}", def),
4655 debug!("type_segment={:?} fn_segment={:?}", type_segment, fn_segment);
4657 // Now that we have categorized what space the parameters for each
4658 // segment belong to, let's sort out the parameters that the user
4659 // provided (if any) into their appropriate spaces. We'll also report
4660 // errors if type parameters are provided in an inappropriate place.
4661 let poly_segments = type_segment.is_some() as usize +
4662 fn_segment.is_some() as usize;
4663 AstConv::prohibit_type_params(self, &segments[..segments.len() - poly_segments]);
4666 Def::Local(nid) | Def::Upvar(nid, ..) => {
4667 let ty = self.local_ty(span, nid);
4668 let ty = self.normalize_associated_types_in(span, &ty);
4669 self.write_ty(self.tcx.hir.node_to_hir_id(node_id), ty);
4675 // Now we have to compare the types that the user *actually*
4676 // provided against the types that were *expected*. If the user
4677 // did not provide any types, then we want to substitute inference
4678 // variables. If the user provided some types, we may still need
4679 // to add defaults. If the user provided *too many* types, that's
4681 self.check_path_parameter_count(span, &mut type_segment, false);
4682 self.check_path_parameter_count(span, &mut fn_segment, false);
4683 self.check_impl_trait(span, &mut fn_segment);
4685 let (fn_start, has_self) = match (type_segment, fn_segment) {
4686 (_, Some((_, generics))) => {
4687 (generics.parent_count(), generics.has_self)
4689 (Some((_, generics)), None) => {
4690 (generics.own_count(), generics.has_self)
4692 (None, None) => (0, false)
4694 let substs = Substs::for_item(self.tcx, def.def_id(), |def, _| {
4695 let mut i = def.index as usize;
4697 let segment = if i < fn_start {
4698 i -= has_self as usize;
4704 let lifetimes = segment.map_or(&[][..], |(s, _)| {
4705 s.parameters.as_ref().map_or(&[][..], |p| &p.lifetimes[..])
4708 if let Some(lifetime) = lifetimes.get(i) {
4709 AstConv::ast_region_to_region(self, lifetime, Some(def))
4711 self.re_infer(span, Some(def)).unwrap()
4714 let mut i = def.index as usize;
4716 let segment = if i < fn_start {
4717 // Handle Self first, so we can adjust the index to match the AST.
4718 if has_self && i == 0 {
4719 return opt_self_ty.unwrap_or_else(|| {
4720 self.type_var_for_def(span, def, substs)
4723 i -= has_self as usize;
4729 let (types, infer_types) = segment.map_or((&[][..], true), |(s, _)| {
4730 (s.parameters.as_ref().map_or(&[][..], |p| &p.types[..]), s.infer_types)
4733 // Skip over the lifetimes in the same segment.
4734 if let Some((_, generics)) = segment {
4735 i -= generics.regions.len();
4738 if let Some(ast_ty) = types.get(i) {
4739 // A provided type parameter.
4741 } else if !infer_types && def.has_default {
4742 // No type parameter provided, but a default exists.
4743 let default = self.tcx.type_of(def.def_id);
4746 default.subst_spanned(self.tcx, substs, Some(span))
4749 // No type parameters were provided, we can infer all.
4750 // This can also be reached in some error cases:
4751 // We prefer to use inference variables instead of
4752 // TyError to let type inference recover somewhat.
4753 self.type_var_for_def(span, def, substs)
4757 // The things we are substituting into the type should not contain
4758 // escaping late-bound regions, and nor should the base type scheme.
4759 let ty = self.tcx.type_of(def.def_id());
4760 assert!(!substs.has_escaping_regions());
4761 assert!(!ty.has_escaping_regions());
4763 // Add all the obligations that are required, substituting and
4764 // normalized appropriately.
4765 let bounds = self.instantiate_bounds(span, def.def_id(), &substs);
4766 self.add_obligations_for_parameters(
4767 traits::ObligationCause::new(span, self.body_id, traits::ItemObligation(def.def_id())),
4770 // Substitute the values for the type parameters into the type of
4771 // the referenced item.
4772 let ty_substituted = self.instantiate_type_scheme(span, &substs, &ty);
4774 if let Some((ty::ImplContainer(impl_def_id), self_ty)) = ufcs_associated {
4775 // In the case of `Foo<T>::method` and `<Foo<T>>::method`, if `method`
4776 // is inherent, there is no `Self` parameter, instead, the impl needs
4777 // type parameters, which we can infer by unifying the provided `Self`
4778 // with the substituted impl type.
4779 let ty = self.tcx.type_of(impl_def_id);
4781 let impl_ty = self.instantiate_type_scheme(span, &substs, &ty);
4782 match self.at(&self.misc(span), self.param_env).sup(impl_ty, self_ty) {
4783 Ok(ok) => self.register_infer_ok_obligations(ok),
4786 "instantiate_value_path: (UFCS) {:?} was a subtype of {:?} but now is not?",
4793 debug!("instantiate_value_path: type of {:?} is {:?}",
4796 self.write_substs(self.tcx.hir.node_to_hir_id(node_id), substs);
4800 /// Report errors if the provided parameters are too few or too many.
4801 fn check_path_parameter_count(&self,
4803 segment: &mut Option<(&hir::PathSegment, &ty::Generics)>,
4804 is_method_call: bool) {
4805 let (lifetimes, types, infer_types, bindings) = segment.map_or(
4806 (&[][..], &[][..], true, &[][..]),
4807 |(s, _)| s.parameters.as_ref().map_or(
4808 (&[][..], &[][..], s.infer_types, &[][..]),
4809 |p| (&p.lifetimes[..], &p.types[..],
4810 s.infer_types, &p.bindings[..])));
4811 let infer_lifetimes = lifetimes.len() == 0;
4813 let count_lifetime_params = |n| {
4814 format!("{} lifetime parameter{}", n, if n == 1 { "" } else { "s" })
4816 let count_type_params = |n| {
4817 format!("{} type parameter{}", n, if n == 1 { "" } else { "s" })
4820 // Check provided type parameters.
4821 let type_defs = segment.map_or(&[][..], |(_, generics)| {
4822 if generics.parent.is_none() {
4823 &generics.types[generics.has_self as usize..]
4828 let required_len = type_defs.iter().take_while(|d| !d.has_default).count();
4829 if types.len() > type_defs.len() {
4830 let span = types[type_defs.len()].span;
4831 let expected_text = count_type_params(type_defs.len());
4832 let actual_text = count_type_params(types.len());
4833 struct_span_err!(self.tcx.sess, span, E0087,
4834 "too many type parameters provided: \
4835 expected at most {}, found {}",
4836 expected_text, actual_text)
4837 .span_label(span, format!("expected {}", expected_text))
4840 // To prevent derived errors to accumulate due to extra
4841 // type parameters, we force instantiate_value_path to
4842 // use inference variables instead of the provided types.
4844 } else if types.len() < required_len && !infer_types {
4845 let expected_text = count_type_params(required_len);
4846 let actual_text = count_type_params(types.len());
4847 struct_span_err!(self.tcx.sess, span, E0089,
4848 "too few type parameters provided: \
4849 expected {}, found {}",
4850 expected_text, actual_text)
4851 .span_label(span, format!("expected {}", expected_text))
4855 if !bindings.is_empty() {
4856 AstConv::prohibit_projection(self, bindings[0].span);
4859 // Check provided lifetime parameters.
4860 let lifetime_defs = segment.map_or(&[][..], |(_, generics)| &generics.regions);
4861 let required_len = lifetime_defs.len();
4863 // Prohibit explicit lifetime arguments if late bound lifetime parameters are present.
4864 let has_late_bound_lifetime_defs =
4865 segment.map_or(None, |(_, generics)| generics.has_late_bound_regions);
4866 if let (Some(span_late), false) = (has_late_bound_lifetime_defs, lifetimes.is_empty()) {
4867 // Report this as a lint only if no error was reported previously.
4868 let primary_msg = "cannot specify lifetime arguments explicitly \
4869 if late bound lifetime parameters are present";
4870 let note_msg = "the late bound lifetime parameter is introduced here";
4871 if !is_method_call && (lifetimes.len() > lifetime_defs.len() ||
4872 lifetimes.len() < required_len && !infer_lifetimes) {
4873 let mut err = self.tcx.sess.struct_span_err(lifetimes[0].span, primary_msg);
4874 err.span_note(span_late, note_msg);
4878 let mut multispan = MultiSpan::from_span(lifetimes[0].span);
4879 multispan.push_span_label(span_late, note_msg.to_string());
4880 self.tcx.lint_node(lint::builtin::LATE_BOUND_LIFETIME_ARGUMENTS,
4881 lifetimes[0].id, multispan, primary_msg);
4886 if lifetimes.len() > lifetime_defs.len() {
4887 let span = lifetimes[lifetime_defs.len()].span;
4888 let expected_text = count_lifetime_params(lifetime_defs.len());
4889 let actual_text = count_lifetime_params(lifetimes.len());
4890 struct_span_err!(self.tcx.sess, span, E0088,
4891 "too many lifetime parameters provided: \
4892 expected at most {}, found {}",
4893 expected_text, actual_text)
4894 .span_label(span, format!("expected {}", expected_text))
4896 } else if lifetimes.len() < required_len && !infer_lifetimes {
4897 let expected_text = count_lifetime_params(lifetime_defs.len());
4898 let actual_text = count_lifetime_params(lifetimes.len());
4899 struct_span_err!(self.tcx.sess, span, E0090,
4900 "too few lifetime parameters provided: \
4901 expected {}, found {}",
4902 expected_text, actual_text)
4903 .span_label(span, format!("expected {}", expected_text))
4908 /// Report error if there is an explicit type parameter when using `impl Trait`.
4909 fn check_impl_trait(&self,
4911 segment: &mut Option<(&hir::PathSegment, &ty::Generics)>) {
4912 use hir::SyntheticTyParamKind::*;
4914 segment.map(|(path_segment, generics)| {
4915 let explicit = !path_segment.infer_types;
4916 let impl_trait = generics.types.iter()
4918 match ty_param.synthetic {
4919 Some(ImplTrait) => true,
4924 if explicit && impl_trait {
4925 let mut err = struct_span_err! {
4929 "cannot provide explicit type parameters when `impl Trait` is \
4930 used in argument position."
4938 fn structurally_resolve_type_or_else<F>(&self, sp: Span, ty: Ty<'tcx>, f: F)
4940 where F: Fn() -> Ty<'tcx>
4942 let mut ty = self.resolve_type_vars_with_obligations(ty);
4945 let alternative = f();
4948 if alternative.is_ty_var() || alternative.references_error() {
4949 if !self.is_tainted_by_errors() {
4950 type_error_struct!(self.tcx.sess, sp, ty, E0619,
4951 "the type of this value must be known in this context")
4954 self.demand_suptype(sp, self.tcx.types.err, ty);
4955 ty = self.tcx.types.err;
4957 self.demand_suptype(sp, alternative, ty);
4965 // Resolves `typ` by a single level if `typ` is a type variable. If no
4966 // resolution is possible, then an error is reported.
4967 pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
4968 self.structurally_resolve_type_or_else(sp, ty, || {
4973 fn with_breakable_ctxt<F: FnOnce() -> R, R>(&self, id: ast::NodeId,
4974 ctxt: BreakableCtxt<'gcx, 'tcx>, f: F)
4975 -> (BreakableCtxt<'gcx, 'tcx>, R) {
4978 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4979 index = enclosing_breakables.stack.len();
4980 enclosing_breakables.by_id.insert(id, index);
4981 enclosing_breakables.stack.push(ctxt);
4985 let mut enclosing_breakables = self.enclosing_breakables.borrow_mut();
4986 debug_assert!(enclosing_breakables.stack.len() == index + 1);
4987 enclosing_breakables.by_id.remove(&id).expect("missing breakable context");
4988 enclosing_breakables.stack.pop().expect("missing breakable context")
4994 pub fn check_bounds_are_used<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
4995 generics: &hir::Generics,
4997 debug!("check_bounds_are_used(n_tps={}, ty={:?})",
4998 generics.ty_params.len(), ty);
5000 // make a vector of booleans initially false, set to true when used
5001 if generics.ty_params.is_empty() { return; }
5002 let mut tps_used = vec![false; generics.ty_params.len()];
5004 for leaf_ty in ty.walk() {
5005 if let ty::TyParam(ParamTy {idx, ..}) = leaf_ty.sty {
5006 debug!("Found use of ty param num {}", idx);
5007 tps_used[idx as usize - generics.lifetimes.len()] = true;
5011 for (&used, param) in tps_used.iter().zip(&generics.ty_params) {
5013 struct_span_err!(tcx.sess, param.span, E0091,
5014 "type parameter `{}` is unused",
5016 .span_label(param.span, "unused type parameter")
5022 fn fatally_break_rust(sess: &Session) {
5023 let handler = sess.diagnostic();
5024 handler.span_bug_no_panic(
5026 "It looks like you're trying to break rust; would you like some ICE?",
5028 handler.note_without_error("the compiler expectedly panicked. this is a feature.");
5029 handler.note_without_error(
5030 "we would appreciate a joke overview: \
5031 https://github.com/rust-lang/rust/issues/43162#issuecomment-320764675"
5033 handler.note_without_error(&format!("rustc {} running on {}",
5034 option_env!("CFG_VERSION").unwrap_or("unknown_version"),
5035 ::session::config::host_triple(),