}
ExprKind::MethodCall(ref segment, ..) => {
if let Some(ref params) = segment.parameters {
- match **params {
- PathParameters::AngleBracketed(ref param_data) => {
- if !param_data.bindings.is_empty() {
- let binding_span = param_data.bindings[0].span;
- self.err_handler().span_err(binding_span,
- "type bindings cannot be used in method calls");
- }
- }
- PathParameters::Parenthesized(..) => {
- self.err_handler().span_err(expr.span,
- "parenthesized parameters cannot be used on method calls");
- }
+ if let PathParameters::Parenthesized(..) = **params {
+ self.err_handler().span_err(expr.span,
+ "parenthesized parameters cannot be used on method calls");
}
}
}
use super::{probe, MethodCallee};
+use astconv::AstConv;
use check::{FnCtxt, LvalueOp, callee};
use hir::def_id::DefId;
use rustc::ty::subst::Substs;
segment: &hir::PathSegment,
substs: &Substs<'tcx>)
-> &'tcx Substs<'tcx> {
- let supplied_method_types = match segment.parameters {
- hir::AngleBracketedParameters(ref data) => &data.types,
- _ => bug!("unexpected generic arguments: {:?}", segment.parameters),
- };
-
// Determine the values for the generic parameters of the method.
// If they were not explicitly supplied, just construct fresh
// variables.
- let num_supplied_types = supplied_method_types.len();
let method_generics = self.tcx.generics_of(pick.item.def_id);
- let num_method_types = method_generics.types.len();
-
- if num_supplied_types > 0 && num_supplied_types != num_method_types {
- if num_method_types == 0 {
- struct_span_err!(self.tcx.sess,
- self.span,
- E0035,
- "does not take type parameters")
- .span_label(self.span, "called with unneeded type parameters")
- .emit();
- } else {
- struct_span_err!(self.tcx.sess,
- self.span,
- E0036,
- "incorrect number of type parameters given for this method: \
- expected {}, found {}",
- num_method_types,
- num_supplied_types)
- .span_label(self.span,
- format!("Passed {} type argument{}, expected {}",
- num_supplied_types,
- if num_supplied_types != 1 { "s" } else { "" },
- num_method_types))
- .emit();
- }
- }
+ let mut fn_segment = Some((segment, method_generics));
+ self.fcx.check_path_parameter_count(self.span, &mut fn_segment);
// Create subst for early-bound lifetime parameters, combining
// parameters from the type and those from the method.
- //
- // FIXME -- permit users to manually specify lifetimes
- let supplied_start = substs.len() + method_generics.regions.len();
+ let (supplied_types, supplied_lifetimes) = match segment.parameters {
+ hir::AngleBracketedParameters(ref data) => (&data.types, &data.lifetimes),
+ _ => bug!("unexpected generic arguments: {:?}", segment.parameters),
+ };
Substs::for_item(self.tcx, pick.item.def_id, |def, _| {
let i = def.index as usize;
if i < substs.len() {
substs.region_at(i)
+ } else if let Some(lifetime) = supplied_lifetimes.get(i - substs.len()) {
+ AstConv::ast_region_to_region(self.fcx, lifetime, Some(def))
} else {
self.region_var_for_def(self.span, def)
}
let i = def.index as usize;
if i < substs.len() {
substs.type_at(i)
- } else if let Some(ast_ty) = supplied_method_types.get(i - supplied_start) {
+ } else if let Some(ast_ty) = supplied_types.get(i - substs.len()) {
self.to_ty(ast_ty)
} else {
self.type_var_for_def(self.span, def, cur_substs)
```
"##,
-E0035: r##"
-You tried to give a type parameter where it wasn't needed. Erroneous code
-example:
-
-```compile_fail,E0035
-struct Test;
-
-impl Test {
- fn method(&self) {}
-}
-
-fn main() {
- let x = Test;
-
- x.method::<i32>(); // Error: Test::method doesn't need type parameter!
-}
-```
-
-To fix this error, just remove the type parameter:
-
-```
-struct Test;
-
-impl Test {
- fn method(&self) {}
-}
-
-fn main() {
- let x = Test;
-
- x.method(); // OK, we're good!
-}
-```
-"##,
-
-E0036: r##"
-This error occurrs when you pass too many or not enough type parameters to
-a method. Erroneous code example:
-
-```compile_fail,E0036
-struct Test;
-
-impl Test {
- fn method<T>(&self, v: &[T]) -> usize {
- v.len()
- }
-}
-
-fn main() {
- let x = Test;
- let v = &[0];
-
- x.method::<i32, i32>(v); // error: only one type parameter is expected!
-}
-```
-
-To fix it, just specify a correct number of type parameters:
-
-```
-struct Test;
-
-impl Test {
- fn method<T>(&self, v: &[T]) -> usize {
- v.len()
- }
-}
-
-fn main() {
- let x = Test;
- let v = &[0];
-
- x.method::<i32>(v); // OK, we're good!
-}
-```
-
-Please note on the last example that we could have called `method` like this:
-
-```
-# struct Test;
-# impl Test { fn method<T>(&self, v: &[T]) -> usize { v.len() } }
-# let x = Test;
-# let v = &[0];
-x.method(v);
-```
-"##,
-
E0040: r##"
It is not allowed to manually call destructors in Rust. It is also not
necessary to do this since `drop` is called automatically whenever a value goes
}
register_diagnostics! {
+// E0035, merged into E0087/E0089
+// E0036, merged into E0087/E0089
// E0068,
// E0085,
// E0086,
+++ /dev/null
-// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-struct Test;
-
-impl Test {
- fn method(&self) {}
-}
-
-fn main() {
- let x = Test;
- x.method::<i32>(); //~ ERROR E0035
- //~| NOTE called with unneeded type parameters
-}
+++ /dev/null
-// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
-// file at the top-level directory of this distribution and at
-// http://rust-lang.org/COPYRIGHT.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-struct Test;
-
-impl Test {
- fn method<T>(&self, v: &[T]) -> usize {
- v.len()
- }
-}
-
-fn main() {
- let x = Test;
- let v = &[0];
- x.method::<i32, i32>(v); //~ ERROR E0036
- //~| NOTE Passed 2 type arguments, expected 1
-}
--- /dev/null
+// Copyright 2017 The Rust Project Developers. See the COPYRIGHT
+// file at the top-level directory of this distribution and at
+// http://rust-lang.org/COPYRIGHT.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+fn main() {
+ 0.clone::<'a>(); //~ ERROR use of undeclared lifetime name `'a`
+}
--- /dev/null
+// Copyright 2017 The Rust Project Developers. See the COPYRIGHT
+// file at the top-level directory of this distribution and at
+// http://rust-lang.org/COPYRIGHT.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+struct S;
+
+impl S {
+ fn late<'a, 'b>(self, _: &'a u8, _: &'b u8) {}
+ fn early<'a, 'b>(self) -> (&'a u8, &'b u8) { loop {} }
+ fn life_and_type<'a, T>(&self) -> &'a T { loop {} }
+}
+
+fn main() {
+ S.late(&0, &0); // OK
+ S.late::<'static>(&0, &0);
+ //~^ ERROR expected at most 0 lifetime parameters, found 1 lifetime parameter
+ S.late::<'static, 'static, 'static>(&0, &0);
+ //~^ ERROR expected at most 0 lifetime parameters, found 3 lifetime parameter
+ S.early(); // OK
+ S.early::<'static>();
+ //~^ ERROR expected 2 lifetime parameters, found 1 lifetime parameter
+ S.early::<'static, 'static, 'static>();
+ //~^ ERROR expected at most 2 lifetime parameters, found 3 lifetime parameters
+ let _: &u8 = S.life_and_type::<'static>();
+ S.life_and_type::<u8>();
+ S.life_and_type::<'static, u8>();
+}
// except according to those terms.
fn main() {
- 0.clone::<T = u8>(); //~ ERROR type bindings cannot be used in method calls
+ 0.clone::<T = u8>(); //~ ERROR unexpected binding of associated item
}
impl bar for u32 { fn dup(&self) -> u32 { *self } fn blah<X>(&self) {} }
fn main() {
- 10.dup::<i32>(); //~ ERROR does not take type parameters
- 10.blah::<i32, i32>();
- //~^ ERROR incorrect number of type parameters given for this method: expected 1, found 2
+ 10.dup::<i32>(); //~ ERROR expected at most 0 type parameters, found 1 type parameter
+ 10.blah::<i32, i32>(); //~ ERROR expected at most 1 type parameter, found 2 type parameters
(box 10 as Box<bar>).dup();
//~^ ERROR E0038
//~| ERROR E0038