]> git.lizzy.rs Git - rust.git/blob - src/librustc_typeck/check/mod.rs
e972a5ca7fb3894848b2816b77f880e624d6a935
[rust.git] / src / librustc_typeck / check / mod.rs
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.
4 //
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.
10
11 /*
12
13 # check.rs
14
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
18 unknown.
19
20 By far the most complex case is checking the body of a function. This
21 can be broken down into several distinct phases:
22
23 - gather: creates type variables to represent the type of each local
24   variable and pattern binding.
25
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.
31
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.
36
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
41   flexibility.
42
43 - vtable: find and records the impls to use for each trait bound that
44   appears on a type parameter.
45
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.
50
51 ## Intermediate types
52
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.item_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 `ccx.tcx`.
60
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.
64
65 The types of top-level items, which never contain unbound type
66 variables, are stored directly into the `tcx` tables.
67
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
75 type parameter).
76
77 */
78
79 pub use self::Expectation::*;
80 pub use self::compare_method::{compare_impl_method, compare_const_impl};
81 use self::TupleArgumentsFlag::*;
82
83 use astconv::{AstConv, ast_region_to_region, PathParamMode};
84 use dep_graph::DepNode;
85 use fmt_macros::{Parser, Piece, Position};
86 use middle::cstore::LOCAL_CRATE;
87 use hir::def::{Def, PathResolution};
88 use hir::def_id::DefId;
89 use hir::pat_util;
90 use rustc::infer::{self, InferCtxt, InferOk, TypeOrigin, TypeTrace, type_variable};
91 use rustc::ty::subst::{Subst, Substs};
92 use rustc::traits::{self, Reveal};
93 use rustc::ty::{ParamTy, ParameterEnvironment};
94 use rustc::ty::{LvaluePreference, NoPreference, PreferMutLvalue};
95 use rustc::ty::{self, ToPolyTraitRef, Ty, TyCtxt, Visibility};
96 use rustc::ty::{MethodCall, MethodCallee};
97 use rustc::ty::adjustment;
98 use rustc::ty::fold::{BottomUpFolder, TypeFoldable};
99 use rustc::ty::util::{Representability, IntTypeExt};
100 use require_c_abi_if_variadic;
101 use rscope::{ElisionFailureInfo, RegionScope};
102 use session::{Session, CompileResult};
103 use CrateCtxt;
104 use TypeAndSubsts;
105 use lint;
106 use util::common::{block_query, ErrorReported, indenter, loop_query};
107 use util::nodemap::{DefIdMap, FnvHashMap, NodeMap};
108
109 use std::cell::{Cell, Ref, RefCell};
110 use std::collections::{HashSet};
111 use std::mem::replace;
112 use std::ops::Deref;
113 use syntax::abi::Abi;
114 use syntax::ast;
115 use syntax::attr;
116 use syntax::attr::AttrMetaMethods;
117 use syntax::codemap::{self, Spanned};
118 use syntax::feature_gate::{GateIssue, emit_feature_err};
119 use syntax::parse::token::{self, InternedString, keywords};
120 use syntax::ptr::P;
121 use syntax::util::lev_distance::find_best_match_for_name;
122 use syntax_pos::{self, Span};
123 use errors::DiagnosticBuilder;
124
125 use rustc::hir::intravisit::{self, Visitor};
126 use rustc::hir::{self, PatKind};
127 use rustc::hir::print as pprust;
128 use rustc_back::slice;
129 use rustc_const_eval::eval_length;
130
131 mod assoc;
132 mod autoderef;
133 pub mod dropck;
134 pub mod _match;
135 pub mod writeback;
136 pub mod regionck;
137 pub mod coercion;
138 pub mod demand;
139 pub mod method;
140 mod upvar;
141 mod wfcheck;
142 mod cast;
143 mod closure;
144 mod callee;
145 mod compare_method;
146 mod intrinsic;
147 mod op;
148
149 /// closures defined within the function.  For example:
150 ///
151 ///     fn foo() {
152 ///         bar(move|| { ... })
153 ///     }
154 ///
155 /// Here, the function `foo()` and the closure passed to
156 /// `bar()` will each have their own `FnCtxt`, but they will
157 /// share the inherited fields.
158 pub struct Inherited<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
159     ccx: &'a CrateCtxt<'a, 'gcx>,
160     infcx: InferCtxt<'a, 'gcx, 'tcx>,
161     locals: RefCell<NodeMap<Ty<'tcx>>>,
162
163     fulfillment_cx: RefCell<traits::FulfillmentContext<'tcx>>,
164
165     // When we process a call like `c()` where `c` is a closure type,
166     // we may not have decided yet whether `c` is a `Fn`, `FnMut`, or
167     // `FnOnce` closure. In that case, we defer full resolution of the
168     // call until upvar inference can kick in and make the
169     // decision. We keep these deferred resolutions grouped by the
170     // def-id of the closure, so that once we decide, we can easily go
171     // back and process them.
172     deferred_call_resolutions: RefCell<DefIdMap<Vec<DeferredCallResolutionHandler<'gcx, 'tcx>>>>,
173
174     deferred_cast_checks: RefCell<Vec<cast::CastCheck<'tcx>>>,
175
176     // Anonymized types found in explicit return types and their
177     // associated fresh inference variable. Writeback resolves these
178     // variables to get the concrete type, which can be used to
179     // deanonymize TyAnon, after typeck is done with all functions.
180     anon_types: RefCell<DefIdMap<Ty<'tcx>>>,
181
182     // Obligations which will have to be checked at the end of
183     // type-checking, after all functions have been inferred.
184     deferred_obligations: RefCell<Vec<traits::DeferredObligation<'tcx>>>,
185 }
186
187 impl<'a, 'gcx, 'tcx> Deref for Inherited<'a, 'gcx, 'tcx> {
188     type Target = InferCtxt<'a, 'gcx, 'tcx>;
189     fn deref(&self) -> &Self::Target {
190         &self.infcx
191     }
192 }
193
194 trait DeferredCallResolution<'gcx, 'tcx> {
195     fn resolve<'a>(&mut self, fcx: &FnCtxt<'a, 'gcx, 'tcx>);
196 }
197
198 type DeferredCallResolutionHandler<'gcx, 'tcx> = Box<DeferredCallResolution<'gcx, 'tcx>+'tcx>;
199
200 /// When type-checking an expression, we propagate downward
201 /// whatever type hint we are able in the form of an `Expectation`.
202 #[derive(Copy, Clone, Debug)]
203 pub enum Expectation<'tcx> {
204     /// We know nothing about what type this expression should have.
205     NoExpectation,
206
207     /// This expression should have the type given (or some subtype)
208     ExpectHasType(Ty<'tcx>),
209
210     /// This expression will be cast to the `Ty`
211     ExpectCastableToType(Ty<'tcx>),
212
213     /// This rvalue expression will be wrapped in `&` or `Box` and coerced
214     /// to `&Ty` or `Box<Ty>`, respectively. `Ty` is `[A]` or `Trait`.
215     ExpectRvalueLikeUnsized(Ty<'tcx>),
216 }
217
218 impl<'a, 'gcx, 'tcx> Expectation<'tcx> {
219     // Disregard "castable to" expectations because they
220     // can lead us astray. Consider for example `if cond
221     // {22} else {c} as u8` -- if we propagate the
222     // "castable to u8" constraint to 22, it will pick the
223     // type 22u8, which is overly constrained (c might not
224     // be a u8). In effect, the problem is that the
225     // "castable to" expectation is not the tightest thing
226     // we can say, so we want to drop it in this case.
227     // The tightest thing we can say is "must unify with
228     // else branch". Note that in the case of a "has type"
229     // constraint, this limitation does not hold.
230
231     // If the expected type is just a type variable, then don't use
232     // an expected type. Otherwise, we might write parts of the type
233     // when checking the 'then' block which are incompatible with the
234     // 'else' branch.
235     fn adjust_for_branches(&self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
236         match *self {
237             ExpectHasType(ety) => {
238                 let ety = fcx.shallow_resolve(ety);
239                 if !ety.is_ty_var() {
240                     ExpectHasType(ety)
241                 } else {
242                     NoExpectation
243                 }
244             }
245             ExpectRvalueLikeUnsized(ety) => {
246                 ExpectRvalueLikeUnsized(ety)
247             }
248             _ => NoExpectation
249         }
250     }
251
252     /// Provide an expectation for an rvalue expression given an *optional*
253     /// hint, which is not required for type safety (the resulting type might
254     /// be checked higher up, as is the case with `&expr` and `box expr`), but
255     /// is useful in determining the concrete type.
256     ///
257     /// The primary use case is where the expected type is a fat pointer,
258     /// like `&[isize]`. For example, consider the following statement:
259     ///
260     ///    let x: &[isize] = &[1, 2, 3];
261     ///
262     /// In this case, the expected type for the `&[1, 2, 3]` expression is
263     /// `&[isize]`. If however we were to say that `[1, 2, 3]` has the
264     /// expectation `ExpectHasType([isize])`, that would be too strong --
265     /// `[1, 2, 3]` does not have the type `[isize]` but rather `[isize; 3]`.
266     /// It is only the `&[1, 2, 3]` expression as a whole that can be coerced
267     /// to the type `&[isize]`. Therefore, we propagate this more limited hint,
268     /// which still is useful, because it informs integer literals and the like.
269     /// See the test case `test/run-pass/coerce-expect-unsized.rs` and #20169
270     /// for examples of where this comes up,.
271     fn rvalue_hint(fcx: &FnCtxt<'a, 'gcx, 'tcx>, ty: Ty<'tcx>) -> Expectation<'tcx> {
272         match fcx.tcx.struct_tail(ty).sty {
273             ty::TySlice(_) | ty::TyStr | ty::TyTrait(..) => {
274                 ExpectRvalueLikeUnsized(ty)
275             }
276             _ => ExpectHasType(ty)
277         }
278     }
279
280     // Resolves `expected` by a single level if it is a variable. If
281     // there is no expected type or resolution is not possible (e.g.,
282     // no constraints yet present), just returns `None`.
283     fn resolve(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Expectation<'tcx> {
284         match self {
285             NoExpectation => {
286                 NoExpectation
287             }
288             ExpectCastableToType(t) => {
289                 ExpectCastableToType(fcx.resolve_type_vars_if_possible(&t))
290             }
291             ExpectHasType(t) => {
292                 ExpectHasType(fcx.resolve_type_vars_if_possible(&t))
293             }
294             ExpectRvalueLikeUnsized(t) => {
295                 ExpectRvalueLikeUnsized(fcx.resolve_type_vars_if_possible(&t))
296             }
297         }
298     }
299
300     fn to_option(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Option<Ty<'tcx>> {
301         match self.resolve(fcx) {
302             NoExpectation => None,
303             ExpectCastableToType(ty) |
304             ExpectHasType(ty) |
305             ExpectRvalueLikeUnsized(ty) => Some(ty),
306         }
307     }
308
309     fn only_has_type(self, fcx: &FnCtxt<'a, 'gcx, 'tcx>) -> Option<Ty<'tcx>> {
310         match self.resolve(fcx) {
311             ExpectHasType(ty) => Some(ty),
312             _ => None
313         }
314     }
315 }
316
317 #[derive(Copy, Clone)]
318 pub struct UnsafetyState {
319     pub def: ast::NodeId,
320     pub unsafety: hir::Unsafety,
321     pub unsafe_push_count: u32,
322     from_fn: bool
323 }
324
325 impl UnsafetyState {
326     pub fn function(unsafety: hir::Unsafety, def: ast::NodeId) -> UnsafetyState {
327         UnsafetyState { def: def, unsafety: unsafety, unsafe_push_count: 0, from_fn: true }
328     }
329
330     pub fn recurse(&mut self, blk: &hir::Block) -> UnsafetyState {
331         match self.unsafety {
332             // If this unsafe, then if the outer function was already marked as
333             // unsafe we shouldn't attribute the unsafe'ness to the block. This
334             // way the block can be warned about instead of ignoring this
335             // extraneous block (functions are never warned about).
336             hir::Unsafety::Unsafe if self.from_fn => *self,
337
338             unsafety => {
339                 let (unsafety, def, count) = match blk.rules {
340                     hir::PushUnsafeBlock(..) =>
341                         (unsafety, blk.id, self.unsafe_push_count.checked_add(1).unwrap()),
342                     hir::PopUnsafeBlock(..) =>
343                         (unsafety, blk.id, self.unsafe_push_count.checked_sub(1).unwrap()),
344                     hir::UnsafeBlock(..) =>
345                         (hir::Unsafety::Unsafe, blk.id, self.unsafe_push_count),
346                     hir::DefaultBlock | hir::PushUnstableBlock | hir:: PopUnstableBlock =>
347                         (unsafety, self.def, self.unsafe_push_count),
348                 };
349                 UnsafetyState{ def: def,
350                                unsafety: unsafety,
351                                unsafe_push_count: count,
352                                from_fn: false }
353             }
354         }
355     }
356 }
357
358 #[derive(Clone)]
359 pub struct FnCtxt<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
360     ast_ty_to_ty_cache: RefCell<NodeMap<Ty<'tcx>>>,
361
362     body_id: ast::NodeId,
363
364     // This flag is set to true if, during the writeback phase, we encounter
365     // a type error in this function.
366     writeback_errors: Cell<bool>,
367
368     // Number of errors that had been reported when we started
369     // checking this function. On exit, if we find that *more* errors
370     // have been reported, we will skip regionck and other work that
371     // expects the types within the function to be consistent.
372     err_count_on_creation: usize,
373
374     ret_ty: Ty<'tcx>,
375
376     ps: RefCell<UnsafetyState>,
377
378     inh: &'a Inherited<'a, 'gcx, 'tcx>,
379 }
380
381 impl<'a, 'gcx, 'tcx> Deref for FnCtxt<'a, 'gcx, 'tcx> {
382     type Target = Inherited<'a, 'gcx, 'tcx>;
383     fn deref(&self) -> &Self::Target {
384         &self.inh
385     }
386 }
387
388 /// Helper type of a temporary returned by ccx.inherited(...).
389 /// Necessary because we can't write the following bound:
390 /// F: for<'b, 'tcx> where 'gcx: 'tcx FnOnce(Inherited<'b, 'gcx, 'tcx>).
391 pub struct InheritedBuilder<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
392     ccx: &'a CrateCtxt<'a, 'gcx>,
393     infcx: infer::InferCtxtBuilder<'a, 'gcx, 'tcx>
394 }
395
396 impl<'a, 'gcx, 'tcx> CrateCtxt<'a, 'gcx> {
397     pub fn inherited(&'a self, id: ast::NodeId)
398                      -> InheritedBuilder<'a, 'gcx, 'tcx> {
399         let param_env = ParameterEnvironment::for_item(self.tcx, id);
400         InheritedBuilder {
401             ccx: self,
402             infcx: self.tcx.infer_ctxt(Some(ty::Tables::empty()),
403                                        Some(param_env),
404                                        Reveal::NotSpecializable)
405         }
406     }
407 }
408
409 impl<'a, 'gcx, 'tcx> InheritedBuilder<'a, 'gcx, 'tcx> {
410     fn enter<F, R>(&'tcx mut self, f: F) -> R
411         where F: for<'b> FnOnce(Inherited<'b, 'gcx, 'tcx>) -> R
412     {
413         let ccx = self.ccx;
414         self.infcx.enter(|infcx| {
415             f(Inherited {
416                 ccx: ccx,
417                 infcx: infcx,
418                 fulfillment_cx: RefCell::new(traits::FulfillmentContext::new()),
419                 locals: RefCell::new(NodeMap()),
420                 deferred_call_resolutions: RefCell::new(DefIdMap()),
421                 deferred_cast_checks: RefCell::new(Vec::new()),
422                 anon_types: RefCell::new(DefIdMap()),
423                 deferred_obligations: RefCell::new(Vec::new()),
424             })
425         })
426     }
427 }
428
429 impl<'a, 'gcx, 'tcx> Inherited<'a, 'gcx, 'tcx> {
430     fn normalize_associated_types_in<T>(&self,
431                                         span: Span,
432                                         body_id: ast::NodeId,
433                                         value: &T)
434                                         -> T
435         where T : TypeFoldable<'tcx>
436     {
437         assoc::normalize_associated_types_in(self,
438                                              &mut self.fulfillment_cx.borrow_mut(),
439                                              span,
440                                              body_id,
441                                              value)
442     }
443
444 }
445
446 struct CheckItemTypesVisitor<'a, 'tcx: 'a> { ccx: &'a CrateCtxt<'a, 'tcx> }
447 struct CheckItemBodiesVisitor<'a, 'tcx: 'a> { ccx: &'a CrateCtxt<'a, 'tcx> }
448
449 impl<'a, 'tcx> Visitor<'tcx> for CheckItemTypesVisitor<'a, 'tcx> {
450     fn visit_item(&mut self, i: &'tcx hir::Item) {
451         check_item_type(self.ccx, i);
452         intravisit::walk_item(self, i);
453     }
454
455     fn visit_ty(&mut self, t: &'tcx hir::Ty) {
456         match t.node {
457             hir::TyFixedLengthVec(_, ref expr) => {
458                 check_const_with_type(self.ccx, &expr, self.ccx.tcx.types.usize, expr.id);
459             }
460             _ => {}
461         }
462
463         intravisit::walk_ty(self, t);
464     }
465 }
466
467 impl<'a, 'tcx> Visitor<'tcx> for CheckItemBodiesVisitor<'a, 'tcx> {
468     fn visit_item(&mut self, i: &'tcx hir::Item) {
469         check_item_body(self.ccx, i);
470     }
471 }
472
473 pub fn check_wf_new(ccx: &CrateCtxt) -> CompileResult {
474     ccx.tcx.sess.track_errors(|| {
475         let mut visit = wfcheck::CheckTypeWellFormedVisitor::new(ccx);
476         ccx.tcx.visit_all_items_in_krate(DepNode::WfCheck, &mut visit);
477     })
478 }
479
480 pub fn check_item_types(ccx: &CrateCtxt) -> CompileResult {
481     ccx.tcx.sess.track_errors(|| {
482         let mut visit = CheckItemTypesVisitor { ccx: ccx };
483         ccx.tcx.visit_all_items_in_krate(DepNode::TypeckItemType, &mut visit);
484     })
485 }
486
487 pub fn check_item_bodies(ccx: &CrateCtxt) -> CompileResult {
488     ccx.tcx.sess.track_errors(|| {
489         let mut visit = CheckItemBodiesVisitor { ccx: ccx };
490         ccx.tcx.visit_all_items_in_krate(DepNode::TypeckItemBody, &mut visit);
491
492         // Process deferred obligations, now that all functions
493         // bodies have been fully inferred.
494         for (&item_id, obligations) in ccx.deferred_obligations.borrow().iter() {
495             // Use the same DepNode as for the body of the original function/item.
496             let def_id = ccx.tcx.map.local_def_id(item_id);
497             let _task = ccx.tcx.dep_graph.in_task(DepNode::TypeckItemBody(def_id));
498
499             let param_env = ParameterEnvironment::for_item(ccx.tcx, item_id);
500             ccx.tcx.infer_ctxt(None, Some(param_env),
501                                Reveal::NotSpecializable).enter(|infcx| {
502                 let mut fulfillment_cx = traits::FulfillmentContext::new();
503                 for obligation in obligations.iter().map(|o| o.to_obligation()) {
504                     fulfillment_cx.register_predicate_obligation(&infcx, obligation);
505                 }
506
507                 if let Err(errors) = fulfillment_cx.select_all_or_error(&infcx) {
508                     infcx.report_fulfillment_errors(&errors);
509                 }
510
511                 if let Err(errors) = fulfillment_cx.select_rfc1592_obligations(&infcx) {
512                     infcx.report_fulfillment_errors_as_warnings(&errors, item_id);
513                 }
514             });
515         }
516     })
517 }
518
519 pub fn check_drop_impls(ccx: &CrateCtxt) -> CompileResult {
520     ccx.tcx.sess.track_errors(|| {
521         let _task = ccx.tcx.dep_graph.in_task(DepNode::Dropck);
522         let drop_trait = match ccx.tcx.lang_items.drop_trait() {
523             Some(id) => ccx.tcx.lookup_trait_def(id), None => { return }
524         };
525         drop_trait.for_each_impl(ccx.tcx, |drop_impl_did| {
526             let _task = ccx.tcx.dep_graph.in_task(DepNode::DropckImpl(drop_impl_did));
527             if drop_impl_did.is_local() {
528                 match dropck::check_drop_impl(ccx, drop_impl_did) {
529                     Ok(()) => {}
530                     Err(()) => {
531                         assert!(ccx.tcx.sess.has_errors());
532                     }
533                 }
534             }
535         });
536     })
537 }
538
539 fn check_bare_fn<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
540                            decl: &'tcx hir::FnDecl,
541                            body: &'tcx hir::Block,
542                            fn_id: ast::NodeId) {
543     let raw_fty = ccx.tcx.lookup_item_type(ccx.tcx.map.local_def_id(fn_id)).ty;
544     let fn_ty = match raw_fty.sty {
545         ty::TyFnDef(_, _, f) => f,
546         _ => span_bug!(body.span, "check_bare_fn: function type expected")
547     };
548
549     ccx.inherited(fn_id).enter(|inh| {
550         // Compute the fty from point of view of inside fn.
551         let fn_scope = inh.tcx.region_maps.call_site_extent(fn_id, body.id);
552         let fn_sig =
553             fn_ty.sig.subst(inh.tcx, &inh.parameter_environment.free_substs);
554         let fn_sig =
555             inh.tcx.liberate_late_bound_regions(fn_scope, &fn_sig);
556         let fn_sig =
557             inh.normalize_associated_types_in(body.span, body.id, &fn_sig);
558
559         let fcx = check_fn(&inh, fn_ty.unsafety, fn_id, &fn_sig, decl, fn_id, body);
560
561         fcx.select_all_obligations_and_apply_defaults();
562         fcx.closure_analyze_fn(body);
563         fcx.select_obligations_where_possible();
564         fcx.check_casts();
565         fcx.select_all_obligations_or_error(); // Casts can introduce new obligations.
566
567         fcx.regionck_fn(fn_id, decl, body);
568         fcx.resolve_type_vars_in_fn(decl, body, fn_id);
569     });
570 }
571
572 struct GatherLocalsVisitor<'a, 'gcx: 'a+'tcx, 'tcx: 'a> {
573     fcx: &'a FnCtxt<'a, 'gcx, 'tcx>
574 }
575
576 impl<'a, 'gcx, 'tcx> GatherLocalsVisitor<'a, 'gcx, 'tcx> {
577     fn assign(&mut self, _span: Span, nid: ast::NodeId, ty_opt: Option<Ty<'tcx>>) -> Ty<'tcx> {
578         match ty_opt {
579             None => {
580                 // infer the variable's type
581                 let var_ty = self.fcx.next_ty_var();
582                 self.fcx.locals.borrow_mut().insert(nid, var_ty);
583                 var_ty
584             }
585             Some(typ) => {
586                 // take type that the user specified
587                 self.fcx.locals.borrow_mut().insert(nid, typ);
588                 typ
589             }
590         }
591     }
592 }
593
594 impl<'a, 'gcx, 'tcx> Visitor<'gcx> for GatherLocalsVisitor<'a, 'gcx, 'tcx> {
595     // Add explicitly-declared locals.
596     fn visit_local(&mut self, local: &'gcx hir::Local) {
597         let o_ty = match local.ty {
598             Some(ref ty) => Some(self.fcx.to_ty(&ty)),
599             None => None
600         };
601         self.assign(local.span, local.id, o_ty);
602         debug!("Local variable {:?} is assigned type {}",
603                local.pat,
604                self.fcx.ty_to_string(
605                    self.fcx.locals.borrow().get(&local.id).unwrap().clone()));
606         intravisit::walk_local(self, local);
607     }
608
609     // Add pattern bindings.
610     fn visit_pat(&mut self, p: &'gcx hir::Pat) {
611         if let PatKind::Binding(_, ref path1, _) = p.node {
612             let var_ty = self.assign(p.span, p.id, None);
613
614             self.fcx.require_type_is_sized(var_ty, p.span,
615                                            traits::VariableType(p.id));
616
617             debug!("Pattern binding {} is assigned to {} with type {:?}",
618                    path1.node,
619                    self.fcx.ty_to_string(
620                        self.fcx.locals.borrow().get(&p.id).unwrap().clone()),
621                    var_ty);
622         }
623         intravisit::walk_pat(self, p);
624     }
625
626     fn visit_block(&mut self, b: &'gcx hir::Block) {
627         // non-obvious: the `blk` variable maps to region lb, so
628         // we have to keep this up-to-date.  This
629         // is... unfortunate.  It'd be nice to not need this.
630         intravisit::walk_block(self, b);
631     }
632
633     // Since an expr occurs as part of the type fixed size arrays we
634     // need to record the type for that node
635     fn visit_ty(&mut self, t: &'gcx hir::Ty) {
636         match t.node {
637             hir::TyFixedLengthVec(ref ty, ref count_expr) => {
638                 self.visit_ty(&ty);
639                 self.fcx.check_expr_with_hint(&count_expr, self.fcx.tcx.types.usize);
640             }
641             hir::TyBareFn(ref function_declaration) => {
642                 intravisit::walk_fn_decl_nopat(self, &function_declaration.decl);
643                 walk_list!(self, visit_lifetime_def, &function_declaration.lifetimes);
644             }
645             _ => intravisit::walk_ty(self, t)
646         }
647     }
648
649     // Don't descend into the bodies of nested closures
650     fn visit_fn(&mut self, _: intravisit::FnKind<'gcx>, _: &'gcx hir::FnDecl,
651                 _: &'gcx hir::Block, _: Span, _: ast::NodeId) { }
652 }
653
654 /// Helper used by check_bare_fn and check_expr_fn. Does the grungy work of checking a function
655 /// body and returns the function context used for that purpose, since in the case of a fn item
656 /// there is still a bit more to do.
657 ///
658 /// * ...
659 /// * inherited: other fields inherited from the enclosing fn (if any)
660 fn check_fn<'a, 'gcx, 'tcx>(inherited: &'a Inherited<'a, 'gcx, 'tcx>,
661                             unsafety: hir::Unsafety,
662                             unsafety_id: ast::NodeId,
663                             fn_sig: &ty::FnSig<'tcx>,
664                             decl: &'gcx hir::FnDecl,
665                             fn_id: ast::NodeId,
666                             body: &'gcx hir::Block)
667                             -> FnCtxt<'a, 'gcx, 'tcx>
668 {
669     let mut fn_sig = fn_sig.clone();
670
671     debug!("check_fn(sig={:?}, fn_id={})", fn_sig, fn_id);
672
673     // Create the function context.  This is either derived from scratch or,
674     // in the case of function expressions, based on the outer context.
675     let mut fcx = FnCtxt::new(inherited, fn_sig.output, body.id);
676     *fcx.ps.borrow_mut() = UnsafetyState::function(unsafety, unsafety_id);
677
678     fcx.require_type_is_sized(fcx.ret_ty, decl.output.span(), traits::ReturnType);
679     fcx.ret_ty = fcx.instantiate_anon_types(&fcx.ret_ty);
680     fn_sig.output = fcx.ret_ty;
681
682     {
683         let mut visit = GatherLocalsVisitor { fcx: &fcx, };
684
685         // Add formal parameters.
686         for (arg_ty, input) in fn_sig.inputs.iter().zip(&decl.inputs) {
687             // The type of the argument must be well-formed.
688             //
689             // NB -- this is now checked in wfcheck, but that
690             // currently only results in warnings, so we issue an
691             // old-style WF obligation here so that we still get the
692             // errors that we used to get.
693             fcx.register_old_wf_obligation(arg_ty, input.ty.span, traits::MiscObligation);
694
695             // Create type variables for each argument.
696             pat_util::pat_bindings(&input.pat, |_bm, pat_id, sp, _path| {
697                 let var_ty = visit.assign(sp, pat_id, None);
698                 fcx.require_type_is_sized(var_ty, sp, traits::VariableType(pat_id));
699             });
700
701             // Check the pattern.
702             fcx.check_pat(&input.pat, arg_ty);
703             fcx.write_ty(input.id, arg_ty);
704         }
705
706         visit.visit_block(body);
707     }
708
709     inherited.tables.borrow_mut().liberated_fn_sigs.insert(fn_id, fn_sig);
710
711     // FIXME(aburka) do we need this special case? and should it be is_uninhabited?
712     let expected = if fcx.ret_ty.is_never() {
713         NoExpectation
714     } else {
715         ExpectHasType(fcx.ret_ty)
716     };
717     fcx.check_block_with_expected(body, expected);
718
719     fcx
720 }
721
722 pub fn check_struct(ccx: &CrateCtxt, id: ast::NodeId, span: Span) {
723     let tcx = ccx.tcx;
724
725     check_representable(tcx, span, id, "struct");
726
727     if tcx.lookup_simd(ccx.tcx.map.local_def_id(id)) {
728         check_simd(tcx, span, id);
729     }
730 }
731
732 pub fn check_item_type<'a,'tcx>(ccx: &CrateCtxt<'a,'tcx>, it: &'tcx hir::Item) {
733     debug!("check_item_type(it.id={}, it.name={})",
734            it.id,
735            ccx.tcx.item_path_str(ccx.tcx.map.local_def_id(it.id)));
736     let _indenter = indenter();
737     match it.node {
738       // Consts can play a role in type-checking, so they are included here.
739       hir::ItemStatic(_, _, ref e) |
740       hir::ItemConst(_, ref e) => check_const(ccx, &e, it.id),
741       hir::ItemEnum(ref enum_definition, _) => {
742         check_enum_variants(ccx,
743                             it.span,
744                             &enum_definition.variants,
745                             it.id);
746       }
747       hir::ItemFn(..) => {} // entirely within check_item_body
748       hir::ItemImpl(_, _, _, _, _, ref impl_items) => {
749           debug!("ItemImpl {} with id {}", it.name, it.id);
750           let impl_def_id = ccx.tcx.map.local_def_id(it.id);
751           match ccx.tcx.impl_trait_ref(impl_def_id) {
752               Some(impl_trait_ref) => {
753                   check_impl_items_against_trait(ccx,
754                                                  it.span,
755                                                  impl_def_id,
756                                                  &impl_trait_ref,
757                                                  impl_items);
758                   let trait_def_id = impl_trait_ref.def_id;
759                   check_on_unimplemented(ccx, trait_def_id, it);
760               }
761               None => { }
762           }
763       }
764       hir::ItemTrait(..) => {
765         let def_id = ccx.tcx.map.local_def_id(it.id);
766         check_on_unimplemented(ccx, def_id, it);
767       }
768       hir::ItemStruct(..) => {
769         check_struct(ccx, it.id, it.span);
770       }
771       hir::ItemTy(_, ref generics) => {
772         let pty_ty = ccx.tcx.node_id_to_type(it.id);
773         check_bounds_are_used(ccx, generics, pty_ty);
774       }
775       hir::ItemForeignMod(ref m) => {
776         if m.abi == Abi::RustIntrinsic {
777             for item in &m.items {
778                 intrinsic::check_intrinsic_type(ccx, item);
779             }
780         } else if m.abi == Abi::PlatformIntrinsic {
781             for item in &m.items {
782                 intrinsic::check_platform_intrinsic_type(ccx, item);
783             }
784         } else {
785             for item in &m.items {
786                 let pty = ccx.tcx.lookup_item_type(ccx.tcx.map.local_def_id(item.id));
787                 if !pty.generics.types.is_empty() {
788                     let mut err = struct_span_err!(ccx.tcx.sess, item.span, E0044,
789                         "foreign items may not have type parameters");
790                     span_help!(&mut err, item.span,
791                         "consider using specialization instead of \
792                         type parameters");
793                     err.emit();
794                 }
795
796                 if let hir::ForeignItemFn(ref fn_decl, _) = item.node {
797                     require_c_abi_if_variadic(ccx.tcx, fn_decl, m.abi, item.span);
798                 }
799             }
800         }
801       }
802       _ => {/* nothing to do */ }
803     }
804 }
805
806 pub fn check_item_body<'a,'tcx>(ccx: &CrateCtxt<'a,'tcx>, it: &'tcx hir::Item) {
807     debug!("check_item_body(it.id={}, it.name={})",
808            it.id,
809            ccx.tcx.item_path_str(ccx.tcx.map.local_def_id(it.id)));
810     let _indenter = indenter();
811     match it.node {
812       hir::ItemFn(ref decl, _, _, _, _, ref body) => {
813         check_bare_fn(ccx, &decl, &body, it.id);
814       }
815       hir::ItemImpl(_, _, _, _, _, ref impl_items) => {
816         debug!("ItemImpl {} with id {}", it.name, it.id);
817
818         for impl_item in impl_items {
819             match impl_item.node {
820                 hir::ImplItemKind::Const(_, ref expr) => {
821                     check_const(ccx, &expr, impl_item.id)
822                 }
823                 hir::ImplItemKind::Method(ref sig, ref body) => {
824                     check_bare_fn(ccx, &sig.decl, body, impl_item.id);
825                 }
826                 hir::ImplItemKind::Type(_) => {
827                     // Nothing to do here.
828                 }
829             }
830         }
831       }
832       hir::ItemTrait(_, _, _, ref trait_items) => {
833         for trait_item in trait_items {
834             match trait_item.node {
835                 hir::ConstTraitItem(_, Some(ref expr)) => {
836                     check_const(ccx, &expr, trait_item.id)
837                 }
838                 hir::MethodTraitItem(ref sig, Some(ref body)) => {
839                     check_trait_fn_not_const(ccx, trait_item.span, sig.constness);
840
841                     check_bare_fn(ccx, &sig.decl, body, trait_item.id);
842                 }
843                 hir::MethodTraitItem(ref sig, None) => {
844                     check_trait_fn_not_const(ccx, trait_item.span, sig.constness);
845                 }
846                 hir::ConstTraitItem(_, None) |
847                 hir::TypeTraitItem(..) => {
848                     // Nothing to do.
849                 }
850             }
851         }
852       }
853       _ => {/* nothing to do */ }
854     }
855 }
856
857 fn check_trait_fn_not_const<'a,'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
858                                      span: Span,
859                                      constness: hir::Constness)
860 {
861     match constness {
862         hir::Constness::NotConst => {
863             // good
864         }
865         hir::Constness::Const => {
866             struct_span_err!(ccx.tcx.sess, span, E0379, "trait fns cannot be declared const")
867                 .span_label(span, &format!("trait fns cannot be const"))
868                 .emit()
869         }
870     }
871 }
872
873 fn check_on_unimplemented<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
874                                     def_id: DefId,
875                                     item: &hir::Item) {
876     let generics = ccx.tcx.lookup_generics(def_id);
877     if let Some(ref attr) = item.attrs.iter().find(|a| {
878         a.check_name("rustc_on_unimplemented")
879     }) {
880         if let Some(ref istring) = attr.value_str() {
881             let parser = Parser::new(&istring);
882             let types = &generics.types;
883             for token in parser {
884                 match token {
885                     Piece::String(_) => (), // Normal string, no need to check it
886                     Piece::NextArgument(a) => match a.position {
887                         // `{Self}` is allowed
888                         Position::ArgumentNamed(s) if s == "Self" => (),
889                         // So is `{A}` if A is a type parameter
890                         Position::ArgumentNamed(s) => match types.iter().find(|t| {
891                             t.name.as_str() == s
892                         }) {
893                             Some(_) => (),
894                             None => {
895                                 let name = ccx.tcx.item_name(def_id);
896                                 span_err!(ccx.tcx.sess, attr.span, E0230,
897                                                  "there is no type parameter \
898                                                           {} on trait {}",
899                                                            s, name);
900                             }
901                         },
902                         // `{:1}` and `{}` are not to be used
903                         Position::ArgumentIs(_) => {
904                             span_err!(ccx.tcx.sess, attr.span, E0231,
905                                                   "only named substitution \
906                                                    parameters are allowed");
907                         }
908                     }
909                 }
910             }
911         } else {
912             struct_span_err!(
913                 ccx.tcx.sess, attr.span, E0232,
914                 "this attribute must have a value")
915                 .span_label(attr.span, &format!("attribute requires a value"))
916                 .note(&format!("eg `#[rustc_on_unimplemented = \"foo\"]`"))
917                 .emit();
918         }
919     }
920 }
921
922 fn report_forbidden_specialization<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
923                                              impl_item: &hir::ImplItem,
924                                              parent_impl: DefId)
925 {
926     let mut err = struct_span_err!(
927         tcx.sess, impl_item.span, E0520,
928         "item `{}` is provided by an `impl` that specializes \
929          another, but the item in the parent `impl` is not \
930          marked `default` and so it cannot be specialized.",
931         impl_item.name);
932
933     match tcx.span_of_impl(parent_impl) {
934         Ok(span) => {
935             err.span_note(span, "parent implementation is here:");
936         }
937         Err(cname) => {
938             err.note(&format!("parent implementation is in crate `{}`", cname));
939         }
940     }
941
942     err.emit();
943 }
944
945 fn check_specialization_validity<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
946                                            trait_def: &ty::TraitDef<'tcx>,
947                                            impl_id: DefId,
948                                            impl_item: &hir::ImplItem)
949 {
950     let ancestors = trait_def.ancestors(impl_id);
951
952     let parent = match impl_item.node {
953         hir::ImplItemKind::Const(..) => {
954             ancestors.const_defs(tcx, impl_item.name).skip(1).next()
955                 .map(|node_item| node_item.map(|parent| parent.defaultness))
956         }
957         hir::ImplItemKind::Method(..) => {
958             ancestors.fn_defs(tcx, impl_item.name).skip(1).next()
959                 .map(|node_item| node_item.map(|parent| parent.defaultness))
960
961         }
962         hir::ImplItemKind::Type(_) => {
963             ancestors.type_defs(tcx, impl_item.name).skip(1).next()
964                 .map(|node_item| node_item.map(|parent| parent.defaultness))
965         }
966     };
967
968     if let Some(parent) = parent {
969         if parent.item.is_final() {
970             report_forbidden_specialization(tcx, impl_item, parent.node.def_id());
971         }
972     }
973
974 }
975
976 fn check_impl_items_against_trait<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
977                                             impl_span: Span,
978                                             impl_id: DefId,
979                                             impl_trait_ref: &ty::TraitRef<'tcx>,
980                                             impl_items: &[hir::ImplItem]) {
981     // If the trait reference itself is erroneous (so the compilation is going
982     // to fail), skip checking the items here -- the `impl_item` table in `tcx`
983     // isn't populated for such impls.
984     if impl_trait_ref.references_error() { return; }
985
986     // Locate trait definition and items
987     let tcx = ccx.tcx;
988     let trait_def = tcx.lookup_trait_def(impl_trait_ref.def_id);
989     let trait_items = tcx.trait_items(impl_trait_ref.def_id);
990     let mut overridden_associated_type = None;
991
992     // Check existing impl methods to see if they are both present in trait
993     // and compatible with trait signature
994     for impl_item in impl_items {
995         let ty_impl_item = tcx.impl_or_trait_item(tcx.map.local_def_id(impl_item.id));
996         let ty_trait_item = trait_items.iter()
997             .find(|ac| ac.name() == ty_impl_item.name());
998
999         // Check that impl definition matches trait definition
1000         if let Some(ty_trait_item) = ty_trait_item {
1001             match impl_item.node {
1002                 hir::ImplItemKind::Const(..) => {
1003                     let impl_const = match ty_impl_item {
1004                         ty::ConstTraitItem(ref cti) => cti,
1005                         _ => span_bug!(impl_item.span, "non-const impl-item for const")
1006                     };
1007
1008                     // Find associated const definition.
1009                     if let &ty::ConstTraitItem(ref trait_const) = ty_trait_item {
1010                         compare_const_impl(ccx,
1011                                            &impl_const,
1012                                            impl_item.span,
1013                                            trait_const,
1014                                            &impl_trait_ref);
1015                     } else {
1016                          let mut err = struct_span_err!(tcx.sess, impl_item.span, E0323,
1017                                   "item `{}` is an associated const, \
1018                                   which doesn't match its trait `{:?}`",
1019                                   impl_const.name,
1020                                   impl_trait_ref);
1021                          err.span_label(impl_item.span, &format!("does not match trait"));
1022                          // We can only get the spans from local trait definition
1023                          // Same for E0324 and E0325
1024                          if let Some(trait_span) = tcx.map.span_if_local(ty_trait_item.def_id()) {
1025                             err.span_label(trait_span, &format!("item in trait"));
1026                          }
1027                          err.emit()
1028                     }
1029                 }
1030                 hir::ImplItemKind::Method(ref sig, ref body) => {
1031                     check_trait_fn_not_const(ccx, impl_item.span, sig.constness);
1032
1033                     let impl_method = match ty_impl_item {
1034                         ty::MethodTraitItem(ref mti) => mti,
1035                         _ => span_bug!(impl_item.span, "non-method impl-item for method")
1036                     };
1037
1038                     if let &ty::MethodTraitItem(ref trait_method) = ty_trait_item {
1039                         compare_impl_method(ccx,
1040                                             &impl_method,
1041                                             impl_item.span,
1042                                             body.id,
1043                                             &trait_method,
1044                                             &impl_trait_ref);
1045                     } else {
1046                         let mut err = struct_span_err!(tcx.sess, impl_item.span, E0324,
1047                                   "item `{}` is an associated method, \
1048                                   which doesn't match its trait `{:?}`",
1049                                   impl_method.name,
1050                                   impl_trait_ref);
1051                          err.span_label(impl_item.span, &format!("does not match trait"));
1052                          if let Some(trait_span) = tcx.map.span_if_local(ty_trait_item.def_id()) {
1053                             err.span_label(trait_span, &format!("item in trait"));
1054                          }
1055                          err.emit()
1056                     }
1057                 }
1058                 hir::ImplItemKind::Type(_) => {
1059                     let impl_type = match ty_impl_item {
1060                         ty::TypeTraitItem(ref tti) => tti,
1061                         _ => span_bug!(impl_item.span, "non-type impl-item for type")
1062                     };
1063
1064                     if let &ty::TypeTraitItem(ref at) = ty_trait_item {
1065                         if let Some(_) = at.ty {
1066                             overridden_associated_type = Some(impl_item);
1067                         }
1068                     } else {
1069                         let mut err = struct_span_err!(tcx.sess, impl_item.span, E0325,
1070                                   "item `{}` is an associated type, \
1071                                   which doesn't match its trait `{:?}`",
1072                                   impl_type.name,
1073                                   impl_trait_ref);
1074                          err.span_label(impl_item.span, &format!("does not match trait"));
1075                          if let Some(trait_span) = tcx.map.span_if_local(ty_trait_item.def_id()) {
1076                             err.span_label(trait_span, &format!("item in trait"));
1077                          }
1078                          err.emit()
1079                     }
1080                 }
1081             }
1082         }
1083
1084         check_specialization_validity(tcx, trait_def, impl_id, impl_item);
1085     }
1086
1087     // Check for missing items from trait
1088     let provided_methods = tcx.provided_trait_methods(impl_trait_ref.def_id);
1089     let mut missing_items = Vec::new();
1090     let mut invalidated_items = Vec::new();
1091     let associated_type_overridden = overridden_associated_type.is_some();
1092     for trait_item in trait_items.iter() {
1093         let is_implemented;
1094         let is_provided;
1095
1096         match *trait_item {
1097             ty::ConstTraitItem(ref associated_const) => {
1098                 is_provided = associated_const.has_value;
1099                 is_implemented = impl_items.iter().any(|ii| {
1100                     match ii.node {
1101                         hir::ImplItemKind::Const(..) => {
1102                             ii.name == associated_const.name
1103                         }
1104                         _ => false,
1105                     }
1106                 });
1107             }
1108             ty::MethodTraitItem(ref trait_method) => {
1109                 is_provided = provided_methods.iter().any(|m| m.name == trait_method.name);
1110                 is_implemented = trait_def.ancestors(impl_id)
1111                     .fn_defs(tcx, trait_method.name)
1112                     .next()
1113                     .map(|node_item| !node_item.node.is_from_trait())
1114                     .unwrap_or(false);
1115             }
1116             ty::TypeTraitItem(ref trait_assoc_ty) => {
1117                 is_provided = trait_assoc_ty.ty.is_some();
1118                 is_implemented = trait_def.ancestors(impl_id)
1119                     .type_defs(tcx, trait_assoc_ty.name)
1120                     .next()
1121                     .map(|node_item| !node_item.node.is_from_trait())
1122                     .unwrap_or(false);
1123             }
1124         }
1125
1126         if !is_implemented {
1127             if !is_provided {
1128                 missing_items.push(trait_item.name());
1129             } else if associated_type_overridden {
1130                 invalidated_items.push(trait_item.name());
1131             }
1132         }
1133     }
1134
1135     if !missing_items.is_empty() {
1136         struct_span_err!(tcx.sess, impl_span, E0046,
1137             "not all trait items implemented, missing: `{}`",
1138             missing_items.iter()
1139                   .map(|name| name.to_string())
1140                   .collect::<Vec<_>>().join("`, `"))
1141             .span_label(impl_span, &format!("missing `{}` in implementation",
1142                 missing_items.iter()
1143                     .map(|name| name.to_string())
1144                     .collect::<Vec<_>>().join("`, `"))
1145             ).emit();
1146     }
1147
1148     if !invalidated_items.is_empty() {
1149         let invalidator = overridden_associated_type.unwrap();
1150         span_err!(tcx.sess, invalidator.span, E0399,
1151                   "the following trait items need to be reimplemented \
1152                    as `{}` was overridden: `{}`",
1153                   invalidator.name,
1154                   invalidated_items.iter()
1155                                    .map(|name| name.to_string())
1156                                    .collect::<Vec<_>>().join("`, `"))
1157     }
1158 }
1159
1160 /// Checks a constant with a given type.
1161 fn check_const_with_type<'a, 'tcx>(ccx: &'a CrateCtxt<'a, 'tcx>,
1162                                    expr: &'tcx hir::Expr,
1163                                    expected_type: Ty<'tcx>,
1164                                    id: ast::NodeId) {
1165     ccx.inherited(id).enter(|inh| {
1166         let fcx = FnCtxt::new(&inh, expected_type, expr.id);
1167         fcx.require_type_is_sized(expected_type, expr.span, traits::ConstSized);
1168
1169         // Gather locals in statics (because of block expressions).
1170         // This is technically unnecessary because locals in static items are forbidden,
1171         // but prevents type checking from blowing up before const checking can properly
1172         // emit an error.
1173         GatherLocalsVisitor { fcx: &fcx }.visit_expr(expr);
1174
1175         fcx.check_expr_coercable_to_type(expr, expected_type);
1176
1177         fcx.select_all_obligations_and_apply_defaults();
1178         fcx.closure_analyze_const(expr);
1179         fcx.select_obligations_where_possible();
1180         fcx.check_casts();
1181         fcx.select_all_obligations_or_error();
1182
1183         fcx.regionck_expr(expr);
1184         fcx.resolve_type_vars_in_expr(expr, id);
1185     });
1186 }
1187
1188 fn check_const<'a, 'tcx>(ccx: &CrateCtxt<'a,'tcx>,
1189                          expr: &'tcx hir::Expr,
1190                          id: ast::NodeId) {
1191     let decl_ty = ccx.tcx.lookup_item_type(ccx.tcx.map.local_def_id(id)).ty;
1192     check_const_with_type(ccx, expr, decl_ty, id);
1193 }
1194
1195 /// Checks whether a type can be represented in memory. In particular, it
1196 /// identifies types that contain themselves without indirection through a
1197 /// pointer, which would mean their size is unbounded.
1198 pub fn check_representable<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>,
1199                                      sp: Span,
1200                                      item_id: ast::NodeId,
1201                                      _designation: &str) -> bool {
1202     let rty = tcx.node_id_to_type(item_id);
1203
1204     // Check that it is possible to represent this type. This call identifies
1205     // (1) types that contain themselves and (2) types that contain a different
1206     // recursive type. It is only necessary to throw an error on those that
1207     // contain themselves. For case 2, there must be an inner type that will be
1208     // caught by case 1.
1209     match rty.is_representable(tcx, sp) {
1210         Representability::SelfRecursive => {
1211             let item_def_id = tcx.map.local_def_id(item_id);
1212             tcx.recursive_type_with_infinite_size_error(item_def_id).emit();
1213             return false
1214         }
1215         Representability::Representable | Representability::ContainsRecursive => (),
1216     }
1217     return true
1218 }
1219
1220 pub fn check_simd<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, sp: Span, id: ast::NodeId) {
1221     let t = tcx.node_id_to_type(id);
1222     match t.sty {
1223         ty::TyStruct(def, substs) => {
1224             let fields = &def.struct_variant().fields;
1225             if fields.is_empty() {
1226                 span_err!(tcx.sess, sp, E0075, "SIMD vector cannot be empty");
1227                 return;
1228             }
1229             let e = fields[0].ty(tcx, substs);
1230             if !fields.iter().all(|f| f.ty(tcx, substs) == e) {
1231                 span_err!(tcx.sess, sp, E0076, "SIMD vector should be homogeneous");
1232                 return;
1233             }
1234             match e.sty {
1235                 ty::TyParam(_) => { /* struct<T>(T, T, T, T) is ok */ }
1236                 _ if e.is_machine()  => { /* struct(u8, u8, u8, u8) is ok */ }
1237                 _ => {
1238                     span_err!(tcx.sess, sp, E0077,
1239                               "SIMD vector element type should be machine type");
1240                     return;
1241                 }
1242             }
1243         }
1244         _ => ()
1245     }
1246 }
1247
1248 #[allow(trivial_numeric_casts)]
1249 pub fn check_enum_variants<'a,'tcx>(ccx: &CrateCtxt<'a,'tcx>,
1250                                     sp: Span,
1251                                     vs: &'tcx [hir::Variant],
1252                                     id: ast::NodeId) {
1253     let def_id = ccx.tcx.map.local_def_id(id);
1254     let hint = *ccx.tcx.lookup_repr_hints(def_id).get(0).unwrap_or(&attr::ReprAny);
1255
1256     if hint != attr::ReprAny && vs.is_empty() {
1257         struct_span_err!(
1258             ccx.tcx.sess, sp, E0084,
1259             "unsupported representation for zero-variant enum")
1260             .span_label(sp, &format!("unsupported enum representation"))
1261             .emit();
1262     }
1263
1264     let repr_type_ty = ccx.tcx.enum_repr_type(Some(&hint)).to_ty(ccx.tcx);
1265     for v in vs {
1266         if let Some(ref e) = v.node.disr_expr {
1267             check_const_with_type(ccx, e, repr_type_ty, e.id);
1268         }
1269     }
1270
1271     let def_id = ccx.tcx.map.local_def_id(id);
1272
1273     let variants = &ccx.tcx.lookup_adt_def(def_id).variants;
1274     let mut disr_vals: Vec<ty::Disr> = Vec::new();
1275     for (v, variant) in vs.iter().zip(variants.iter()) {
1276         let current_disr_val = variant.disr_val;
1277
1278         // Check for duplicate discriminant values
1279         if let Some(i) = disr_vals.iter().position(|&x| x == current_disr_val) {
1280             let variant_i_node_id = ccx.tcx.map.as_local_node_id(variants[i].did).unwrap();
1281             let variant_i = ccx.tcx.map.expect_variant(variant_i_node_id);
1282             let i_span = match variant_i.node.disr_expr {
1283                 Some(ref expr) => expr.span,
1284                 None => ccx.tcx.map.span(variant_i_node_id)
1285             };
1286             let span = match v.node.disr_expr {
1287                 Some(ref expr) => expr.span,
1288                 None => v.span
1289             };
1290             struct_span_err!(ccx.tcx.sess, span, E0081,
1291                              "discriminant value `{}` already exists", disr_vals[i])
1292                 .span_label(i_span, &format!("first use of `{}`", disr_vals[i]))
1293                 .span_label(span , &format!("enum already has `{}`", disr_vals[i]))
1294                 .emit();
1295         }
1296         disr_vals.push(current_disr_val);
1297     }
1298
1299     check_representable(ccx.tcx, sp, id, "enum");
1300 }
1301
1302 impl<'a, 'gcx, 'tcx> AstConv<'gcx, 'tcx> for FnCtxt<'a, 'gcx, 'tcx> {
1303     fn tcx<'b>(&'b self) -> TyCtxt<'b, 'gcx, 'tcx> { self.tcx }
1304
1305     fn ast_ty_to_ty_cache(&self) -> &RefCell<NodeMap<Ty<'tcx>>> {
1306         &self.ast_ty_to_ty_cache
1307     }
1308
1309     fn get_generics(&self, _: Span, id: DefId)
1310                     -> Result<&'tcx ty::Generics<'tcx>, ErrorReported>
1311     {
1312         Ok(self.tcx().lookup_generics(id))
1313     }
1314
1315     fn get_item_type_scheme(&self, _: Span, id: DefId)
1316                             -> Result<ty::TypeScheme<'tcx>, ErrorReported>
1317     {
1318         Ok(self.tcx().lookup_item_type(id))
1319     }
1320
1321     fn get_trait_def(&self, _: Span, id: DefId)
1322                      -> Result<&'tcx ty::TraitDef<'tcx>, ErrorReported>
1323     {
1324         Ok(self.tcx().lookup_trait_def(id))
1325     }
1326
1327     fn ensure_super_predicates(&self, _: Span, _: DefId) -> Result<(), ErrorReported> {
1328         // all super predicates are ensured during collect pass
1329         Ok(())
1330     }
1331
1332     fn get_free_substs(&self) -> Option<&Substs<'tcx>> {
1333         Some(&self.parameter_environment.free_substs)
1334     }
1335
1336     fn get_type_parameter_bounds(&self,
1337                                  _: Span,
1338                                  node_id: ast::NodeId)
1339                                  -> Result<Vec<ty::PolyTraitRef<'tcx>>, ErrorReported>
1340     {
1341         let def = self.tcx.type_parameter_def(node_id);
1342         let r = self.parameter_environment
1343                                   .caller_bounds
1344                                   .iter()
1345                                   .filter_map(|predicate| {
1346                                       match *predicate {
1347                                           ty::Predicate::Trait(ref data) => {
1348                                               if data.0.self_ty().is_param(def.index) {
1349                                                   Some(data.to_poly_trait_ref())
1350                                               } else {
1351                                                   None
1352                                               }
1353                                           }
1354                                           _ => {
1355                                               None
1356                                           }
1357                                       }
1358                                   })
1359                                   .collect();
1360         Ok(r)
1361     }
1362
1363     fn trait_defines_associated_type_named(&self,
1364                                            trait_def_id: DefId,
1365                                            assoc_name: ast::Name)
1366                                            -> bool
1367     {
1368         let trait_def = self.tcx().lookup_trait_def(trait_def_id);
1369         trait_def.associated_type_names.contains(&assoc_name)
1370     }
1371
1372     fn ty_infer(&self, _span: Span) -> Ty<'tcx> {
1373         self.next_ty_var()
1374     }
1375
1376     fn ty_infer_for_def(&self,
1377                         ty_param_def: &ty::TypeParameterDef<'tcx>,
1378                         substs: &Substs<'tcx>,
1379                         span: Span) -> Ty<'tcx> {
1380         self.type_var_for_def(span, ty_param_def, substs)
1381     }
1382
1383     fn projected_ty_from_poly_trait_ref(&self,
1384                                         span: Span,
1385                                         poly_trait_ref: ty::PolyTraitRef<'tcx>,
1386                                         item_name: ast::Name)
1387                                         -> Ty<'tcx>
1388     {
1389         let (trait_ref, _) =
1390             self.replace_late_bound_regions_with_fresh_var(
1391                 span,
1392                 infer::LateBoundRegionConversionTime::AssocTypeProjection(item_name),
1393                 &poly_trait_ref);
1394
1395         self.normalize_associated_type(span, trait_ref, item_name)
1396     }
1397
1398     fn projected_ty(&self,
1399                     span: Span,
1400                     trait_ref: ty::TraitRef<'tcx>,
1401                     item_name: ast::Name)
1402                     -> Ty<'tcx>
1403     {
1404         self.normalize_associated_type(span, trait_ref, item_name)
1405     }
1406
1407     fn set_tainted_by_errors(&self) {
1408         self.infcx.set_tainted_by_errors()
1409     }
1410 }
1411
1412 impl<'a, 'gcx, 'tcx> RegionScope for FnCtxt<'a, 'gcx, 'tcx> {
1413     fn object_lifetime_default(&self, span: Span) -> Option<ty::Region> {
1414         Some(self.base_object_lifetime_default(span))
1415     }
1416
1417     fn base_object_lifetime_default(&self, span: Span) -> ty::Region {
1418         // RFC #599 specifies that object lifetime defaults take
1419         // precedence over other defaults. But within a fn body we
1420         // don't have a *default* region, rather we use inference to
1421         // find the *correct* region, which is strictly more general
1422         // (and anyway, within a fn body the right region may not even
1423         // be something the user can write explicitly, since it might
1424         // be some expression).
1425         *self.next_region_var(infer::MiscVariable(span))
1426     }
1427
1428     fn anon_regions(&self, span: Span, count: usize)
1429                     -> Result<Vec<ty::Region>, Option<Vec<ElisionFailureInfo>>> {
1430         Ok((0..count).map(|_| {
1431             *self.next_region_var(infer::MiscVariable(span))
1432         }).collect())
1433     }
1434 }
1435
1436 /// Controls whether the arguments are tupled. This is used for the call
1437 /// operator.
1438 ///
1439 /// Tupling means that all call-side arguments are packed into a tuple and
1440 /// passed as a single parameter. For example, if tupling is enabled, this
1441 /// function:
1442 ///
1443 ///     fn f(x: (isize, isize))
1444 ///
1445 /// Can be called as:
1446 ///
1447 ///     f(1, 2);
1448 ///
1449 /// Instead of:
1450 ///
1451 ///     f((1, 2));
1452 #[derive(Clone, Eq, PartialEq)]
1453 enum TupleArgumentsFlag {
1454     DontTupleArguments,
1455     TupleArguments,
1456 }
1457
1458 impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
1459     pub fn new(inh: &'a Inherited<'a, 'gcx, 'tcx>,
1460                rty: Ty<'tcx>,
1461                body_id: ast::NodeId)
1462                -> FnCtxt<'a, 'gcx, 'tcx> {
1463         FnCtxt {
1464             ast_ty_to_ty_cache: RefCell::new(NodeMap()),
1465             body_id: body_id,
1466             writeback_errors: Cell::new(false),
1467             err_count_on_creation: inh.tcx.sess.err_count(),
1468             ret_ty: rty,
1469             ps: RefCell::new(UnsafetyState::function(hir::Unsafety::Normal, 0)),
1470             inh: inh,
1471         }
1472     }
1473
1474     pub fn param_env(&self) -> &ty::ParameterEnvironment<'tcx> {
1475         &self.parameter_environment
1476     }
1477
1478     pub fn sess(&self) -> &Session {
1479         &self.tcx.sess
1480     }
1481
1482     pub fn err_count_since_creation(&self) -> usize {
1483         self.tcx.sess.err_count() - self.err_count_on_creation
1484     }
1485
1486     /// Resolves type variables in `ty` if possible. Unlike the infcx
1487     /// version (resolve_type_vars_if_possible), this version will
1488     /// also select obligations if it seems useful, in an effort
1489     /// to get more type information.
1490     fn resolve_type_vars_with_obligations(&self, mut ty: Ty<'tcx>) -> Ty<'tcx> {
1491         debug!("resolve_type_vars_with_obligations(ty={:?})", ty);
1492
1493         // No TyInfer()? Nothing needs doing.
1494         if !ty.has_infer_types() {
1495             debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
1496             return ty;
1497         }
1498
1499         // If `ty` is a type variable, see whether we already know what it is.
1500         ty = self.resolve_type_vars_if_possible(&ty);
1501         if !ty.has_infer_types() {
1502             debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
1503             return ty;
1504         }
1505
1506         // If not, try resolving pending obligations as much as
1507         // possible. This can help substantially when there are
1508         // indirect dependencies that don't seem worth tracking
1509         // precisely.
1510         self.select_obligations_where_possible();
1511         ty = self.resolve_type_vars_if_possible(&ty);
1512
1513         debug!("resolve_type_vars_with_obligations: ty={:?}", ty);
1514         ty
1515     }
1516
1517     fn record_deferred_call_resolution(&self,
1518                                        closure_def_id: DefId,
1519                                        r: DeferredCallResolutionHandler<'gcx, 'tcx>) {
1520         let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
1521         deferred_call_resolutions.entry(closure_def_id).or_insert(vec![]).push(r);
1522     }
1523
1524     fn remove_deferred_call_resolutions(&self,
1525                                         closure_def_id: DefId)
1526                                         -> Vec<DeferredCallResolutionHandler<'gcx, 'tcx>>
1527     {
1528         let mut deferred_call_resolutions = self.deferred_call_resolutions.borrow_mut();
1529         deferred_call_resolutions.remove(&closure_def_id).unwrap_or(Vec::new())
1530     }
1531
1532     pub fn tag(&self) -> String {
1533         let self_ptr: *const FnCtxt = self;
1534         format!("{:?}", self_ptr)
1535     }
1536
1537     pub fn local_ty(&self, span: Span, nid: ast::NodeId) -> Ty<'tcx> {
1538         match self.locals.borrow().get(&nid) {
1539             Some(&t) => t,
1540             None => {
1541                 span_err!(self.tcx.sess, span, E0513,
1542                           "no type for local variable {}",
1543                           nid);
1544                 self.tcx.types.err
1545             }
1546         }
1547     }
1548
1549     #[inline]
1550     pub fn write_ty(&self, node_id: ast::NodeId, ty: Ty<'tcx>) {
1551         debug!("write_ty({}, {:?}) in fcx {}",
1552                node_id, ty, self.tag());
1553         self.tables.borrow_mut().node_types.insert(node_id, ty);
1554
1555         // Add adjustments to !-expressions
1556         if ty.is_never() {
1557             if let Some(hir::map::NodeExpr(_)) = self.tcx.map.find(node_id) {
1558                 let adj = adjustment::AdjustNeverToAny(self.next_diverging_ty_var());
1559                 self.write_adjustment(node_id, adj);
1560             }
1561         }
1562     }
1563
1564     pub fn write_substs(&self, node_id: ast::NodeId, substs: ty::ItemSubsts<'tcx>) {
1565         if !substs.substs.is_noop() {
1566             debug!("write_substs({}, {:?}) in fcx {}",
1567                    node_id,
1568                    substs,
1569                    self.tag());
1570
1571             self.tables.borrow_mut().item_substs.insert(node_id, substs);
1572         }
1573     }
1574
1575     pub fn write_autoderef_adjustment(&self,
1576                                       node_id: ast::NodeId,
1577                                       derefs: usize) {
1578         self.write_adjustment(
1579             node_id,
1580             adjustment::AdjustDerefRef(adjustment::AutoDerefRef {
1581                 autoderefs: derefs,
1582                 autoref: None,
1583                 unsize: None
1584             })
1585         );
1586     }
1587
1588     pub fn write_adjustment(&self,
1589                             node_id: ast::NodeId,
1590                             adj: adjustment::AutoAdjustment<'tcx>) {
1591         debug!("write_adjustment(node_id={}, adj={:?})", node_id, adj);
1592
1593         if adj.is_identity() {
1594             return;
1595         }
1596
1597         self.tables.borrow_mut().adjustments.insert(node_id, adj);
1598     }
1599
1600     /// Basically whenever we are converting from a type scheme into
1601     /// the fn body space, we always want to normalize associated
1602     /// types as well. This function combines the two.
1603     fn instantiate_type_scheme<T>(&self,
1604                                   span: Span,
1605                                   substs: &Substs<'tcx>,
1606                                   value: &T)
1607                                   -> T
1608         where T : TypeFoldable<'tcx>
1609     {
1610         let value = value.subst(self.tcx, substs);
1611         let result = self.normalize_associated_types_in(span, &value);
1612         debug!("instantiate_type_scheme(value={:?}, substs={:?}) = {:?}",
1613                value,
1614                substs,
1615                result);
1616         result
1617     }
1618
1619     /// As `instantiate_type_scheme`, but for the bounds found in a
1620     /// generic type scheme.
1621     fn instantiate_bounds(&self,
1622                           span: Span,
1623                           substs: &Substs<'tcx>,
1624                           bounds: &ty::GenericPredicates<'tcx>)
1625                           -> ty::InstantiatedPredicates<'tcx>
1626     {
1627         let result = bounds.instantiate(self.tcx, substs);
1628         let result = self.normalize_associated_types_in(span, &result.predicates);
1629         debug!("instantiate_bounds(bounds={:?}, substs={:?}) = {:?}",
1630                bounds,
1631                substs,
1632                result);
1633         ty::InstantiatedPredicates {
1634             predicates: result
1635         }
1636     }
1637
1638     /// Replace all anonymized types with fresh inference variables
1639     /// and record them for writeback.
1640     fn instantiate_anon_types<T: TypeFoldable<'tcx>>(&self, value: &T) -> T {
1641         value.fold_with(&mut BottomUpFolder { tcx: self.tcx, fldop: |ty| {
1642             if let ty::TyAnon(def_id, substs) = ty.sty {
1643                 // Use the same type variable if the exact same TyAnon appears more
1644                 // than once in the return type (e.g. if it's pased to a type alias).
1645                 if let Some(ty_var) = self.anon_types.borrow().get(&def_id) {
1646                     return ty_var;
1647                 }
1648                 let ty_var = self.next_ty_var();
1649                 self.anon_types.borrow_mut().insert(def_id, ty_var);
1650
1651                 let item_predicates = self.tcx.lookup_predicates(def_id);
1652                 let bounds = item_predicates.instantiate(self.tcx, substs);
1653
1654                 let span = self.tcx.map.def_id_span(def_id, codemap::DUMMY_SP);
1655                 for predicate in bounds.predicates {
1656                     // Change the predicate to refer to the type variable,
1657                     // which will be the concrete type, instead of the TyAnon.
1658                     // This also instantiates nested `impl Trait`.
1659                     let predicate = self.instantiate_anon_types(&predicate);
1660
1661                     // Require that the predicate holds for the concrete type.
1662                     let cause = traits::ObligationCause::new(span, self.body_id,
1663                                                              traits::ReturnType);
1664                     self.register_predicate(traits::Obligation::new(cause, predicate));
1665                 }
1666
1667                 ty_var
1668             } else {
1669                 ty
1670             }
1671         }})
1672     }
1673
1674     fn normalize_associated_types_in<T>(&self, span: Span, value: &T) -> T
1675         where T : TypeFoldable<'tcx>
1676     {
1677         self.inh.normalize_associated_types_in(span, self.body_id, value)
1678     }
1679
1680     fn normalize_associated_type(&self,
1681                                  span: Span,
1682                                  trait_ref: ty::TraitRef<'tcx>,
1683                                  item_name: ast::Name)
1684                                  -> Ty<'tcx>
1685     {
1686         let cause = traits::ObligationCause::new(span,
1687                                                  self.body_id,
1688                                                  traits::ObligationCauseCode::MiscObligation);
1689         self.fulfillment_cx
1690             .borrow_mut()
1691             .normalize_projection_type(self,
1692                                        ty::ProjectionTy {
1693                                            trait_ref: trait_ref,
1694                                            item_name: item_name,
1695                                        },
1696                                        cause)
1697     }
1698
1699     /// Instantiates the type in `did` with the generics in `path` and returns
1700     /// it (registering the necessary trait obligations along the way).
1701     ///
1702     /// Note that this function is only intended to be used with type-paths,
1703     /// not with value-paths.
1704     pub fn instantiate_type_path(&self,
1705                                  did: DefId,
1706                                  path: &hir::Path,
1707                                  node_id: ast::NodeId)
1708                                  -> Ty<'tcx> {
1709         debug!("instantiate_type_path(did={:?}, path={:?})", did, path);
1710         let mut ty = self.tcx.lookup_item_type(did).ty;
1711         if ty.is_fn() {
1712             // Tuple variants have fn type even in type namespace, extract true variant type from it
1713             ty = self.tcx.no_late_bound_regions(&ty.fn_ret()).unwrap();
1714         }
1715         let type_predicates = self.tcx.lookup_predicates(did);
1716         let substs = AstConv::ast_path_substs_for_ty(self, self,
1717                                                      path.span,
1718                                                      PathParamMode::Optional,
1719                                                      did,
1720                                                      path.segments.last().unwrap());
1721         debug!("instantiate_type_path: ty={:?} substs={:?}", ty, substs);
1722         let bounds = self.instantiate_bounds(path.span, substs, &type_predicates);
1723         let cause = traits::ObligationCause::new(path.span, self.body_id,
1724                                                  traits::ItemObligation(did));
1725         self.add_obligations_for_parameters(cause, &bounds);
1726
1727         let ty_substituted = self.instantiate_type_scheme(path.span, substs, &ty);
1728         self.write_ty(node_id, ty_substituted);
1729         self.write_substs(node_id, ty::ItemSubsts {
1730             substs: substs
1731         });
1732         ty_substituted
1733     }
1734
1735     pub fn write_nil(&self, node_id: ast::NodeId) {
1736         self.write_ty(node_id, self.tcx.mk_nil());
1737     }
1738
1739     pub fn write_never(&self, node_id: ast::NodeId) {
1740         self.write_ty(node_id, self.tcx.types.never);
1741     }
1742
1743     pub fn write_error(&self, node_id: ast::NodeId) {
1744         self.write_ty(node_id, self.tcx.types.err);
1745     }
1746
1747     pub fn require_type_meets(&self,
1748                               ty: Ty<'tcx>,
1749                               span: Span,
1750                               code: traits::ObligationCauseCode<'tcx>,
1751                               bound: ty::BuiltinBound)
1752     {
1753         self.register_builtin_bound(
1754             ty,
1755             bound,
1756             traits::ObligationCause::new(span, self.body_id, code));
1757     }
1758
1759     pub fn require_type_is_sized(&self,
1760                                  ty: Ty<'tcx>,
1761                                  span: Span,
1762                                  code: traits::ObligationCauseCode<'tcx>)
1763     {
1764         self.require_type_meets(ty, span, code, ty::BoundSized);
1765     }
1766
1767     pub fn require_expr_have_sized_type(&self,
1768                                         expr: &hir::Expr,
1769                                         code: traits::ObligationCauseCode<'tcx>)
1770     {
1771         self.require_type_is_sized(self.expr_ty(expr), expr.span, code);
1772     }
1773
1774     pub fn register_builtin_bound(&self,
1775                                   ty: Ty<'tcx>,
1776                                   builtin_bound: ty::BuiltinBound,
1777                                   cause: traits::ObligationCause<'tcx>)
1778     {
1779         self.fulfillment_cx.borrow_mut()
1780             .register_builtin_bound(self, ty, builtin_bound, cause);
1781     }
1782
1783     pub fn register_predicate(&self,
1784                               obligation: traits::PredicateObligation<'tcx>)
1785     {
1786         debug!("register_predicate({:?})",
1787                obligation);
1788         self.fulfillment_cx
1789             .borrow_mut()
1790             .register_predicate_obligation(self, obligation);
1791     }
1792
1793     pub fn to_ty(&self, ast_t: &hir::Ty) -> Ty<'tcx> {
1794         let t = AstConv::ast_ty_to_ty(self, self, ast_t);
1795         self.register_wf_obligation(t, ast_t.span, traits::MiscObligation);
1796         t
1797     }
1798
1799     pub fn expr_ty(&self, ex: &hir::Expr) -> Ty<'tcx> {
1800         if let Some(&adjustment::AdjustNeverToAny(ref t))
1801                 = self.tables.borrow().adjustments.get(&ex.id) {
1802             return t;
1803         }
1804         match self.tables.borrow().node_types.get(&ex.id) {
1805             Some(&t) => t,
1806             None => {
1807                 bug!("no type for expr in fcx {}", self.tag());
1808             }
1809         }
1810     }
1811
1812     /// Apply `adjustment` to the type of `expr`
1813     pub fn adjust_expr_ty(&self,
1814                           expr: &hir::Expr,
1815                           adjustment: Option<&adjustment::AutoAdjustment<'tcx>>)
1816                           -> Ty<'tcx>
1817     {
1818         let raw_ty = self.expr_ty(expr);
1819         let raw_ty = self.shallow_resolve(raw_ty);
1820         let resolve_ty = |ty: Ty<'tcx>| self.resolve_type_vars_if_possible(&ty);
1821         raw_ty.adjust(self.tcx, expr.span, expr.id, adjustment, |method_call| {
1822             self.tables.borrow().method_map.get(&method_call)
1823                                         .map(|method| resolve_ty(method.ty))
1824         })
1825     }
1826
1827     pub fn node_ty(&self, id: ast::NodeId) -> Ty<'tcx> {
1828         match self.tables.borrow().node_types.get(&id) {
1829             Some(&t) => t,
1830             None if self.err_count_since_creation() != 0 => self.tcx.types.err,
1831             None => {
1832                 bug!("no type for node {}: {} in fcx {}",
1833                      id, self.tcx.map.node_to_string(id),
1834                      self.tag());
1835             }
1836         }
1837     }
1838
1839     pub fn item_substs(&self) -> Ref<NodeMap<ty::ItemSubsts<'tcx>>> {
1840         // NOTE: @jroesch this is hack that appears to be fixed on nightly, will monitor if
1841         // it changes when we upgrade the snapshot compiler
1842         fn project_item_susbts<'a, 'tcx>(tables: &'a ty::Tables<'tcx>)
1843                                         -> &'a NodeMap<ty::ItemSubsts<'tcx>> {
1844             &tables.item_substs
1845         }
1846
1847         Ref::map(self.tables.borrow(), project_item_susbts)
1848     }
1849
1850     pub fn opt_node_ty_substs<F>(&self,
1851                                  id: ast::NodeId,
1852                                  f: F) where
1853         F: FnOnce(&ty::ItemSubsts<'tcx>),
1854     {
1855         match self.tables.borrow().item_substs.get(&id) {
1856             Some(s) => { f(s) }
1857             None => { }
1858         }
1859     }
1860
1861     /// Registers an obligation for checking later, during regionck, that the type `ty` must
1862     /// outlive the region `r`.
1863     pub fn register_region_obligation(&self,
1864                                       ty: Ty<'tcx>,
1865                                       region: &'tcx ty::Region,
1866                                       cause: traits::ObligationCause<'tcx>)
1867     {
1868         let mut fulfillment_cx = self.fulfillment_cx.borrow_mut();
1869         fulfillment_cx.register_region_obligation(ty, region, cause);
1870     }
1871
1872     /// Registers an obligation for checking later, during regionck, that the type `ty` must
1873     /// outlive the region `r`.
1874     pub fn register_wf_obligation(&self,
1875                                   ty: Ty<'tcx>,
1876                                   span: Span,
1877                                   code: traits::ObligationCauseCode<'tcx>)
1878     {
1879         // WF obligations never themselves fail, so no real need to give a detailed cause:
1880         let cause = traits::ObligationCause::new(span, self.body_id, code);
1881         self.register_predicate(traits::Obligation::new(cause, ty::Predicate::WellFormed(ty)));
1882     }
1883
1884     pub fn register_old_wf_obligation(&self,
1885                                       ty: Ty<'tcx>,
1886                                       span: Span,
1887                                       code: traits::ObligationCauseCode<'tcx>)
1888     {
1889         // Registers an "old-style" WF obligation that uses the
1890         // implicator code.  This is basically a buggy version of
1891         // `register_wf_obligation` that is being kept around
1892         // temporarily just to help with phasing in the newer rules.
1893         //
1894         // FIXME(#27579) all uses of this should be migrated to register_wf_obligation eventually
1895         let cause = traits::ObligationCause::new(span, self.body_id, code);
1896         self.register_region_obligation(ty, self.tcx.mk_region(ty::ReEmpty), cause);
1897     }
1898
1899     /// Registers obligations that all types appearing in `substs` are well-formed.
1900     pub fn add_wf_bounds(&self, substs: &Substs<'tcx>, expr: &hir::Expr)
1901     {
1902         for ty in substs.types() {
1903             self.register_wf_obligation(ty, expr.span, traits::MiscObligation);
1904         }
1905     }
1906
1907     /// Given a fully substituted set of bounds (`generic_bounds`), and the values with which each
1908     /// type/region parameter was instantiated (`substs`), creates and registers suitable
1909     /// trait/region obligations.
1910     ///
1911     /// For example, if there is a function:
1912     ///
1913     /// ```
1914     /// fn foo<'a,T:'a>(...)
1915     /// ```
1916     ///
1917     /// and a reference:
1918     ///
1919     /// ```
1920     /// let f = foo;
1921     /// ```
1922     ///
1923     /// Then we will create a fresh region variable `'$0` and a fresh type variable `$1` for `'a`
1924     /// and `T`. This routine will add a region obligation `$1:'$0` and register it locally.
1925     pub fn add_obligations_for_parameters(&self,
1926                                           cause: traits::ObligationCause<'tcx>,
1927                                           predicates: &ty::InstantiatedPredicates<'tcx>)
1928     {
1929         assert!(!predicates.has_escaping_regions());
1930
1931         debug!("add_obligations_for_parameters(predicates={:?})",
1932                predicates);
1933
1934         for obligation in traits::predicates_for_generics(cause, predicates) {
1935             self.register_predicate(obligation);
1936         }
1937     }
1938
1939     // FIXME(arielb1): use this instead of field.ty everywhere
1940     // Only for fields! Returns <none> for methods>
1941     // Indifferent to privacy flags
1942     pub fn field_ty(&self,
1943                     span: Span,
1944                     field: ty::FieldDef<'tcx>,
1945                     substs: &Substs<'tcx>)
1946                     -> Ty<'tcx>
1947     {
1948         self.normalize_associated_types_in(span,
1949                                            &field.ty(self.tcx, substs))
1950     }
1951
1952     fn check_casts(&self) {
1953         let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
1954         for cast in deferred_cast_checks.drain(..) {
1955             cast.check(self);
1956         }
1957     }
1958
1959     /// Apply "fallbacks" to some types
1960     /// ! gets replaced with (), unconstrained ints with i32, and unconstrained floats with f64.
1961     fn default_type_parameters(&self) {
1962         use rustc::ty::error::UnconstrainedNumeric::Neither;
1963         use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedInt, UnconstrainedFloat};
1964
1965         // Defaulting inference variables becomes very dubious if we have
1966         // encountered type-checking errors. Therefore, if we think we saw
1967         // some errors in this function, just resolve all uninstanted type
1968         // varibles to TyError.
1969         if self.is_tainted_by_errors() {
1970             for ty in &self.unsolved_variables() {
1971                 if let ty::TyInfer(_) = self.shallow_resolve(ty).sty {
1972                     debug!("default_type_parameters: defaulting `{:?}` to error", ty);
1973                     self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx().types.err);
1974                 }
1975             }
1976             return;
1977         }
1978
1979         for ty in &self.unsolved_variables() {
1980             let resolved = self.resolve_type_vars_if_possible(ty);
1981             if self.type_var_diverges(resolved) {
1982                 debug!("default_type_parameters: defaulting `{:?}` to `!` because it diverges",
1983                        resolved);
1984                 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty,
1985                                    self.tcx.mk_diverging_default());
1986             } else {
1987                 match self.type_is_unconstrained_numeric(resolved) {
1988                     UnconstrainedInt => {
1989                         debug!("default_type_parameters: defaulting `{:?}` to `i32`",
1990                                resolved);
1991                         self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.i32)
1992                     },
1993                     UnconstrainedFloat => {
1994                         debug!("default_type_parameters: defaulting `{:?}` to `f32`",
1995                                resolved);
1996                         self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.f64)
1997                     }
1998                     Neither => { }
1999                 }
2000             }
2001         }
2002     }
2003
2004     fn select_all_obligations_and_apply_defaults(&self) {
2005         if self.tcx.sess.features.borrow().default_type_parameter_fallback {
2006             self.new_select_all_obligations_and_apply_defaults();
2007         } else {
2008             self.old_select_all_obligations_and_apply_defaults();
2009         }
2010     }
2011
2012     // Implements old type inference fallback algorithm
2013     fn old_select_all_obligations_and_apply_defaults(&self) {
2014         self.select_obligations_where_possible();
2015         self.default_type_parameters();
2016         self.select_obligations_where_possible();
2017     }
2018
2019     fn new_select_all_obligations_and_apply_defaults(&self) {
2020         use rustc::ty::error::UnconstrainedNumeric::Neither;
2021         use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedInt, UnconstrainedFloat};
2022
2023         // For the time being this errs on the side of being memory wasteful but provides better
2024         // error reporting.
2025         // let type_variables = self.type_variables.clone();
2026
2027         // There is a possibility that this algorithm will have to run an arbitrary number of times
2028         // to terminate so we bound it by the compiler's recursion limit.
2029         for _ in 0..self.tcx.sess.recursion_limit.get() {
2030             // First we try to solve all obligations, it is possible that the last iteration
2031             // has made it possible to make more progress.
2032             self.select_obligations_where_possible();
2033
2034             let mut conflicts = Vec::new();
2035
2036             // Collect all unsolved type, integral and floating point variables.
2037             let unsolved_variables = self.unsolved_variables();
2038
2039             // We must collect the defaults *before* we do any unification. Because we have
2040             // directly attached defaults to the type variables any unification that occurs
2041             // will erase defaults causing conflicting defaults to be completely ignored.
2042             let default_map: FnvHashMap<_, _> =
2043                 unsolved_variables
2044                     .iter()
2045                     .filter_map(|t| self.default(t).map(|d| (t, d)))
2046                     .collect();
2047
2048             let mut unbound_tyvars = HashSet::new();
2049
2050             debug!("select_all_obligations_and_apply_defaults: defaults={:?}", default_map);
2051
2052             // We loop over the unsolved variables, resolving them and if they are
2053             // and unconstrainted numeric type we add them to the set of unbound
2054             // variables. We do this so we only apply literal fallback to type
2055             // variables without defaults.
2056             for ty in &unsolved_variables {
2057                 let resolved = self.resolve_type_vars_if_possible(ty);
2058                 if self.type_var_diverges(resolved) {
2059                     self.demand_eqtype(syntax_pos::DUMMY_SP, *ty,
2060                                        self.tcx.mk_diverging_default());
2061                 } else {
2062                     match self.type_is_unconstrained_numeric(resolved) {
2063                         UnconstrainedInt | UnconstrainedFloat => {
2064                             unbound_tyvars.insert(resolved);
2065                         },
2066                         Neither => {}
2067                     }
2068                 }
2069             }
2070
2071             // We now remove any numeric types that also have defaults, and instead insert
2072             // the type variable with a defined fallback.
2073             for ty in &unsolved_variables {
2074                 if let Some(_default) = default_map.get(ty) {
2075                     let resolved = self.resolve_type_vars_if_possible(ty);
2076
2077                     debug!("select_all_obligations_and_apply_defaults: \
2078                             ty: {:?} with default: {:?}",
2079                              ty, _default);
2080
2081                     match resolved.sty {
2082                         ty::TyInfer(ty::TyVar(_)) => {
2083                             unbound_tyvars.insert(ty);
2084                         }
2085
2086                         ty::TyInfer(ty::IntVar(_)) | ty::TyInfer(ty::FloatVar(_)) => {
2087                             unbound_tyvars.insert(ty);
2088                             if unbound_tyvars.contains(resolved) {
2089                                 unbound_tyvars.remove(resolved);
2090                             }
2091                         }
2092
2093                         _ => {}
2094                     }
2095                 }
2096             }
2097
2098             // If there are no more fallbacks to apply at this point we have applied all possible
2099             // defaults and type inference will proceed as normal.
2100             if unbound_tyvars.is_empty() {
2101                 break;
2102             }
2103
2104             // Finally we go through each of the unbound type variables and unify them with
2105             // the proper fallback, reporting a conflicting default error if any of the
2106             // unifications fail. We know it must be a conflicting default because the
2107             // variable would only be in `unbound_tyvars` and have a concrete value if
2108             // it had been solved by previously applying a default.
2109
2110             // We wrap this in a transaction for error reporting, if we detect a conflict
2111             // we will rollback the inference context to its prior state so we can probe
2112             // for conflicts and correctly report them.
2113
2114
2115             let _ = self.commit_if_ok(|_: &infer::CombinedSnapshot| {
2116                 for ty in &unbound_tyvars {
2117                     if self.type_var_diverges(ty) {
2118                         self.demand_eqtype(syntax_pos::DUMMY_SP, *ty,
2119                                            self.tcx.mk_diverging_default());
2120                     } else {
2121                         match self.type_is_unconstrained_numeric(ty) {
2122                             UnconstrainedInt => {
2123                                 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.i32)
2124                             },
2125                             UnconstrainedFloat => {
2126                                 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.f64)
2127                             }
2128                             Neither => {
2129                                 if let Some(default) = default_map.get(ty) {
2130                                     let default = default.clone();
2131                                     match self.eq_types(false,
2132                                             TypeOrigin::Misc(default.origin_span),
2133                                             ty, default.ty) {
2134                                         Ok(InferOk { obligations, .. }) => {
2135                                             // FIXME(#32730) propagate obligations
2136                                             assert!(obligations.is_empty())
2137                                         },
2138                                         Err(_) => {
2139                                             conflicts.push((*ty, default));
2140                                         }
2141                                     }
2142                                 }
2143                             }
2144                         }
2145                     }
2146                 }
2147
2148                 // If there are conflicts we rollback, otherwise commit
2149                 if conflicts.len() > 0 {
2150                     Err(())
2151                 } else {
2152                     Ok(())
2153                 }
2154             });
2155
2156             if conflicts.len() > 0 {
2157                 // Loop through each conflicting default, figuring out the default that caused
2158                 // a unification failure and then report an error for each.
2159                 for (conflict, default) in conflicts {
2160                     let conflicting_default =
2161                         self.find_conflicting_default(&unbound_tyvars, &default_map, conflict)
2162                             .unwrap_or(type_variable::Default {
2163                                 ty: self.next_ty_var(),
2164                                 origin_span: syntax_pos::DUMMY_SP,
2165                                 def_id: self.tcx.map.local_def_id(0) // what do I put here?
2166                             });
2167
2168                     // This is to ensure that we elimnate any non-determinism from the error
2169                     // reporting by fixing an order, it doesn't matter what order we choose
2170                     // just that it is consistent.
2171                     let (first_default, second_default) =
2172                         if default.def_id < conflicting_default.def_id {
2173                             (default, conflicting_default)
2174                         } else {
2175                             (conflicting_default, default)
2176                         };
2177
2178
2179                     self.report_conflicting_default_types(
2180                         first_default.origin_span,
2181                         first_default,
2182                         second_default)
2183                 }
2184             }
2185         }
2186
2187         self.select_obligations_where_possible();
2188     }
2189
2190     // For use in error handling related to default type parameter fallback. We explicitly
2191     // apply the default that caused conflict first to a local version of the type variable
2192     // table then apply defaults until we find a conflict. That default must be the one
2193     // that caused conflict earlier.
2194     fn find_conflicting_default(&self,
2195                                 unbound_vars: &HashSet<Ty<'tcx>>,
2196                                 default_map: &FnvHashMap<&Ty<'tcx>, type_variable::Default<'tcx>>,
2197                                 conflict: Ty<'tcx>)
2198                                 -> Option<type_variable::Default<'tcx>> {
2199         use rustc::ty::error::UnconstrainedNumeric::Neither;
2200         use rustc::ty::error::UnconstrainedNumeric::{UnconstrainedInt, UnconstrainedFloat};
2201
2202         // Ensure that we apply the conflicting default first
2203         let mut unbound_tyvars = Vec::with_capacity(unbound_vars.len() + 1);
2204         unbound_tyvars.push(conflict);
2205         unbound_tyvars.extend(unbound_vars.iter());
2206
2207         let mut result = None;
2208         // We run the same code as above applying defaults in order, this time when
2209         // we find the conflict we just return it for error reporting above.
2210
2211         // We also run this inside snapshot that never commits so we can do error
2212         // reporting for more then one conflict.
2213         for ty in &unbound_tyvars {
2214             if self.type_var_diverges(ty) {
2215                 self.demand_eqtype(syntax_pos::DUMMY_SP, *ty,
2216                                    self.tcx.mk_diverging_default());
2217             } else {
2218                 match self.type_is_unconstrained_numeric(ty) {
2219                     UnconstrainedInt => {
2220                         self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.i32)
2221                     },
2222                     UnconstrainedFloat => {
2223                         self.demand_eqtype(syntax_pos::DUMMY_SP, *ty, self.tcx.types.f64)
2224                     },
2225                     Neither => {
2226                         if let Some(default) = default_map.get(ty) {
2227                             let default = default.clone();
2228                             match self.eq_types(false,
2229                                     TypeOrigin::Misc(default.origin_span),
2230                                     ty, default.ty) {
2231                                 // FIXME(#32730) propagate obligations
2232                                 Ok(InferOk { obligations, .. }) => assert!(obligations.is_empty()),
2233                                 Err(_) => {
2234                                     result = Some(default);
2235                                 }
2236                             }
2237                         }
2238                     }
2239                 }
2240             }
2241         }
2242
2243         return result;
2244     }
2245
2246     fn select_all_obligations_or_error(&self) {
2247         debug!("select_all_obligations_or_error");
2248
2249         // upvar inference should have ensured that all deferred call
2250         // resolutions are handled by now.
2251         assert!(self.deferred_call_resolutions.borrow().is_empty());
2252
2253         self.select_all_obligations_and_apply_defaults();
2254
2255         let mut fulfillment_cx = self.fulfillment_cx.borrow_mut();
2256
2257         // Steal the deferred obligations before the fulfillment
2258         // context can turn all of them into errors.
2259         let obligations = fulfillment_cx.take_deferred_obligations();
2260         self.deferred_obligations.borrow_mut().extend(obligations);
2261
2262         match fulfillment_cx.select_all_or_error(self) {
2263             Ok(()) => { }
2264             Err(errors) => { self.report_fulfillment_errors(&errors); }
2265         }
2266
2267         if let Err(ref errors) = fulfillment_cx.select_rfc1592_obligations(self) {
2268             self.report_fulfillment_errors_as_warnings(errors, self.body_id);
2269         }
2270     }
2271
2272     /// Select as many obligations as we can at present.
2273     fn select_obligations_where_possible(&self) {
2274         match self.fulfillment_cx.borrow_mut().select_where_possible(self) {
2275             Ok(()) => { }
2276             Err(errors) => { self.report_fulfillment_errors(&errors); }
2277         }
2278     }
2279
2280     /// For the overloaded lvalue expressions (`*x`, `x[3]`), the trait
2281     /// returns a type of `&T`, but the actual type we assign to the
2282     /// *expression* is `T`. So this function just peels off the return
2283     /// type by one layer to yield `T`.
2284     fn make_overloaded_lvalue_return_type(&self,
2285                                           method: MethodCallee<'tcx>)
2286                                           -> ty::TypeAndMut<'tcx>
2287     {
2288         // extract method return type, which will be &T;
2289         // all LB regions should have been instantiated during method lookup
2290         let ret_ty = method.ty.fn_ret();
2291         let ret_ty = self.tcx.no_late_bound_regions(&ret_ty).unwrap();
2292
2293         // method returns &T, but the type as visible to user is T, so deref
2294         ret_ty.builtin_deref(true, NoPreference).unwrap()
2295     }
2296
2297     fn lookup_indexing(&self,
2298                        expr: &hir::Expr,
2299                        base_expr: &'gcx hir::Expr,
2300                        base_ty: Ty<'tcx>,
2301                        idx_ty: Ty<'tcx>,
2302                        lvalue_pref: LvaluePreference)
2303                        -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)>
2304     {
2305         // FIXME(#18741) -- this is almost but not quite the same as the
2306         // autoderef that normal method probing does. They could likely be
2307         // consolidated.
2308
2309         let mut autoderef = self.autoderef(base_expr.span, base_ty);
2310
2311         while let Some((adj_ty, autoderefs)) = autoderef.next() {
2312             if let Some(final_mt) = self.try_index_step(
2313                 MethodCall::expr(expr.id),
2314                 expr, base_expr, adj_ty, autoderefs,
2315                 false, lvalue_pref, idx_ty)
2316             {
2317                 autoderef.finalize(lvalue_pref, Some(base_expr));
2318                 return Some(final_mt);
2319             }
2320
2321             if let ty::TyArray(element_ty, _) = adj_ty.sty {
2322                 autoderef.finalize(lvalue_pref, Some(base_expr));
2323                 let adjusted_ty = self.tcx.mk_slice(element_ty);
2324                 return self.try_index_step(
2325                     MethodCall::expr(expr.id), expr, base_expr,
2326                     adjusted_ty, autoderefs, true, lvalue_pref, idx_ty);
2327             }
2328         }
2329         autoderef.unambiguous_final_ty();
2330         None
2331     }
2332
2333     /// To type-check `base_expr[index_expr]`, we progressively autoderef
2334     /// (and otherwise adjust) `base_expr`, looking for a type which either
2335     /// supports builtin indexing or overloaded indexing.
2336     /// This loop implements one step in that search; the autoderef loop
2337     /// is implemented by `lookup_indexing`.
2338     fn try_index_step(&self,
2339                       method_call: MethodCall,
2340                       expr: &hir::Expr,
2341                       base_expr: &'gcx hir::Expr,
2342                       adjusted_ty: Ty<'tcx>,
2343                       autoderefs: usize,
2344                       unsize: bool,
2345                       lvalue_pref: LvaluePreference,
2346                       index_ty: Ty<'tcx>)
2347                       -> Option<(/*index type*/ Ty<'tcx>, /*element type*/ Ty<'tcx>)>
2348     {
2349         let tcx = self.tcx;
2350         debug!("try_index_step(expr={:?}, base_expr.id={:?}, adjusted_ty={:?}, \
2351                                autoderefs={}, unsize={}, index_ty={:?})",
2352                expr,
2353                base_expr,
2354                adjusted_ty,
2355                autoderefs,
2356                unsize,
2357                index_ty);
2358
2359         let input_ty = self.next_ty_var();
2360
2361         // First, try built-in indexing.
2362         match (adjusted_ty.builtin_index(), &index_ty.sty) {
2363             (Some(ty), &ty::TyUint(ast::UintTy::Us)) | (Some(ty), &ty::TyInfer(ty::IntVar(_))) => {
2364                 debug!("try_index_step: success, using built-in indexing");
2365                 // If we had `[T; N]`, we should've caught it before unsizing to `[T]`.
2366                 assert!(!unsize);
2367                 self.write_autoderef_adjustment(base_expr.id, autoderefs);
2368                 return Some((tcx.types.usize, ty));
2369             }
2370             _ => {}
2371         }
2372
2373         // Try `IndexMut` first, if preferred.
2374         let method = match (lvalue_pref, tcx.lang_items.index_mut_trait()) {
2375             (PreferMutLvalue, Some(trait_did)) => {
2376                 self.lookup_method_in_trait_adjusted(expr.span,
2377                                                      Some(&base_expr),
2378                                                      token::intern("index_mut"),
2379                                                      trait_did,
2380                                                      autoderefs,
2381                                                      unsize,
2382                                                      adjusted_ty,
2383                                                      Some(vec![input_ty]))
2384             }
2385             _ => None,
2386         };
2387
2388         // Otherwise, fall back to `Index`.
2389         let method = match (method, tcx.lang_items.index_trait()) {
2390             (None, Some(trait_did)) => {
2391                 self.lookup_method_in_trait_adjusted(expr.span,
2392                                                      Some(&base_expr),
2393                                                      token::intern("index"),
2394                                                      trait_did,
2395                                                      autoderefs,
2396                                                      unsize,
2397                                                      adjusted_ty,
2398                                                      Some(vec![input_ty]))
2399             }
2400             (method, _) => method,
2401         };
2402
2403         // If some lookup succeeds, write callee into table and extract index/element
2404         // type from the method signature.
2405         // If some lookup succeeded, install method in table
2406         method.map(|method| {
2407             debug!("try_index_step: success, using overloaded indexing");
2408             self.tables.borrow_mut().method_map.insert(method_call, method);
2409             (input_ty, self.make_overloaded_lvalue_return_type(method).ty)
2410         })
2411     }
2412
2413     fn check_method_argument_types(&self,
2414                                    sp: Span,
2415                                    method_fn_ty: Ty<'tcx>,
2416                                    callee_expr: &'gcx hir::Expr,
2417                                    args_no_rcvr: &'gcx [P<hir::Expr>],
2418                                    tuple_arguments: TupleArgumentsFlag,
2419                                    expected: Expectation<'tcx>)
2420                                    -> Ty<'tcx> {
2421         if method_fn_ty.references_error() {
2422             let err_inputs = self.err_args(args_no_rcvr.len());
2423
2424             let err_inputs = match tuple_arguments {
2425                 DontTupleArguments => err_inputs,
2426                 TupleArguments => vec![self.tcx.mk_tup(err_inputs)],
2427             };
2428
2429             self.check_argument_types(sp, &err_inputs[..], &[], args_no_rcvr,
2430                                       false, tuple_arguments);
2431             self.tcx.types.err
2432         } else {
2433             match method_fn_ty.sty {
2434                 ty::TyFnDef(_, _, ref fty) => {
2435                     // HACK(eddyb) ignore self in the definition (see above).
2436                     let expected_arg_tys = self.expected_types_for_fn_args(sp, expected,
2437                                                                            fty.sig.0.output,
2438                                                                            &fty.sig.0.inputs[1..]);
2439                     self.check_argument_types(sp, &fty.sig.0.inputs[1..], &expected_arg_tys[..],
2440                                               args_no_rcvr, fty.sig.0.variadic, tuple_arguments);
2441                     fty.sig.0.output
2442                 }
2443                 _ => {
2444                     span_bug!(callee_expr.span, "method without bare fn type");
2445                 }
2446             }
2447         }
2448     }
2449
2450     /// Generic function that factors out common logic from function calls,
2451     /// method calls and overloaded operators.
2452     fn check_argument_types(&self,
2453                             sp: Span,
2454                             fn_inputs: &[Ty<'tcx>],
2455                             expected_arg_tys: &[Ty<'tcx>],
2456                             args: &'gcx [P<hir::Expr>],
2457                             variadic: bool,
2458                             tuple_arguments: TupleArgumentsFlag) {
2459         let tcx = self.tcx;
2460
2461         // Grab the argument types, supplying fresh type variables
2462         // if the wrong number of arguments were supplied
2463         let supplied_arg_count = if tuple_arguments == DontTupleArguments {
2464             args.len()
2465         } else {
2466             1
2467         };
2468
2469         // All the input types from the fn signature must outlive the call
2470         // so as to validate implied bounds.
2471         for &fn_input_ty in fn_inputs {
2472             self.register_wf_obligation(fn_input_ty, sp, traits::MiscObligation);
2473         }
2474
2475         let mut expected_arg_tys = expected_arg_tys;
2476         let expected_arg_count = fn_inputs.len();
2477
2478         fn parameter_count_error<'tcx>(sess: &Session, sp: Span, fn_inputs: &[Ty<'tcx>],
2479                                        expected_count: usize, arg_count: usize, error_code: &str,
2480                                        variadic: bool) {
2481             let mut err = sess.struct_span_err_with_code(sp,
2482                 &format!("this function takes {}{} parameter{} but {} parameter{} supplied",
2483                     if variadic {"at least "} else {""},
2484                     expected_count,
2485                     if expected_count == 1 {""} else {"s"},
2486                     arg_count,
2487                     if arg_count == 1 {" was"} else {"s were"}),
2488                 error_code);
2489
2490             err.span_label(sp, &format!("expected {}{} parameter{}",
2491                                         if variadic {"at least "} else {""},
2492                                         expected_count,
2493                                         if expected_count == 1 {""} else {"s"}));
2494
2495             let input_types = fn_inputs.iter().map(|i| format!("{:?}", i)).collect::<Vec<String>>();
2496             if input_types.len() > 0 {
2497                 err.note(&format!("the following parameter type{} expected: {}",
2498                         if expected_count == 1 {" was"} else {"s were"},
2499                         input_types.join(", ")));
2500             }
2501             err.emit();
2502         }
2503
2504         let formal_tys = if tuple_arguments == TupleArguments {
2505             let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
2506             match tuple_type.sty {
2507                 ty::TyTuple(arg_types) if arg_types.len() != args.len() => {
2508                     parameter_count_error(tcx.sess, sp, fn_inputs, arg_types.len(), args.len(),
2509                                           "E0057", false);
2510                     expected_arg_tys = &[];
2511                     self.err_args(args.len())
2512                 }
2513                 ty::TyTuple(arg_types) => {
2514                     expected_arg_tys = match expected_arg_tys.get(0) {
2515                         Some(&ty) => match ty.sty {
2516                             ty::TyTuple(ref tys) => &tys,
2517                             _ => &[]
2518                         },
2519                         None => &[]
2520                     };
2521                     arg_types.to_vec()
2522                 }
2523                 _ => {
2524                     span_err!(tcx.sess, sp, E0059,
2525                         "cannot use call notation; the first type parameter \
2526                          for the function trait is neither a tuple nor unit");
2527                     expected_arg_tys = &[];
2528                     self.err_args(args.len())
2529                 }
2530             }
2531         } else if expected_arg_count == supplied_arg_count {
2532             fn_inputs.to_vec()
2533         } else if variadic {
2534             if supplied_arg_count >= expected_arg_count {
2535                 fn_inputs.to_vec()
2536             } else {
2537                 parameter_count_error(tcx.sess, sp, fn_inputs, expected_arg_count,
2538                                       supplied_arg_count, "E0060", true);
2539                 expected_arg_tys = &[];
2540                 self.err_args(supplied_arg_count)
2541             }
2542         } else {
2543             parameter_count_error(tcx.sess, sp, fn_inputs, expected_arg_count, supplied_arg_count,
2544                                   "E0061", false);
2545             expected_arg_tys = &[];
2546             self.err_args(supplied_arg_count)
2547         };
2548
2549         debug!("check_argument_types: formal_tys={:?}",
2550                formal_tys.iter().map(|t| self.ty_to_string(*t)).collect::<Vec<String>>());
2551
2552         // Check the arguments.
2553         // We do this in a pretty awful way: first we typecheck any arguments
2554         // that are not anonymous functions, then we typecheck the anonymous
2555         // functions. This is so that we have more information about the types
2556         // of arguments when we typecheck the functions. This isn't really the
2557         // right way to do this.
2558         let xs = [false, true];
2559         let mut any_diverges = false; // has any of the arguments diverged?
2560         let mut warned = false; // have we already warned about unreachable code?
2561         for check_blocks in &xs {
2562             let check_blocks = *check_blocks;
2563             debug!("check_blocks={}", check_blocks);
2564
2565             // More awful hacks: before we check argument types, try to do
2566             // an "opportunistic" vtable resolution of any trait bounds on
2567             // the call. This helps coercions.
2568             if check_blocks {
2569                 self.select_obligations_where_possible();
2570             }
2571
2572             // For variadic functions, we don't have a declared type for all of
2573             // the arguments hence we only do our usual type checking with
2574             // the arguments who's types we do know.
2575             let t = if variadic {
2576                 expected_arg_count
2577             } else if tuple_arguments == TupleArguments {
2578                 args.len()
2579             } else {
2580                 supplied_arg_count
2581             };
2582             for (i, arg) in args.iter().take(t).enumerate() {
2583                 if any_diverges && !warned {
2584                     self.tcx
2585                         .sess
2586                         .add_lint(lint::builtin::UNREACHABLE_CODE,
2587                                   arg.id,
2588                                   arg.span,
2589                                   "unreachable expression".to_string());
2590                     warned = true;
2591                 }
2592                 let is_block = match arg.node {
2593                     hir::ExprClosure(..) => true,
2594                     _ => false
2595                 };
2596
2597                 if is_block == check_blocks {
2598                     debug!("checking the argument");
2599                     let formal_ty = formal_tys[i];
2600
2601                     // The special-cased logic below has three functions:
2602                     // 1. Provide as good of an expected type as possible.
2603                     let expected = expected_arg_tys.get(i).map(|&ty| {
2604                         Expectation::rvalue_hint(self, ty)
2605                     });
2606
2607                     self.check_expr_with_expectation(&arg,
2608                         expected.unwrap_or(ExpectHasType(formal_ty)));
2609                     // 2. Coerce to the most detailed type that could be coerced
2610                     //    to, which is `expected_ty` if `rvalue_hint` returns an
2611                     //    `ExpectHasType(expected_ty)`, or the `formal_ty` otherwise.
2612                     let coerce_ty = expected.and_then(|e| e.only_has_type(self));
2613                     self.demand_coerce(&arg, coerce_ty.unwrap_or(formal_ty));
2614
2615                     // 3. Relate the expected type and the formal one,
2616                     //    if the expected type was used for the coercion.
2617                     coerce_ty.map(|ty| self.demand_suptype(arg.span, formal_ty, ty));
2618                 }
2619
2620                 if let Some(&arg_ty) = self.tables.borrow().node_types.get(&arg.id) {
2621                     // FIXME(canndrew): This is_never should probably be an is_uninhabited
2622                     any_diverges = any_diverges ||
2623                                    self.type_var_diverges(arg_ty) ||
2624                                    arg_ty.is_never();
2625                 }
2626             }
2627             if any_diverges && !warned {
2628                 let parent = self.tcx.map.get_parent_node(args[0].id);
2629                 self.tcx
2630                     .sess
2631                     .add_lint(lint::builtin::UNREACHABLE_CODE,
2632                               parent,
2633                               sp,
2634                               "unreachable call".to_string());
2635                 warned = true;
2636             }
2637
2638         }
2639
2640         // We also need to make sure we at least write the ty of the other
2641         // arguments which we skipped above.
2642         if variadic {
2643             for arg in args.iter().skip(expected_arg_count) {
2644                 self.check_expr(&arg);
2645
2646                 // There are a few types which get autopromoted when passed via varargs
2647                 // in C but we just error out instead and require explicit casts.
2648                 let arg_ty = self.structurally_resolved_type(arg.span,
2649                                                              self.expr_ty(&arg));
2650                 match arg_ty.sty {
2651                     ty::TyFloat(ast::FloatTy::F32) => {
2652                         self.type_error_message(arg.span, |t| {
2653                             format!("can't pass an `{}` to variadic \
2654                                      function, cast to `c_double`", t)
2655                         }, arg_ty);
2656                     }
2657                     ty::TyInt(ast::IntTy::I8) | ty::TyInt(ast::IntTy::I16) | ty::TyBool => {
2658                         self.type_error_message(arg.span, |t| {
2659                             format!("can't pass `{}` to variadic \
2660                                      function, cast to `c_int`",
2661                                            t)
2662                         }, arg_ty);
2663                     }
2664                     ty::TyUint(ast::UintTy::U8) | ty::TyUint(ast::UintTy::U16) => {
2665                         self.type_error_message(arg.span, |t| {
2666                             format!("can't pass `{}` to variadic \
2667                                      function, cast to `c_uint`",
2668                                            t)
2669                         }, arg_ty);
2670                     }
2671                     ty::TyFnDef(_, _, f) => {
2672                         let ptr_ty = self.tcx.mk_fn_ptr(f);
2673                         let ptr_ty = self.resolve_type_vars_if_possible(&ptr_ty);
2674                         self.type_error_message(arg.span,
2675                                                 |t| {
2676                             format!("can't pass `{}` to variadic \
2677                                      function, cast to `{}`", t, ptr_ty)
2678                         }, arg_ty);
2679                     }
2680                     _ => {}
2681                 }
2682             }
2683         }
2684     }
2685
2686     fn err_args(&self, len: usize) -> Vec<Ty<'tcx>> {
2687         (0..len).map(|_| self.tcx.types.err).collect()
2688     }
2689
2690     fn write_call(&self,
2691                   call_expr: &hir::Expr,
2692                   output: Ty<'tcx>) {
2693         self.write_ty(call_expr.id, output);
2694     }
2695
2696     // AST fragment checking
2697     fn check_lit(&self,
2698                  lit: &ast::Lit,
2699                  expected: Expectation<'tcx>)
2700                  -> Ty<'tcx>
2701     {
2702         let tcx = self.tcx;
2703
2704         match lit.node {
2705             ast::LitKind::Str(..) => tcx.mk_static_str(),
2706             ast::LitKind::ByteStr(ref v) => {
2707                 tcx.mk_imm_ref(tcx.mk_region(ty::ReStatic),
2708                                 tcx.mk_array(tcx.types.u8, v.len()))
2709             }
2710             ast::LitKind::Byte(_) => tcx.types.u8,
2711             ast::LitKind::Char(_) => tcx.types.char,
2712             ast::LitKind::Int(_, ast::LitIntType::Signed(t)) => tcx.mk_mach_int(t),
2713             ast::LitKind::Int(_, ast::LitIntType::Unsigned(t)) => tcx.mk_mach_uint(t),
2714             ast::LitKind::Int(_, ast::LitIntType::Unsuffixed) => {
2715                 let opt_ty = expected.to_option(self).and_then(|ty| {
2716                     match ty.sty {
2717                         ty::TyInt(_) | ty::TyUint(_) => Some(ty),
2718                         ty::TyChar => Some(tcx.types.u8),
2719                         ty::TyRawPtr(..) => Some(tcx.types.usize),
2720                         ty::TyFnDef(..) | ty::TyFnPtr(_) => Some(tcx.types.usize),
2721                         _ => None
2722                     }
2723                 });
2724                 opt_ty.unwrap_or_else(
2725                     || tcx.mk_int_var(self.next_int_var_id()))
2726             }
2727             ast::LitKind::Float(_, t) => tcx.mk_mach_float(t),
2728             ast::LitKind::FloatUnsuffixed(_) => {
2729                 let opt_ty = expected.to_option(self).and_then(|ty| {
2730                     match ty.sty {
2731                         ty::TyFloat(_) => Some(ty),
2732                         _ => None
2733                     }
2734                 });
2735                 opt_ty.unwrap_or_else(
2736                     || tcx.mk_float_var(self.next_float_var_id()))
2737             }
2738             ast::LitKind::Bool(_) => tcx.types.bool
2739         }
2740     }
2741
2742     fn check_expr_eq_type(&self,
2743                           expr: &'gcx hir::Expr,
2744                           expected: Ty<'tcx>) {
2745         self.check_expr_with_hint(expr, expected);
2746         self.demand_eqtype(expr.span, expected, self.expr_ty(expr));
2747     }
2748
2749     pub fn check_expr_has_type(&self,
2750                                expr: &'gcx hir::Expr,
2751                                expected: Ty<'tcx>) {
2752         self.check_expr_with_hint(expr, expected);
2753         self.demand_suptype(expr.span, expected, self.expr_ty(expr));
2754     }
2755
2756     fn check_expr_coercable_to_type(&self,
2757                                     expr: &'gcx hir::Expr,
2758                                     expected: Ty<'tcx>) {
2759         self.check_expr_with_hint(expr, expected);
2760         self.demand_coerce(expr, expected);
2761     }
2762
2763     fn check_expr_with_hint(&self, expr: &'gcx hir::Expr,
2764                             expected: Ty<'tcx>) {
2765         self.check_expr_with_expectation(expr, ExpectHasType(expected))
2766     }
2767
2768     fn check_expr_with_expectation(&self,
2769                                    expr: &'gcx hir::Expr,
2770                                    expected: Expectation<'tcx>) {
2771         self.check_expr_with_expectation_and_lvalue_pref(expr, expected, NoPreference)
2772     }
2773
2774     fn check_expr(&self, expr: &'gcx hir::Expr)  {
2775         self.check_expr_with_expectation(expr, NoExpectation)
2776     }
2777
2778     fn check_expr_with_lvalue_pref(&self, expr: &'gcx hir::Expr,
2779                                    lvalue_pref: LvaluePreference)  {
2780         self.check_expr_with_expectation_and_lvalue_pref(expr, NoExpectation, lvalue_pref)
2781     }
2782
2783     // determine the `self` type, using fresh variables for all variables
2784     // declared on the impl declaration e.g., `impl<A,B> for Vec<(A,B)>`
2785     // would return ($0, $1) where $0 and $1 are freshly instantiated type
2786     // variables.
2787     pub fn impl_self_ty(&self,
2788                         span: Span, // (potential) receiver for this impl
2789                         did: DefId)
2790                         -> TypeAndSubsts<'tcx> {
2791         let ity = self.tcx.lookup_item_type(did);
2792         debug!("impl_self_ty: ity={:?}", ity);
2793
2794         let substs = self.fresh_substs_for_item(span, did);
2795         let substd_ty = self.instantiate_type_scheme(span, &substs, &ity.ty);
2796
2797         TypeAndSubsts { substs: substs, ty: substd_ty }
2798     }
2799
2800     /// Unifies the return type with the expected type early, for more coercions
2801     /// and forward type information on the argument expressions.
2802     fn expected_types_for_fn_args(&self,
2803                                   call_span: Span,
2804                                   expected_ret: Expectation<'tcx>,
2805                                   formal_ret: Ty<'tcx>,
2806                                   formal_args: &[Ty<'tcx>])
2807                                   -> Vec<Ty<'tcx>> {
2808         let expected_args = expected_ret.only_has_type(self).and_then(|ret_ty| {
2809             self.commit_regions_if_ok(|| {
2810                 // Attempt to apply a subtyping relationship between the formal
2811                 // return type (likely containing type variables if the function
2812                 // is polymorphic) and the expected return type.
2813                 // No argument expectations are produced if unification fails.
2814                 let origin = TypeOrigin::Misc(call_span);
2815                 let ures = self.sub_types(false, origin, formal_ret, ret_ty);
2816                 // FIXME(#15760) can't use try! here, FromError doesn't default
2817                 // to identity so the resulting type is not constrained.
2818                 match ures {
2819                     // FIXME(#32730) propagate obligations
2820                     Ok(InferOk { obligations, .. }) => assert!(obligations.is_empty()),
2821                     Err(e) => return Err(e),
2822                 }
2823
2824                 // Record all the argument types, with the substitutions
2825                 // produced from the above subtyping unification.
2826                 Ok(formal_args.iter().map(|ty| {
2827                     self.resolve_type_vars_if_possible(ty)
2828                 }).collect())
2829             }).ok()
2830         }).unwrap_or(vec![]);
2831         debug!("expected_types_for_fn_args(formal={:?} -> {:?}, expected={:?} -> {:?})",
2832                formal_args, formal_ret,
2833                expected_args, expected_ret);
2834         expected_args
2835     }
2836
2837     // Checks a method call.
2838     fn check_method_call(&self,
2839                          expr: &'gcx hir::Expr,
2840                          method_name: Spanned<ast::Name>,
2841                          args: &'gcx [P<hir::Expr>],
2842                          tps: &[P<hir::Ty>],
2843                          expected: Expectation<'tcx>,
2844                          lvalue_pref: LvaluePreference) {
2845         let rcvr = &args[0];
2846         self.check_expr_with_lvalue_pref(&rcvr, lvalue_pref);
2847
2848         // no need to check for bot/err -- callee does that
2849         let expr_t = self.structurally_resolved_type(expr.span, self.expr_ty(&rcvr));
2850
2851         let tps = tps.iter().map(|ast_ty| self.to_ty(&ast_ty)).collect::<Vec<_>>();
2852         let fn_ty = match self.lookup_method(method_name.span,
2853                                              method_name.node,
2854                                              expr_t,
2855                                              tps,
2856                                              expr,
2857                                              rcvr) {
2858             Ok(method) => {
2859                 let method_ty = method.ty;
2860                 let method_call = MethodCall::expr(expr.id);
2861                 self.tables.borrow_mut().method_map.insert(method_call, method);
2862                 method_ty
2863             }
2864             Err(error) => {
2865                 if method_name.node != keywords::Invalid.name() {
2866                     self.report_method_error(method_name.span, expr_t,
2867                                              method_name.node, Some(rcvr), error);
2868                 }
2869                 self.write_error(expr.id);
2870                 self.tcx.types.err
2871             }
2872         };
2873
2874         // Call the generic checker.
2875         let ret_ty = self.check_method_argument_types(method_name.span, fn_ty,
2876                                                       expr, &args[1..],
2877                                                       DontTupleArguments,
2878                                                       expected);
2879
2880         self.write_call(expr, ret_ty);
2881     }
2882
2883     // A generic function for checking the then and else in an if
2884     // or if-else.
2885     fn check_then_else(&self,
2886                        cond_expr: &'gcx hir::Expr,
2887                        then_blk: &'gcx hir::Block,
2888                        opt_else_expr: Option<&'gcx hir::Expr>,
2889                        id: ast::NodeId,
2890                        sp: Span,
2891                        expected: Expectation<'tcx>) {
2892         self.check_expr_has_type(cond_expr, self.tcx.types.bool);
2893
2894         let expected = expected.adjust_for_branches(self);
2895         self.check_block_with_expected(then_blk, expected);
2896         let then_ty = self.node_ty(then_blk.id);
2897
2898         let unit = self.tcx.mk_nil();
2899         let (origin, expected, found, result) =
2900         if let Some(else_expr) = opt_else_expr {
2901             self.check_expr_with_expectation(else_expr, expected);
2902             let else_ty = self.expr_ty(else_expr);
2903             let origin = TypeOrigin::IfExpression(sp);
2904
2905             // Only try to coerce-unify if we have a then expression
2906             // to assign coercions to, otherwise it's () or diverging.
2907             let result = if let Some(ref then) = then_blk.expr {
2908                 let res = self.try_find_coercion_lub(origin, || Some(&**then),
2909                                                      then_ty, else_expr);
2910
2911                 // In case we did perform an adjustment, we have to update
2912                 // the type of the block, because old trans still uses it.
2913                 let adj = self.tables.borrow().adjustments.get(&then.id).cloned();
2914                 if res.is_ok() && adj.is_some() {
2915                     self.write_ty(then_blk.id, self.adjust_expr_ty(then, adj.as_ref()));
2916                 }
2917
2918                 res
2919             } else {
2920                 self.commit_if_ok(|_| {
2921                     let trace = TypeTrace::types(origin, true, then_ty, else_ty);
2922                     self.lub(true, trace, &then_ty, &else_ty)
2923                         .map(|InferOk { value, obligations }| {
2924                             // FIXME(#32730) propagate obligations
2925                             assert!(obligations.is_empty());
2926                             value
2927                         })
2928                 })
2929             };
2930             (origin, then_ty, else_ty, result)
2931         } else {
2932             let origin = TypeOrigin::IfExpressionWithNoElse(sp);
2933             (origin, unit, then_ty,
2934              self.eq_types(true, origin, unit, then_ty)
2935                  .map(|InferOk { obligations, .. }| {
2936                      // FIXME(#32730) propagate obligations
2937                      assert!(obligations.is_empty());
2938                      unit
2939                  }))
2940         };
2941
2942         let if_ty = match result {
2943             Ok(ty) => {
2944                 if self.expr_ty(cond_expr).references_error() {
2945                     self.tcx.types.err
2946                 } else {
2947                     ty
2948                 }
2949             }
2950             Err(e) => {
2951                 self.report_mismatched_types(origin, expected, found, e);
2952                 self.tcx.types.err
2953             }
2954         };
2955
2956         self.write_ty(id, if_ty);
2957     }
2958
2959     // Check field access expressions
2960     fn check_field(&self,
2961                    expr: &'gcx hir::Expr,
2962                    lvalue_pref: LvaluePreference,
2963                    base: &'gcx hir::Expr,
2964                    field: &Spanned<ast::Name>) {
2965         self.check_expr_with_lvalue_pref(base, lvalue_pref);
2966         let expr_t = self.structurally_resolved_type(expr.span,
2967                                                      self.expr_ty(base));
2968         let mut private_candidate = None;
2969         let mut autoderef = self.autoderef(expr.span, expr_t);
2970         while let Some((base_t, autoderefs)) = autoderef.next() {
2971             if let ty::TyStruct(base_def, substs) = base_t.sty {
2972                 debug!("struct named {:?}",  base_t);
2973                 if let Some(field) = base_def.struct_variant().find_field_named(field.node) {
2974                     let field_ty = self.field_ty(expr.span, field, substs);
2975                     if field.vis.is_accessible_from(self.body_id, &self.tcx().map) {
2976                         autoderef.finalize(lvalue_pref, Some(base));
2977                         self.write_ty(expr.id, field_ty);
2978                         self.write_autoderef_adjustment(base.id, autoderefs);
2979                         return;
2980                     }
2981                     private_candidate = Some((base_def.did, field_ty));
2982                 }
2983             }
2984         }
2985         autoderef.unambiguous_final_ty();
2986
2987         if let Some((did, field_ty)) = private_candidate {
2988             let struct_path = self.tcx().item_path_str(did);
2989             self.write_ty(expr.id, field_ty);
2990             let msg = format!("field `{}` of struct `{}` is private", field.node, struct_path);
2991             let mut err = self.tcx().sess.struct_span_err(expr.span, &msg);
2992             // Also check if an accessible method exists, which is often what is meant.
2993             if self.method_exists(field.span, field.node, expr_t, expr.id, false) {
2994                 err.note(&format!("a method `{}` also exists, perhaps you wish to call it",
2995                                   field.node));
2996             }
2997             err.emit();
2998         } else if field.node == keywords::Invalid.name() {
2999             self.write_error(expr.id);
3000         } else if self.method_exists(field.span, field.node, expr_t, expr.id, true) {
3001             self.type_error_struct(field.span, |actual| {
3002                 format!("attempted to take value of method `{}` on type \
3003                          `{}`", field.node, actual)
3004             }, expr_t)
3005                 .help("maybe a `()` to call it is missing? \
3006                        If not, try an anonymous function")
3007                 .emit();
3008             self.write_error(expr.id);
3009         } else {
3010             let mut err = self.type_error_struct(expr.span, |actual| {
3011                 format!("attempted access of field `{}` on type `{}`, \
3012                          but no field with that name was found",
3013                         field.node, actual)
3014             }, expr_t);
3015             if let ty::TyRawPtr(..) = expr_t.sty {
3016                 err.note(&format!("`{0}` is a native pointer; perhaps you need to deref with \
3017                                   `(*{0}).{1}`", pprust::expr_to_string(base), field.node));
3018             }
3019             if let ty::TyStruct(def, _) = expr_t.sty {
3020                 Self::suggest_field_names(&mut err, def.struct_variant(), field, vec![]);
3021             }
3022             err.emit();
3023             self.write_error(expr.id);
3024         }
3025     }
3026
3027     // displays hints about the closest matches in field names
3028     fn suggest_field_names(err: &mut DiagnosticBuilder,
3029                            variant: ty::VariantDef<'tcx>,
3030                            field: &Spanned<ast::Name>,
3031                            skip : Vec<InternedString>) {
3032         let name = field.node.as_str();
3033         let names = variant.fields.iter().filter_map(|field| {
3034             // ignore already set fields and private fields from non-local crates
3035             if skip.iter().any(|x| *x == field.name.as_str()) ||
3036                (variant.did.krate != LOCAL_CRATE && field.vis != Visibility::Public) {
3037                 None
3038             } else {
3039                 Some(&field.name)
3040             }
3041         });
3042
3043         // only find fits with at least one matching letter
3044         if let Some(name) = find_best_match_for_name(names, &name, Some(name.len())) {
3045             err.span_help(field.span,
3046                           &format!("did you mean `{}`?", name));
3047         }
3048     }
3049
3050     // Check tuple index expressions
3051     fn check_tup_field(&self,
3052                        expr: &'gcx hir::Expr,
3053                        lvalue_pref: LvaluePreference,
3054                        base: &'gcx hir::Expr,
3055                        idx: codemap::Spanned<usize>) {
3056         self.check_expr_with_lvalue_pref(base, lvalue_pref);
3057         let expr_t = self.structurally_resolved_type(expr.span,
3058                                                      self.expr_ty(base));
3059         let mut private_candidate = None;
3060         let mut tuple_like = false;
3061         let mut autoderef = self.autoderef(expr.span, expr_t);
3062         while let Some((base_t, autoderefs)) = autoderef.next() {
3063             let field = match base_t.sty {
3064                 ty::TyStruct(base_def, substs) => {
3065                     tuple_like = base_def.struct_variant().kind == ty::VariantKind::Tuple;
3066                     if !tuple_like { continue }
3067
3068                     debug!("tuple struct named {:?}",  base_t);
3069                     base_def.struct_variant().fields.get(idx.node).and_then(|field| {
3070                         let field_ty = self.field_ty(expr.span, field, substs);
3071                         private_candidate = Some((base_def.did, field_ty));
3072                         if field.vis.is_accessible_from(self.body_id, &self.tcx().map) {
3073                             Some(field_ty)
3074                         } else {
3075                             None
3076                         }
3077                     })
3078                 }
3079                 ty::TyTuple(ref v) => {
3080                     tuple_like = true;
3081                     v.get(idx.node).cloned()
3082                 }
3083                 _ => continue
3084             };
3085
3086             if let Some(field_ty) = field {
3087                 autoderef.finalize(lvalue_pref, Some(base));
3088                 self.write_ty(expr.id, field_ty);
3089                 self.write_autoderef_adjustment(base.id, autoderefs);
3090                 return;
3091             }
3092         }
3093         autoderef.unambiguous_final_ty();
3094
3095         if let Some((did, field_ty)) = private_candidate {
3096             let struct_path = self.tcx().item_path_str(did);
3097             let msg = format!("field `{}` of struct `{}` is private", idx.node, struct_path);
3098             self.tcx().sess.span_err(expr.span, &msg);
3099             self.write_ty(expr.id, field_ty);
3100             return;
3101         }
3102
3103         self.type_error_message(
3104             expr.span,
3105             |actual| {
3106                 if tuple_like {
3107                     format!("attempted out-of-bounds tuple index `{}` on \
3108                                     type `{}`",
3109                                    idx.node,
3110                                    actual)
3111                 } else {
3112                     format!("attempted tuple index `{}` on type `{}`, but the \
3113                                      type was not a tuple or tuple struct",
3114                                     idx.node,
3115                                     actual)
3116                 }
3117             },
3118             expr_t);
3119
3120         self.write_error(expr.id);
3121     }
3122
3123     fn report_unknown_field(&self,
3124                             ty: Ty<'tcx>,
3125                             variant: ty::VariantDef<'tcx>,
3126                             field: &hir::Field,
3127                             skip_fields: &[hir::Field]) {
3128         let mut err = self.type_error_struct_with_diag(
3129             field.name.span,
3130             |actual| if let ty::TyEnum(..) = ty.sty {
3131                 struct_span_err!(self.tcx.sess, field.name.span, E0559,
3132                                  "struct variant `{}::{}` has no field named `{}`",
3133                                  actual, variant.name.as_str(), field.name.node)
3134             } else {
3135                 struct_span_err!(self.tcx.sess, field.name.span, E0560,
3136                                  "structure `{}` has no field named `{}`",
3137                                  actual, field.name.node)
3138             },
3139             ty);
3140         // prevent all specified fields from being suggested
3141         let skip_fields = skip_fields.iter().map(|ref x| x.name.node.as_str());
3142         Self::suggest_field_names(&mut err, variant, &field.name, skip_fields.collect());
3143         err.emit();
3144     }
3145
3146     fn check_expr_struct_fields(&self,
3147                                 adt_ty: Ty<'tcx>,
3148                                 span: Span,
3149                                 variant: ty::VariantDef<'tcx>,
3150                                 ast_fields: &'gcx [hir::Field],
3151                                 check_completeness: bool) {
3152         let tcx = self.tcx;
3153         let substs = match adt_ty.sty {
3154             ty::TyStruct(_, substs) | ty::TyEnum(_, substs) => substs,
3155             _ => span_bug!(span, "non-ADT passed to check_expr_struct_fields")
3156         };
3157
3158         let mut remaining_fields = FnvHashMap();
3159         for field in &variant.fields {
3160             remaining_fields.insert(field.name, field);
3161         }
3162
3163         let mut seen_fields = FnvHashMap();
3164
3165         let mut error_happened = false;
3166
3167         // Typecheck each field.
3168         for field in ast_fields {
3169             let expected_field_type;
3170
3171             if let Some(v_field) = remaining_fields.remove(&field.name.node) {
3172                 expected_field_type = self.field_ty(field.span, v_field, substs);
3173
3174                 seen_fields.insert(field.name.node, field.span);
3175             } else {
3176                 error_happened = true;
3177                 expected_field_type = tcx.types.err;
3178                 if let Some(_) = variant.find_field_named(field.name.node) {
3179                     let mut err = struct_span_err!(self.tcx.sess,
3180                                                 field.name.span,
3181                                                 E0062,
3182                                                 "field `{}` specified more than once",
3183                                                 field.name.node);
3184
3185                     err.span_label(field.name.span, &format!("used more than once"));
3186
3187                     if let Some(prev_span) = seen_fields.get(&field.name.node) {
3188                         err.span_label(*prev_span, &format!("first use of `{}`", field.name.node));
3189                     }
3190
3191                     err.emit();
3192                 } else {
3193                     self.report_unknown_field(adt_ty, variant, field, ast_fields);
3194                 }
3195             }
3196
3197             // Make sure to give a type to the field even if there's
3198             // an error, so we can continue typechecking
3199             self.check_expr_coercable_to_type(&field.expr, expected_field_type);
3200         }
3201
3202             // Make sure the programmer specified all the fields.
3203         if check_completeness &&
3204             !error_happened &&
3205             !remaining_fields.is_empty()
3206         {
3207             span_err!(tcx.sess, span, E0063,
3208                       "missing field{} {} in initializer of `{}`",
3209                       if remaining_fields.len() == 1 {""} else {"s"},
3210                       remaining_fields.keys()
3211                                       .map(|n| format!("`{}`", n))
3212                                       .collect::<Vec<_>>()
3213                                       .join(", "),
3214                       adt_ty);
3215         }
3216
3217     }
3218
3219     fn check_struct_fields_on_error(&self,
3220                                     id: ast::NodeId,
3221                                     fields: &'gcx [hir::Field],
3222                                     base_expr: &'gcx Option<P<hir::Expr>>) {
3223         // Make sure to still write the types
3224         // otherwise we might ICE
3225         self.write_error(id);
3226         for field in fields {
3227             self.check_expr(&field.expr);
3228         }
3229         match *base_expr {
3230             Some(ref base) => self.check_expr(&base),
3231             None => {}
3232         }
3233     }
3234
3235     pub fn check_struct_path(&self,
3236                          path: &hir::Path,
3237                          node_id: ast::NodeId,
3238                          span: Span)
3239                          -> Option<(ty::VariantDef<'tcx>,  Ty<'tcx>)> {
3240         let def = self.finish_resolving_struct_path(path, node_id, span);
3241         let variant = match def {
3242             Def::Err => {
3243                 self.set_tainted_by_errors();
3244                 return None;
3245             }
3246             Def::Variant(type_did, _) | Def::Struct(type_did) => {
3247                 Some((type_did, self.tcx.expect_variant_def(def)))
3248             }
3249             Def::TyAlias(did) => {
3250                 if let Some(&ty::TyStruct(adt, _)) = self.tcx.opt_lookup_item_type(did)
3251                                                              .map(|scheme| &scheme.ty.sty) {
3252                     Some((did, adt.struct_variant()))
3253                 } else {
3254                     None
3255                 }
3256             }
3257             _ => None
3258         };
3259
3260         if let Some((def_id, variant)) = variant {
3261             if variant.kind == ty::VariantKind::Tuple &&
3262                     !self.tcx.sess.features.borrow().relaxed_adts {
3263                 emit_feature_err(&self.tcx.sess.parse_sess.span_diagnostic,
3264                                  "relaxed_adts", span, GateIssue::Language,
3265                                  "tuple structs and variants in struct patterns are unstable");
3266             }
3267             let ty = self.instantiate_type_path(def_id, path, node_id);
3268             Some((variant, ty))
3269         } else {
3270             struct_span_err!(self.tcx.sess, path.span, E0071,
3271                              "`{}` does not name a struct or a struct variant",
3272                              pprust::path_to_string(path))
3273                 .span_label(path.span, &format!("not a struct"))
3274                 .emit();
3275             None
3276         }
3277     }
3278
3279     fn check_expr_struct(&self,
3280                          expr: &hir::Expr,
3281                          path: &hir::Path,
3282                          fields: &'gcx [hir::Field],
3283                          base_expr: &'gcx Option<P<hir::Expr>>)
3284     {
3285         // Find the relevant variant
3286         let (variant, expr_ty) = if let Some(variant_ty) = self.check_struct_path(path, expr.id,
3287                                                                                   expr.span) {
3288             variant_ty
3289         } else {
3290             self.check_struct_fields_on_error(expr.id, fields, base_expr);
3291             return;
3292         };
3293
3294         self.check_expr_struct_fields(expr_ty, path.span, variant, fields,
3295                                       base_expr.is_none());
3296         if let &Some(ref base_expr) = base_expr {
3297             self.check_expr_has_type(base_expr, expr_ty);
3298             match expr_ty.sty {
3299                 ty::TyStruct(adt, substs) => {
3300                     self.tables.borrow_mut().fru_field_types.insert(
3301                         expr.id,
3302                         adt.struct_variant().fields.iter().map(|f| {
3303                             self.normalize_associated_types_in(
3304                                 expr.span, &f.ty(self.tcx, substs)
3305                             )
3306                         }).collect()
3307                     );
3308                 }
3309                 _ => {
3310                     span_err!(self.tcx.sess, base_expr.span, E0436,
3311                               "functional record update syntax requires a struct");
3312                 }
3313             }
3314         }
3315     }
3316
3317
3318     /// Invariant:
3319     /// If an expression has any sub-expressions that result in a type error,
3320     /// inspecting that expression's type with `ty.references_error()` will return
3321     /// true. Likewise, if an expression is known to diverge, inspecting its
3322     /// type with `ty::type_is_bot` will return true (n.b.: since Rust is
3323     /// strict, _|_ can appear in the type of an expression that does not,
3324     /// itself, diverge: for example, fn() -> _|_.)
3325     /// Note that inspecting a type's structure *directly* may expose the fact
3326     /// that there are actually multiple representations for `TyError`, so avoid
3327     /// that when err needs to be handled differently.
3328     fn check_expr_with_expectation_and_lvalue_pref(&self,
3329                                                    expr: &'gcx hir::Expr,
3330                                                    expected: Expectation<'tcx>,
3331                                                    lvalue_pref: LvaluePreference) {
3332         debug!(">> typechecking: expr={:?} expected={:?}",
3333                expr, expected);
3334
3335         let tcx = self.tcx;
3336         let id = expr.id;
3337         match expr.node {
3338           hir::ExprBox(ref subexpr) => {
3339             let expected_inner = expected.to_option(self).map_or(NoExpectation, |ty| {
3340                 match ty.sty {
3341                     ty::TyBox(ty) => Expectation::rvalue_hint(self, ty),
3342                     _ => NoExpectation
3343                 }
3344             });
3345             self.check_expr_with_expectation(subexpr, expected_inner);
3346             let referent_ty = self.expr_ty(&subexpr);
3347             self.write_ty(id, tcx.mk_box(referent_ty));
3348           }
3349
3350           hir::ExprLit(ref lit) => {
3351             let typ = self.check_lit(&lit, expected);
3352             self.write_ty(id, typ);
3353           }
3354           hir::ExprBinary(op, ref lhs, ref rhs) => {
3355             self.check_binop(expr, op, lhs, rhs);
3356           }
3357           hir::ExprAssignOp(op, ref lhs, ref rhs) => {
3358             self.check_binop_assign(expr, op, lhs, rhs);
3359           }
3360           hir::ExprUnary(unop, ref oprnd) => {
3361             let expected_inner = match unop {
3362                 hir::UnNot | hir::UnNeg => {
3363                     expected
3364                 }
3365                 hir::UnDeref => {
3366                     NoExpectation
3367                 }
3368             };
3369             let lvalue_pref = match unop {
3370                 hir::UnDeref => lvalue_pref,
3371                 _ => NoPreference
3372             };
3373             self.check_expr_with_expectation_and_lvalue_pref(&oprnd,
3374                                                              expected_inner,
3375                                                              lvalue_pref);
3376             let mut oprnd_t = self.expr_ty(&oprnd);
3377
3378             if !oprnd_t.references_error() {
3379                 match unop {
3380                     hir::UnDeref => {
3381                         oprnd_t = self.structurally_resolved_type(expr.span, oprnd_t);
3382
3383                         if let Some(mt) = oprnd_t.builtin_deref(true, NoPreference) {
3384                             oprnd_t = mt.ty;
3385                         } else if let Some(method) = self.try_overloaded_deref(
3386                                 expr.span, Some(&oprnd), oprnd_t, lvalue_pref) {
3387                             oprnd_t = self.make_overloaded_lvalue_return_type(method).ty;
3388                             self.tables.borrow_mut().method_map.insert(MethodCall::expr(expr.id),
3389                                                                            method);
3390                         } else {
3391                             self.type_error_message(expr.span, |actual| {
3392                                 format!("type `{}` cannot be \
3393                                         dereferenced", actual)
3394                             }, oprnd_t);
3395                             oprnd_t = tcx.types.err;
3396                         }
3397                     }
3398                     hir::UnNot => {
3399                         oprnd_t = self.structurally_resolved_type(oprnd.span,
3400                                                                   oprnd_t);
3401                         if !(oprnd_t.is_integral() || oprnd_t.sty == ty::TyBool) {
3402                             oprnd_t = self.check_user_unop("!", "not",
3403                                                            tcx.lang_items.not_trait(),
3404                                                            expr, &oprnd, oprnd_t, unop);
3405                         }
3406                     }
3407                     hir::UnNeg => {
3408                         oprnd_t = self.structurally_resolved_type(oprnd.span,
3409                                                                   oprnd_t);
3410                         if !(oprnd_t.is_integral() || oprnd_t.is_fp()) {
3411                             oprnd_t = self.check_user_unop("-", "neg",
3412                                                            tcx.lang_items.neg_trait(),
3413                                                            expr, &oprnd, oprnd_t, unop);
3414                         }
3415                     }
3416                 }
3417             }
3418             self.write_ty(id, oprnd_t);
3419           }
3420           hir::ExprAddrOf(mutbl, ref oprnd) => {
3421             let hint = expected.only_has_type(self).map_or(NoExpectation, |ty| {
3422                 match ty.sty {
3423                     ty::TyRef(_, ref mt) | ty::TyRawPtr(ref mt) => {
3424                         if self.tcx.expr_is_lval(&oprnd) {
3425                             // Lvalues may legitimately have unsized types.
3426                             // For example, dereferences of a fat pointer and
3427                             // the last field of a struct can be unsized.
3428                             ExpectHasType(mt.ty)
3429                         } else {
3430                             Expectation::rvalue_hint(self, mt.ty)
3431                         }
3432                     }
3433                     _ => NoExpectation
3434                 }
3435             });
3436             let lvalue_pref = LvaluePreference::from_mutbl(mutbl);
3437             self.check_expr_with_expectation_and_lvalue_pref(&oprnd, hint, lvalue_pref);
3438
3439             let tm = ty::TypeAndMut { ty: self.expr_ty(&oprnd), mutbl: mutbl };
3440             let oprnd_t = if tm.ty.references_error() {
3441                 tcx.types.err
3442             } else {
3443                 // Note: at this point, we cannot say what the best lifetime
3444                 // is to use for resulting pointer.  We want to use the
3445                 // shortest lifetime possible so as to avoid spurious borrowck
3446                 // errors.  Moreover, the longest lifetime will depend on the
3447                 // precise details of the value whose address is being taken
3448                 // (and how long it is valid), which we don't know yet until type
3449                 // inference is complete.
3450                 //
3451                 // Therefore, here we simply generate a region variable.  The
3452                 // region inferencer will then select the ultimate value.
3453                 // Finally, borrowck is charged with guaranteeing that the
3454                 // value whose address was taken can actually be made to live
3455                 // as long as it needs to live.
3456                 let region = self.next_region_var(infer::AddrOfRegion(expr.span));
3457                 tcx.mk_ref(region, tm)
3458             };
3459             self.write_ty(id, oprnd_t);
3460           }
3461           hir::ExprPath(ref opt_qself, ref path) => {
3462               let opt_self_ty = opt_qself.as_ref().map(|qself| self.to_ty(&qself.ty));
3463               let (def, opt_ty, segments) = self.resolve_ty_and_def_ufcs(opt_self_ty, path,
3464                                                                          expr.id, expr.span);
3465               if def != Def::Err {
3466                   self.instantiate_value_path(segments, opt_ty, def, expr.span, id);
3467               } else {
3468                   self.set_tainted_by_errors();
3469                   self.write_error(id);
3470               }
3471
3472               // We always require that the type provided as the value for
3473               // a type parameter outlives the moment of instantiation.
3474               self.opt_node_ty_substs(expr.id, |item_substs| {
3475                   self.add_wf_bounds(&item_substs.substs, expr);
3476               });
3477           }
3478           hir::ExprInlineAsm(_, ref outputs, ref inputs) => {
3479               for output in outputs {
3480                   self.check_expr(output);
3481               }
3482               for input in inputs {
3483                   self.check_expr(input);
3484               }
3485               self.write_nil(id);
3486           }
3487           hir::ExprBreak(_) => { self.write_never(id); }
3488           hir::ExprAgain(_) => { self.write_never(id); }
3489           hir::ExprRet(ref expr_opt) => {
3490             if let Some(ref e) = *expr_opt {
3491                 self.check_expr_coercable_to_type(&e, self.ret_ty);
3492             } else {
3493                 let eq_result = self.eq_types(false,
3494                                               TypeOrigin::Misc(expr.span),
3495                                               self.ret_ty,
3496                                               tcx.mk_nil())
3497                     // FIXME(#32730) propagate obligations
3498                     .map(|InferOk { obligations, .. }| assert!(obligations.is_empty()));
3499                 if eq_result.is_err() {
3500                     struct_span_err!(tcx.sess, expr.span, E0069,
3501                              "`return;` in a function whose return type is not `()`")
3502                         .span_label(expr.span, &format!("return type is not ()"))
3503                         .emit();
3504                 }
3505             }
3506             self.write_never(id);
3507           }
3508           hir::ExprAssign(ref lhs, ref rhs) => {
3509             self.check_expr_with_lvalue_pref(&lhs, PreferMutLvalue);
3510
3511             let tcx = self.tcx;
3512             if !tcx.expr_is_lval(&lhs) {
3513                 struct_span_err!(
3514                     tcx.sess, expr.span, E0070,
3515                     "invalid left-hand side expression")
3516                 .span_label(
3517                     expr.span,
3518                     &format!("left-hand of expression not valid"))
3519                 .emit();
3520             }
3521
3522             let lhs_ty = self.expr_ty(&lhs);
3523             self.check_expr_coercable_to_type(&rhs, lhs_ty);
3524             let rhs_ty = self.expr_ty(&rhs);
3525
3526             self.require_expr_have_sized_type(&lhs, traits::AssignmentLhsSized);
3527
3528             if lhs_ty.references_error() || rhs_ty.references_error() {
3529                 self.write_error(id);
3530             } else {
3531                 self.write_nil(id);
3532             }
3533           }
3534           hir::ExprIf(ref cond, ref then_blk, ref opt_else_expr) => {
3535             self.check_then_else(&cond, &then_blk, opt_else_expr.as_ref().map(|e| &**e),
3536                                  id, expr.span, expected);
3537           }
3538           hir::ExprWhile(ref cond, ref body, _) => {
3539             self.check_expr_has_type(&cond, tcx.types.bool);
3540             self.check_block_no_value(&body);
3541             let cond_ty = self.expr_ty(&cond);
3542             let body_ty = self.node_ty(body.id);
3543             if cond_ty.references_error() || body_ty.references_error() {
3544                 self.write_error(id);
3545             }
3546             else {
3547                 self.write_nil(id);
3548             }
3549           }
3550           hir::ExprLoop(ref body, _) => {
3551             self.check_block_no_value(&body);
3552             if !may_break(tcx, expr.id, &body) {
3553                 self.write_never(id);
3554             } else {
3555                 self.write_nil(id);
3556             }
3557           }
3558           hir::ExprMatch(ref discrim, ref arms, match_src) => {
3559             self.check_match(expr, &discrim, arms, expected, match_src);
3560           }
3561           hir::ExprClosure(capture, ref decl, ref body, _) => {
3562               self.check_expr_closure(expr, capture, &decl, &body, expected);
3563           }
3564           hir::ExprBlock(ref b) => {
3565             self.check_block_with_expected(&b, expected);
3566             self.write_ty(id, self.node_ty(b.id));
3567           }
3568           hir::ExprCall(ref callee, ref args) => {
3569               self.check_call(expr, &callee, &args[..], expected);
3570
3571               // we must check that return type of called functions is WF:
3572               let ret_ty = self.expr_ty(expr);
3573               self.register_wf_obligation(ret_ty, expr.span, traits::MiscObligation);
3574           }
3575           hir::ExprMethodCall(name, ref tps, ref args) => {
3576               self.check_method_call(expr, name, &args[..], &tps[..], expected, lvalue_pref);
3577               let arg_tys = args.iter().map(|a| self.expr_ty(&a));
3578               let args_err = arg_tys.fold(false, |rest_err, a| rest_err || a.references_error());
3579               if args_err {
3580                   self.write_error(id);
3581               }
3582           }
3583           hir::ExprCast(ref e, ref t) => {
3584             if let hir::TyFixedLengthVec(_, ref count_expr) = t.node {
3585                 self.check_expr_with_hint(&count_expr, tcx.types.usize);
3586             }
3587
3588             // Find the type of `e`. Supply hints based on the type we are casting to,
3589             // if appropriate.
3590             let t_cast = self.to_ty(t);
3591             let t_cast = self.resolve_type_vars_if_possible(&t_cast);
3592             self.check_expr_with_expectation(e, ExpectCastableToType(t_cast));
3593             let t_expr = self.expr_ty(e);
3594             let t_cast = self.resolve_type_vars_if_possible(&t_cast);
3595
3596             // Eagerly check for some obvious errors.
3597             if t_expr.references_error() || t_cast.references_error() {
3598                 self.write_error(id);
3599             } else {
3600                 // Write a type for the whole expression, assuming everything is going
3601                 // to work out Ok.
3602                 self.write_ty(id, t_cast);
3603
3604                 // Defer other checks until we're done type checking.
3605                 let mut deferred_cast_checks = self.deferred_cast_checks.borrow_mut();
3606                 match cast::CastCheck::new(self, e, t_expr, t_cast, t.span, expr.span) {
3607                     Ok(cast_check) => {
3608                         deferred_cast_checks.push(cast_check);
3609                     }
3610                     Err(ErrorReported) => {
3611                         self.write_error(id);
3612                     }
3613                 }
3614             }
3615           }
3616           hir::ExprType(ref e, ref t) => {
3617             let typ = self.to_ty(&t);
3618             self.check_expr_eq_type(&e, typ);
3619             self.write_ty(id, typ);
3620           }
3621           hir::ExprVec(ref args) => {
3622             let uty = expected.to_option(self).and_then(|uty| {
3623                 match uty.sty {
3624                     ty::TyArray(ty, _) | ty::TySlice(ty) => Some(ty),
3625                     _ => None
3626                 }
3627             });
3628
3629             let mut unified = self.next_ty_var();
3630             let coerce_to = uty.unwrap_or(unified);
3631
3632             for (i, e) in args.iter().enumerate() {
3633                 self.check_expr_with_hint(e, coerce_to);
3634                 let e_ty = self.expr_ty(e);
3635                 let origin = TypeOrigin::Misc(e.span);
3636
3637                 // Special-case the first element, as it has no "previous expressions".
3638                 let result = if i == 0 {
3639                     self.try_coerce(e, coerce_to)
3640                 } else {
3641                     let prev_elems = || args[..i].iter().map(|e| &**e);
3642                     self.try_find_coercion_lub(origin, prev_elems, unified, e)
3643                 };
3644
3645                 match result {
3646                     Ok(ty) => unified = ty,
3647                     Err(e) => {
3648                         self.report_mismatched_types(origin, unified, e_ty, e);
3649                     }
3650                 }
3651             }
3652             self.write_ty(id, tcx.mk_array(unified, args.len()));
3653           }
3654           hir::ExprRepeat(ref element, ref count_expr) => {
3655             self.check_expr_has_type(&count_expr, tcx.types.usize);
3656             let count = eval_length(self.tcx.global_tcx(), &count_expr, "repeat count")
3657                   .unwrap_or(0);
3658
3659             let uty = match expected {
3660                 ExpectHasType(uty) => {
3661                     match uty.sty {
3662                         ty::TyArray(ty, _) | ty::TySlice(ty) => Some(ty),
3663                         _ => None
3664                     }
3665                 }
3666                 _ => None
3667             };
3668
3669             let (element_ty, t) = match uty {
3670                 Some(uty) => {
3671                     self.check_expr_coercable_to_type(&element, uty);
3672                     (uty, uty)
3673                 }
3674                 None => {
3675                     let t: Ty = self.next_ty_var();
3676                     self.check_expr_has_type(&element, t);
3677                     (self.expr_ty(&element), t)
3678                 }
3679             };
3680
3681             if count > 1 {
3682                 // For [foo, ..n] where n > 1, `foo` must have
3683                 // Copy type:
3684                 self.require_type_meets(t, expr.span, traits::RepeatVec, ty::BoundCopy);
3685             }
3686
3687             if element_ty.references_error() {
3688                 self.write_error(id);
3689             } else {
3690                 let t = tcx.mk_array(t, count);
3691                 self.write_ty(id, t);
3692             }
3693           }
3694           hir::ExprTup(ref elts) => {
3695             let flds = expected.only_has_type(self).and_then(|ty| {
3696                 match ty.sty {
3697                     ty::TyTuple(ref flds) => Some(&flds[..]),
3698                     _ => None
3699                 }
3700             });
3701             let mut err_field = false;
3702
3703             let elt_ts = elts.iter().enumerate().map(|(i, e)| {
3704                 let t = match flds {
3705                     Some(ref fs) if i < fs.len() => {
3706                         let ety = fs[i];
3707                         self.check_expr_coercable_to_type(&e, ety);
3708                         ety
3709                     }
3710                     _ => {
3711                         self.check_expr_with_expectation(&e, NoExpectation);
3712                         self.expr_ty(&e)
3713                     }
3714                 };
3715                 err_field = err_field || t.references_error();
3716                 t
3717             }).collect();
3718             if err_field {
3719                 self.write_error(id);
3720             } else {
3721                 let typ = tcx.mk_tup(elt_ts);
3722                 self.write_ty(id, typ);
3723             }
3724           }
3725           hir::ExprStruct(ref path, ref fields, ref base_expr) => {
3726             self.check_expr_struct(expr, path, fields, base_expr);
3727
3728             self.require_expr_have_sized_type(expr, traits::StructInitializerSized);
3729           }
3730           hir::ExprField(ref base, ref field) => {
3731             self.check_field(expr, lvalue_pref, &base, field);
3732           }
3733           hir::ExprTupField(ref base, idx) => {
3734             self.check_tup_field(expr, lvalue_pref, &base, idx);
3735           }
3736           hir::ExprIndex(ref base, ref idx) => {
3737               self.check_expr_with_lvalue_pref(&base, lvalue_pref);
3738               self.check_expr(&idx);
3739
3740               let base_t = self.expr_ty(&base);
3741               let idx_t = self.expr_ty(&idx);
3742
3743               if base_t.references_error() {
3744                   self.write_ty(id, base_t);
3745               } else if idx_t.references_error() {
3746                   self.write_ty(id, idx_t);
3747               } else {
3748                   let base_t = self.structurally_resolved_type(expr.span, base_t);
3749                   match self.lookup_indexing(expr, base, base_t, idx_t, lvalue_pref) {
3750                       Some((index_ty, element_ty)) => {
3751                           let idx_expr_ty = self.expr_ty(idx);
3752                           self.demand_eqtype(expr.span, index_ty, idx_expr_ty);
3753                           self.write_ty(id, element_ty);
3754                       }
3755                       None => {
3756                           self.check_expr_has_type(&idx, self.tcx.types.err);
3757                           let mut err = self.type_error_struct(
3758                               expr.span,
3759                               |actual| {
3760                                   format!("cannot index a value of type `{}`",
3761                                           actual)
3762                               },
3763                               base_t);
3764                           // Try to give some advice about indexing tuples.
3765                           if let ty::TyTuple(_) = base_t.sty {
3766                               let mut needs_note = true;
3767                               // If the index is an integer, we can show the actual
3768                               // fixed expression:
3769                               if let hir::ExprLit(ref lit) = idx.node {
3770                                   if let ast::LitKind::Int(i,
3771                                             ast::LitIntType::Unsuffixed) = lit.node {
3772                                       let snip = tcx.sess.codemap().span_to_snippet(base.span);
3773                                       if let Ok(snip) = snip {
3774                                           err.span_suggestion(expr.span,
3775                                                               "to access tuple elements, \
3776                                                                use tuple indexing syntax \
3777                                                                as shown",
3778                                                               format!("{}.{}", snip, i));
3779                                           needs_note = false;
3780                                       }
3781                                   }
3782                               }
3783                               if needs_note {
3784                                   err.help("to access tuple elements, use tuple indexing \
3785                                             syntax (e.g. `tuple.0`)");
3786                               }
3787                           }
3788                           err.emit();
3789                           self.write_ty(id, self.tcx().types.err);
3790                       }
3791                   }
3792               }
3793            }
3794         }
3795
3796         debug!("type of expr({}) {} is...", expr.id,
3797                pprust::expr_to_string(expr));
3798         debug!("... {:?}, expected is {:?}",
3799                self.expr_ty(expr),
3800                expected);
3801     }
3802
3803     // Finish resolving a path in a struct expression or pattern `S::A { .. }` if necessary.
3804     // The newly resolved definition is written into `def_map`.
3805     pub fn finish_resolving_struct_path(&self,
3806                                         path: &hir::Path,
3807                                         node_id: ast::NodeId,
3808                                         span: Span)
3809                                         -> Def
3810     {
3811         let path_res = self.tcx().expect_resolution(node_id);
3812         if path_res.depth == 0 {
3813             // If fully resolved already, we don't have to do anything.
3814             path_res.base_def
3815         } else {
3816             let base_ty_end = path.segments.len() - path_res.depth;
3817             let (_ty, def) = AstConv::finish_resolving_def_to_ty(self, self, span,
3818                                                                  PathParamMode::Optional,
3819                                                                  path_res.base_def,
3820                                                                  None,
3821                                                                  node_id,
3822                                                                  &path.segments[..base_ty_end],
3823                                                                  &path.segments[base_ty_end..]);
3824             // Write back the new resolution.
3825             self.tcx().def_map.borrow_mut().insert(node_id, PathResolution::new(def));
3826             def
3827         }
3828     }
3829
3830     // Resolve associated value path into a base type and associated constant or method definition.
3831     // The newly resolved definition is written into `def_map`.
3832     pub fn resolve_ty_and_def_ufcs<'b>(&self,
3833                                        opt_self_ty: Option<Ty<'tcx>>,
3834                                        path: &'b hir::Path,
3835                                        node_id: ast::NodeId,
3836                                        span: Span)
3837                                        -> (Def, Option<Ty<'tcx>>, &'b [hir::PathSegment])
3838     {
3839         let path_res = self.tcx().expect_resolution(node_id);
3840         if path_res.depth == 0 {
3841             // If fully resolved already, we don't have to do anything.
3842             (path_res.base_def, opt_self_ty, &path.segments)
3843         } else {
3844             // Try to resolve everything except for the last segment as a type.
3845             let ty_segments = path.segments.split_last().unwrap().1;
3846             let base_ty_end = path.segments.len() - path_res.depth;
3847             let (ty, _def) = AstConv::finish_resolving_def_to_ty(self, self, span,
3848                                                                  PathParamMode::Optional,
3849                                                                  path_res.base_def,
3850                                                                  opt_self_ty,
3851                                                                  node_id,
3852                                                                  &ty_segments[..base_ty_end],
3853                                                                  &ty_segments[base_ty_end..]);
3854
3855             // Resolve an associated constant or method on the previously resolved type.
3856             let item_segment = path.segments.last().unwrap();
3857             let item_name = item_segment.name;
3858             let def = match self.resolve_ufcs(span, item_name, ty, node_id) {
3859                 Ok(def) => def,
3860                 Err(error) => {
3861                     let def = match error {
3862                         method::MethodError::PrivateMatch(def) => def,
3863                         _ => Def::Err,
3864                     };
3865                     if item_name != keywords::Invalid.name() {
3866                         self.report_method_error(span, ty, item_name, None, error);
3867                     }
3868                     def
3869                 }
3870             };
3871
3872             // Write back the new resolution.
3873             self.tcx().def_map.borrow_mut().insert(node_id, PathResolution::new(def));
3874             (def, Some(ty), slice::ref_slice(item_segment))
3875         }
3876     }
3877
3878     pub fn check_decl_initializer(&self,
3879                                   local: &'gcx hir::Local,
3880                                   init: &'gcx hir::Expr)
3881     {
3882         let ref_bindings = self.tcx.pat_contains_ref_binding(&local.pat);
3883
3884         let local_ty = self.local_ty(init.span, local.id);
3885         if let Some(m) = ref_bindings {
3886             // Somewhat subtle: if we have a `ref` binding in the pattern,
3887             // we want to avoid introducing coercions for the RHS. This is
3888             // both because it helps preserve sanity and, in the case of
3889             // ref mut, for soundness (issue #23116). In particular, in
3890             // the latter case, we need to be clear that the type of the
3891             // referent for the reference that results is *equal to* the
3892             // type of the lvalue it is referencing, and not some
3893             // supertype thereof.
3894             self.check_expr_with_lvalue_pref(init, LvaluePreference::from_mutbl(m));
3895             let init_ty = self.expr_ty(init);
3896             self.demand_eqtype(init.span, init_ty, local_ty);
3897         } else {
3898             self.check_expr_coercable_to_type(init, local_ty)
3899         };
3900     }
3901
3902     pub fn check_decl_local(&self, local: &'gcx hir::Local)  {
3903         let t = self.local_ty(local.span, local.id);
3904         self.write_ty(local.id, t);
3905
3906         if let Some(ref init) = local.init {
3907             self.check_decl_initializer(local, &init);
3908             let init_ty = self.expr_ty(&init);
3909             if init_ty.references_error() {
3910                 self.write_ty(local.id, init_ty);
3911             }
3912         }
3913
3914         self.check_pat(&local.pat, t);
3915         let pat_ty = self.node_ty(local.pat.id);
3916         if pat_ty.references_error() {
3917             self.write_ty(local.id, pat_ty);
3918         }
3919     }
3920
3921     pub fn check_stmt(&self, stmt: &'gcx hir::Stmt)  {
3922         let node_id;
3923         let mut saw_bot = false;
3924         let mut saw_err = false;
3925         match stmt.node {
3926           hir::StmtDecl(ref decl, id) => {
3927             node_id = id;
3928             match decl.node {
3929               hir::DeclLocal(ref l) => {
3930                   self.check_decl_local(&l);
3931                   let l_t = self.node_ty(l.id);
3932                   saw_bot = saw_bot || self.type_var_diverges(l_t);
3933                   saw_err = saw_err || l_t.references_error();
3934               }
3935               hir::DeclItem(_) => {/* ignore for now */ }
3936             }
3937           }
3938           hir::StmtExpr(ref expr, id) => {
3939             node_id = id;
3940             // Check with expected type of ()
3941             self.check_expr_has_type(&expr, self.tcx.mk_nil());
3942             let expr_ty = self.expr_ty(&expr);
3943             saw_bot = saw_bot || self.type_var_diverges(expr_ty);
3944             saw_err = saw_err || expr_ty.references_error();
3945           }
3946           hir::StmtSemi(ref expr, id) => {
3947             node_id = id;
3948             self.check_expr(&expr);
3949             let expr_ty = self.expr_ty(&expr);
3950             saw_bot |= self.type_var_diverges(expr_ty);
3951             saw_err |= expr_ty.references_error();
3952           }
3953         }
3954         if saw_bot {
3955             self.write_ty(node_id, self.next_diverging_ty_var());
3956         }
3957         else if saw_err {
3958             self.write_error(node_id);
3959         }
3960         else {
3961             self.write_nil(node_id)
3962         }
3963     }
3964
3965     pub fn check_block_no_value(&self, blk: &'gcx hir::Block)  {
3966         self.check_block_with_expected(blk, ExpectHasType(self.tcx.mk_nil()));
3967         let blkty = self.node_ty(blk.id);
3968         if blkty.references_error() {
3969             self.write_error(blk.id);
3970         } else {
3971             let nilty = self.tcx.mk_nil();
3972             self.demand_suptype(blk.span, nilty, blkty);
3973         }
3974     }
3975
3976     fn check_block_with_expected(&self,
3977                                  blk: &'gcx hir::Block,
3978                                  expected: Expectation<'tcx>) {
3979         let prev = {
3980             let mut fcx_ps = self.ps.borrow_mut();
3981             let unsafety_state = fcx_ps.recurse(blk);
3982             replace(&mut *fcx_ps, unsafety_state)
3983         };
3984
3985         let mut warned = false;
3986         let mut any_diverges = false;
3987         let mut any_err = false;
3988         for s in &blk.stmts {
3989             self.check_stmt(s);
3990             let s_id = s.node.id();
3991             let s_ty = self.node_ty(s_id);
3992             if any_diverges && !warned && match s.node {
3993                 hir::StmtDecl(ref decl, _) => {
3994                     match decl.node {
3995                         hir::DeclLocal(_) => true,
3996                         _ => false,
3997                     }
3998                 }
3999                 hir::StmtExpr(_, _) | hir::StmtSemi(_, _) => true,
4000             } {
4001                 self.tcx
4002                     .sess
4003                     .add_lint(lint::builtin::UNREACHABLE_CODE,
4004                               s_id,
4005                               s.span,
4006                               "unreachable statement".to_string());
4007                 warned = true;
4008             }
4009             // FIXME(canndrew): This is_never should probably be an is_uninhabited
4010             any_diverges = any_diverges ||
4011                            self.type_var_diverges(s_ty) ||
4012                            s_ty.is_never();
4013             any_err = any_err || s_ty.references_error();
4014         }
4015         match blk.expr {
4016             None => if any_err {
4017                 self.write_error(blk.id);
4018             } else if any_diverges {
4019                 self.write_ty(blk.id, self.next_diverging_ty_var());
4020             } else {
4021                 self.write_nil(blk.id);
4022             },
4023             Some(ref e) => {
4024                 if any_diverges && !warned {
4025                     self.tcx
4026                         .sess
4027                         .add_lint(lint::builtin::UNREACHABLE_CODE,
4028                                   e.id,
4029                                   e.span,
4030                                   "unreachable expression".to_string());
4031                 }
4032                 let ety = match expected {
4033                     ExpectHasType(ety) => {
4034                         self.check_expr_coercable_to_type(&e, ety);
4035                         ety
4036                     }
4037                     _ => {
4038                         self.check_expr_with_expectation(&e, expected);
4039                         self.expr_ty(&e)
4040                     }
4041                 };
4042
4043                 if any_err {
4044                     self.write_error(blk.id);
4045                 } else if any_diverges {
4046                     self.write_ty(blk.id, self.next_diverging_ty_var());
4047                 } else {
4048                     self.write_ty(blk.id, ety);
4049                 }
4050             }
4051         };
4052
4053         *self.ps.borrow_mut() = prev;
4054     }
4055
4056     // Instantiates the given path, which must refer to an item with the given
4057     // number of type parameters and type.
4058     pub fn instantiate_value_path(&self,
4059                                   segments: &[hir::PathSegment],
4060                                   opt_self_ty: Option<Ty<'tcx>>,
4061                                   def: Def,
4062                                   span: Span,
4063                                   node_id: ast::NodeId)
4064                                   -> Ty<'tcx> {
4065         debug!("instantiate_value_path(path={:?}, def={:?}, node_id={})",
4066                segments,
4067                def,
4068                node_id);
4069
4070         // We need to extract the type parameters supplied by the user in
4071         // the path `path`. Due to the current setup, this is a bit of a
4072         // tricky-process; the problem is that resolve only tells us the
4073         // end-point of the path resolution, and not the intermediate steps.
4074         // Luckily, we can (at least for now) deduce the intermediate steps
4075         // just from the end-point.
4076         //
4077         // There are basically four cases to consider:
4078         //
4079         // 1. Reference to a *type*, such as a struct or enum:
4080         //
4081         //        mod a { struct Foo<T> { ... } }
4082         //
4083         //    Because we don't allow types to be declared within one
4084         //    another, a path that leads to a type will always look like
4085         //    `a::b::Foo<T>` where `a` and `b` are modules. This implies
4086         //    that only the final segment can have type parameters, and
4087         //    they are located in the TypeSpace.
4088         //
4089         //    *Note:* Generally speaking, references to types don't
4090         //    actually pass through this function, but rather the
4091         //    `ast_ty_to_ty` function in `astconv`. However, in the case
4092         //    of struct patterns (and maybe literals) we do invoke
4093         //    `instantiate_value_path` to get the general type of an instance of
4094         //    a struct. (In these cases, there are actually no type
4095         //    parameters permitted at present, but perhaps we will allow
4096         //    them in the future.)
4097         //
4098         // 1b. Reference to an enum variant or tuple-like struct:
4099         //
4100         //        struct foo<T>(...)
4101         //        enum E<T> { foo(...) }
4102         //
4103         //    In these cases, the parameters are declared in the type
4104         //    space.
4105         //
4106         // 2. Reference to a *fn item*:
4107         //
4108         //        fn foo<T>() { }
4109         //
4110         //    In this case, the path will again always have the form
4111         //    `a::b::foo::<T>` where only the final segment should have
4112         //    type parameters. However, in this case, those parameters are
4113         //    declared on a value, and hence are in the `FnSpace`.
4114         //
4115         // 3. Reference to a *method*:
4116         //
4117         //        impl<A> SomeStruct<A> {
4118         //            fn foo<B>(...)
4119         //        }
4120         //
4121         //    Here we can have a path like
4122         //    `a::b::SomeStruct::<A>::foo::<B>`, in which case parameters
4123         //    may appear in two places. The penultimate segment,
4124         //    `SomeStruct::<A>`, contains parameters in TypeSpace, and the
4125         //    final segment, `foo::<B>` contains parameters in fn space.
4126         //
4127         // 4. Reference to an *associated const*:
4128         //
4129         // impl<A> AnotherStruct<A> {
4130         // const FOO: B = BAR;
4131         // }
4132         //
4133         // The path in this case will look like
4134         // `a::b::AnotherStruct::<A>::FOO`, so the penultimate segment
4135         // only will have parameters in TypeSpace.
4136         //
4137         // The first step then is to categorize the segments appropriately.
4138
4139         assert!(!segments.is_empty());
4140
4141         let mut ufcs_associated = None;
4142         let mut type_segment = None;
4143         let mut fn_segment = None;
4144         match def {
4145             // Case 1 and 1b. Reference to a *type* or *enum variant*.
4146             Def::Struct(def_id) |
4147             Def::Variant(_, def_id) |
4148             Def::Enum(def_id) |
4149             Def::TyAlias(def_id) |
4150             Def::AssociatedTy(_, def_id) |
4151             Def::Trait(def_id) => {
4152                 // Everything but the final segment should have no
4153                 // parameters at all.
4154                 let mut generics = self.tcx.lookup_generics(def_id);
4155                 if let Some(def_id) = generics.parent {
4156                     // Variant and struct constructors use the
4157                     // generics of their parent type definition.
4158                     generics = self.tcx.lookup_generics(def_id);
4159                 }
4160                 type_segment = Some((segments.last().unwrap(), generics));
4161             }
4162
4163             // Case 2. Reference to a top-level value.
4164             Def::Fn(def_id) |
4165             Def::Const(def_id) |
4166             Def::Static(def_id, _) => {
4167                 fn_segment = Some((segments.last().unwrap(),
4168                                    self.tcx.lookup_generics(def_id)));
4169             }
4170
4171             // Case 3. Reference to a method or associated const.
4172             Def::Method(def_id) |
4173             Def::AssociatedConst(def_id) => {
4174                 let container = self.tcx.impl_or_trait_item(def_id).container();
4175                 match container {
4176                     ty::TraitContainer(trait_did) => {
4177                         callee::check_legal_trait_for_method_call(self.ccx, span, trait_did)
4178                     }
4179                     ty::ImplContainer(_) => {}
4180                 }
4181
4182                 let generics = self.tcx.lookup_generics(def_id);
4183                 if segments.len() >= 2 {
4184                     let parent_generics = self.tcx.lookup_generics(generics.parent.unwrap());
4185                     type_segment = Some((&segments[segments.len() - 2], parent_generics));
4186                 } else {
4187                     // `<T>::assoc` will end up here, and so can `T::assoc`.
4188                     let self_ty = opt_self_ty.expect("UFCS sugared assoc missing Self");
4189                     ufcs_associated = Some((container, self_ty));
4190                 }
4191                 fn_segment = Some((segments.last().unwrap(), generics));
4192             }
4193
4194             // Other cases. Various nonsense that really shouldn't show up
4195             // here. If they do, an error will have been reported
4196             // elsewhere. (I hope)
4197             Def::Mod(..) |
4198             Def::ForeignMod(..) |
4199             Def::PrimTy(..) |
4200             Def::SelfTy(..) |
4201             Def::TyParam(..) |
4202             Def::Local(..) |
4203             Def::Label(..) |
4204             Def::Upvar(..) |
4205             Def::Err => {}
4206         }
4207
4208         // In `<T as Trait<A, B>>::method`, `A` and `B` are mandatory, but
4209         // `opt_self_ty` can also be Some for `Foo::method`, where Foo's
4210         // type parameters are not mandatory.
4211         let require_type_space = opt_self_ty.is_some() && ufcs_associated.is_none();
4212
4213         debug!("type_segment={:?} fn_segment={:?}", type_segment, fn_segment);
4214
4215         // Now that we have categorized what space the parameters for each
4216         // segment belong to, let's sort out the parameters that the user
4217         // provided (if any) into their appropriate spaces. We'll also report
4218         // errors if type parameters are provided in an inappropriate place.
4219         let poly_segments = type_segment.is_some() as usize +
4220                             fn_segment.is_some() as usize;
4221         self.tcx.prohibit_type_params(&segments[..segments.len() - poly_segments]);
4222
4223         match def {
4224             Def::Local(_, nid) | Def::Upvar(_, nid, _, _) => {
4225                 let ty = self.local_ty(span, nid);
4226                 let ty = self.normalize_associated_types_in(span, &ty);
4227                 self.write_ty(node_id, ty);
4228                 self.write_substs(node_id, ty::ItemSubsts {
4229                     substs: Substs::empty(self.tcx)
4230                 });
4231                 return ty;
4232             }
4233             _ => {}
4234         }
4235
4236         // Now we have to compare the types that the user *actually*
4237         // provided against the types that were *expected*. If the user
4238         // did not provide any types, then we want to substitute inference
4239         // variables. If the user provided some types, we may still need
4240         // to add defaults. If the user provided *too many* types, that's
4241         // a problem.
4242         self.check_path_parameter_count(span, !require_type_space, &mut type_segment);
4243         self.check_path_parameter_count(span, true, &mut fn_segment);
4244
4245         let (fn_start, has_self) = match (type_segment, fn_segment) {
4246             (_, Some((_, generics))) => {
4247                 (generics.parent_count(), generics.has_self)
4248             }
4249             (Some((_, generics)), None) => {
4250                 (generics.own_count(), generics.has_self)
4251             }
4252             (None, None) => (0, false)
4253         };
4254         let substs = Substs::for_item(self.tcx, def.def_id(), |def, _| {
4255             let mut i = def.index as usize;
4256
4257             let segment = if i < fn_start {
4258                 i -= has_self as usize;
4259                 type_segment
4260             } else {
4261                 i -= fn_start;
4262                 fn_segment
4263             };
4264             let lifetimes = match segment.map(|(s, _)| &s.parameters) {
4265                 Some(&hir::AngleBracketedParameters(ref data)) => &data.lifetimes[..],
4266                 Some(&hir::ParenthesizedParameters(_)) => bug!(),
4267                 None => &[]
4268             };
4269
4270             if let Some(ast_lifetime) = lifetimes.get(i) {
4271                 ast_region_to_region(self.tcx, ast_lifetime)
4272             } else {
4273                 self.region_var_for_def(span, def)
4274             }
4275         }, |def, substs| {
4276             let mut i = def.index as usize;
4277
4278             let can_omit = i >= fn_start || !require_type_space;
4279             let segment = if i < fn_start {
4280                 // Handle Self first, so we can adjust the index to match the AST.
4281                 if has_self && i == 0 {
4282                     return opt_self_ty.unwrap_or_else(|| {
4283                         self.type_var_for_def(span, def, substs)
4284                     });
4285                 }
4286                 i -= has_self as usize;
4287                 type_segment
4288             } else {
4289                 i -= fn_start;
4290                 fn_segment
4291             };
4292             let types = match segment.map(|(s, _)| &s.parameters) {
4293                 Some(&hir::AngleBracketedParameters(ref data)) => &data.types[..],
4294                 Some(&hir::ParenthesizedParameters(_)) => bug!(),
4295                 None => &[]
4296             };
4297
4298             // Skip over the lifetimes in the same segment.
4299             if let Some((_, generics)) = segment {
4300                 i -= generics.regions.len();
4301             }
4302
4303             let omitted = can_omit && types.is_empty();
4304             if let Some(ast_ty) = types.get(i) {
4305                 // A provided type parameter.
4306                 self.to_ty(ast_ty)
4307             } else if let (false, Some(default)) = (omitted, def.default) {
4308                 // No type parameter provided, but a default exists.
4309                 default.subst_spanned(self.tcx, substs, Some(span))
4310             } else {
4311                 // No type parameters were provided, we can infer all.
4312                 // This can also be reached in some error cases:
4313                 // We prefer to use inference variables instead of
4314                 // TyError to let type inference recover somewhat.
4315                 self.type_var_for_def(span, def, substs)
4316             }
4317         });
4318
4319         // The things we are substituting into the type should not contain
4320         // escaping late-bound regions, and nor should the base type scheme.
4321         let scheme = self.tcx.lookup_item_type(def.def_id());
4322         let type_predicates = self.tcx.lookup_predicates(def.def_id());
4323         assert!(!substs.has_escaping_regions());
4324         assert!(!scheme.ty.has_escaping_regions());
4325
4326         // Add all the obligations that are required, substituting and
4327         // normalized appropriately.
4328         let bounds = self.instantiate_bounds(span, &substs, &type_predicates);
4329         self.add_obligations_for_parameters(
4330             traits::ObligationCause::new(span, self.body_id, traits::ItemObligation(def.def_id())),
4331             &bounds);
4332
4333         // Substitute the values for the type parameters into the type of
4334         // the referenced item.
4335         let ty_substituted = self.instantiate_type_scheme(span, &substs, &scheme.ty);
4336
4337
4338         if let Some((ty::ImplContainer(impl_def_id), self_ty)) = ufcs_associated {
4339             // In the case of `Foo<T>::method` and `<Foo<T>>::method`, if `method`
4340             // is inherent, there is no `Self` parameter, instead, the impl needs
4341             // type parameters, which we can infer by unifying the provided `Self`
4342             // with the substituted impl type.
4343             let impl_scheme = self.tcx.lookup_item_type(impl_def_id);
4344
4345             let impl_ty = self.instantiate_type_scheme(span, &substs, &impl_scheme.ty);
4346             match self.sub_types(false, TypeOrigin::Misc(span), self_ty, impl_ty) {
4347                 Ok(InferOk { obligations, .. }) => {
4348                     // FIXME(#32730) propagate obligations
4349                     assert!(obligations.is_empty());
4350                 }
4351                 Err(_) => {
4352                     span_bug!(span,
4353                         "instantiate_value_path: (UFCS) {:?} was a subtype of {:?} but now is not?",
4354                         self_ty,
4355                         impl_ty);
4356                 }
4357             }
4358         }
4359
4360         debug!("instantiate_value_path: type of {:?} is {:?}",
4361                node_id,
4362                ty_substituted);
4363         self.write_ty(node_id, ty_substituted);
4364         self.write_substs(node_id, ty::ItemSubsts {
4365             substs: substs
4366         });
4367         ty_substituted
4368     }
4369
4370     /// Report errors if the provided parameters are too few or too many.
4371     fn check_path_parameter_count(&self,
4372                                   span: Span,
4373                                   can_omit: bool,
4374                                   segment: &mut Option<(&hir::PathSegment, &ty::Generics)>) {
4375         let (lifetimes, types, bindings) = match segment.map(|(s, _)| &s.parameters) {
4376             Some(&hir::AngleBracketedParameters(ref data)) => {
4377                 (&data.lifetimes[..], &data.types[..], &data.bindings[..])
4378             }
4379             Some(&hir::ParenthesizedParameters(_)) => {
4380                 span_bug!(span, "parenthesized parameters cannot appear in ExprPath");
4381             }
4382             None => (&[][..], &[][..], &[][..])
4383         };
4384
4385         let count = |n| {
4386             format!("{} parameter{}", n, if n == 1 { "" } else { "s" })
4387         };
4388
4389         // Check provided lifetime parameters.
4390         let lifetime_defs = segment.map_or(&[][..], |(_, generics)| &generics.regions);
4391         if lifetimes.len() > lifetime_defs.len() {
4392             let span = lifetimes[lifetime_defs.len()].span;
4393             span_err!(self.tcx.sess, span, E0088,
4394                       "too many lifetime parameters provided: \
4395                        expected {}, found {}",
4396                       count(lifetime_defs.len()),
4397                       count(lifetimes.len()));
4398         } else if lifetimes.len() > 0 && lifetimes.len() < lifetime_defs.len() {
4399             span_err!(self.tcx.sess, span, E0090,
4400                       "too few lifetime parameters provided: \
4401                        expected {}, found {}",
4402                       count(lifetime_defs.len()),
4403                       count(lifetimes.len()));
4404         }
4405
4406         // Check provided type parameters.
4407         let type_defs = segment.map_or(&[][..], |(_, generics)| {
4408             if generics.parent.is_none() {
4409                 &generics.types[generics.has_self as usize..]
4410             } else {
4411                 &generics.types
4412             }
4413         });
4414         let required_len = type_defs.iter()
4415                                     .take_while(|d| d.default.is_none())
4416                                     .count();
4417         if types.len() > type_defs.len() {
4418             let span = types[type_defs.len()].span;
4419             struct_span_err!(self.tcx.sess, span, E0087,
4420                              "too many type parameters provided: \
4421                               expected at most {}, found {}",
4422                              count(type_defs.len()),
4423                              count(types.len()))
4424                 .span_label(span, &format!("too many type parameters")).emit();
4425
4426             // To prevent derived errors to accumulate due to extra
4427             // type parameters, we force instantiate_value_path to
4428             // use inference variables instead of the provided types.
4429             *segment = None;
4430         } else if !(can_omit && types.len() == 0) && types.len() < required_len {
4431             let qualifier =
4432                 if type_defs.len() != required_len { "at least " } else { "" };
4433             span_err!(self.tcx.sess, span, E0089,
4434                       "too few type parameters provided: \
4435                        expected {}{}, found {}",
4436                       qualifier,
4437                       count(required_len),
4438                       count(types.len()));
4439         }
4440
4441         if !bindings.is_empty() {
4442             span_err!(self.tcx.sess, bindings[0].span, E0182,
4443                       "unexpected binding of associated item in expression path \
4444                        (only allowed in type paths)");
4445         }
4446     }
4447
4448     fn structurally_resolve_type_or_else<F>(&self, sp: Span, ty: Ty<'tcx>, f: F)
4449                                             -> Ty<'tcx>
4450         where F: Fn() -> Ty<'tcx>
4451     {
4452         let mut ty = self.resolve_type_vars_with_obligations(ty);
4453
4454         if ty.is_ty_var() {
4455             let alternative = f();
4456
4457             // If not, error.
4458             if alternative.is_ty_var() || alternative.references_error() {
4459                 if !self.is_tainted_by_errors() {
4460                     self.type_error_message(sp, |_actual| {
4461                         "the type of this value must be known in this context".to_string()
4462                     }, ty);
4463                 }
4464                 self.demand_suptype(sp, self.tcx.types.err, ty);
4465                 ty = self.tcx.types.err;
4466             } else {
4467                 self.demand_suptype(sp, alternative, ty);
4468                 ty = alternative;
4469             }
4470         }
4471
4472         ty
4473     }
4474
4475     // Resolves `typ` by a single level if `typ` is a type variable.  If no
4476     // resolution is possible, then an error is reported.
4477     pub fn structurally_resolved_type(&self, sp: Span, ty: Ty<'tcx>) -> Ty<'tcx> {
4478         self.structurally_resolve_type_or_else(sp, ty, || {
4479             self.tcx.types.err
4480         })
4481     }
4482 }
4483
4484 // Returns true if b contains a break that can exit from b
4485 pub fn may_break(tcx: TyCtxt, id: ast::NodeId, b: &hir::Block) -> bool {
4486     // First: is there an unlabeled break immediately
4487     // inside the loop?
4488     (loop_query(&b, |e| {
4489         match *e {
4490             hir::ExprBreak(None) => true,
4491             _ => false
4492         }
4493     })) ||
4494     // Second: is there a labeled break with label
4495     // <id> nested anywhere inside the loop?
4496     (block_query(b, |e| {
4497         if let hir::ExprBreak(Some(_)) = e.node {
4498             tcx.expect_def(e.id) == Def::Label(id)
4499         } else {
4500             false
4501         }
4502     }))
4503 }
4504
4505 pub fn check_bounds_are_used<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
4506                                        generics: &hir::Generics,
4507                                        ty: Ty<'tcx>) {
4508     debug!("check_bounds_are_used(n_tps={}, ty={:?})",
4509            generics.ty_params.len(),  ty);
4510
4511     // make a vector of booleans initially false, set to true when used
4512     if generics.ty_params.is_empty() { return; }
4513     let mut tps_used = vec![false; generics.ty_params.len()];
4514
4515     for leaf_ty in ty.walk() {
4516         if let ty::TyParam(ParamTy {idx, ..}) = leaf_ty.sty {
4517             debug!("Found use of ty param num {}", idx);
4518             tps_used[idx as usize - generics.lifetimes.len()] = true;
4519         }
4520     }
4521
4522     for (&used, param) in tps_used.iter().zip(&generics.ty_params) {
4523         if !used {
4524             struct_span_err!(ccx.tcx.sess, param.span, E0091,
4525                 "type parameter `{}` is unused",
4526                 param.name)
4527                 .span_label(param.span, &format!("unused type parameter"))
4528                 .emit();
4529         }
4530     }
4531 }