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