Skip to content

Commit c735d7f

Browse files
author
Jonathan Turner
committed
Point arg num mismatch errors back to their definition
1 parent b30022a commit c735d7f

12 files changed

+59
-59
lines changed

src/librustc_typeck/check/callee.rs

+10-6
Original file line numberDiff line numberDiff line change
@@ -193,9 +193,11 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
193193
-> Ty<'tcx> {
194194
let error_fn_sig;
195195

196-
let fn_sig = match callee_ty.sty {
197-
ty::TyFnDef(.., &ty::BareFnTy {ref sig, ..}) |
198-
ty::TyFnPtr(&ty::BareFnTy {ref sig, ..}) => sig,
196+
let (fn_sig, def_span) = match callee_ty.sty {
197+
ty::TyFnDef(def_id, .., &ty::BareFnTy {ref sig, ..}) => {
198+
(sig, self.tcx.map.span_if_local(def_id))
199+
}
200+
ty::TyFnPtr(&ty::BareFnTy {ref sig, ..}) => (sig, None),
199201
ref t => {
200202
let mut unit_variant = None;
201203
if let &ty::TyAdt(adt_def, ..) = t {
@@ -241,7 +243,7 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
241243
variadic: false,
242244
});
243245

244-
&error_fn_sig
246+
(&error_fn_sig, None)
245247
}
246248
};
247249

@@ -266,7 +268,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
266268
&expected_arg_tys[..],
267269
arg_exprs,
268270
fn_sig.variadic,
269-
TupleArgumentsFlag::DontTupleArguments);
271+
TupleArgumentsFlag::DontTupleArguments,
272+
def_span);
270273

271274
fn_sig.output
272275
}
@@ -292,7 +295,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
292295
&expected_arg_tys,
293296
arg_exprs,
294297
fn_sig.variadic,
295-
TupleArgumentsFlag::TupleArguments);
298+
TupleArgumentsFlag::TupleArguments,
299+
None);
296300

297301
fn_sig.output
298302
}

src/librustc_typeck/check/mod.rs

+22-25
Original file line numberDiff line numberDiff line change
@@ -2465,17 +2465,19 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
24652465
};
24662466

24672467
self.check_argument_types(sp, &err_inputs[..], &[], args_no_rcvr,
2468-
false, tuple_arguments);
2468+
false, tuple_arguments, None);
24692469
self.tcx.types.err
24702470
} else {
24712471
match method_fn_ty.sty {
2472-
ty::TyFnDef(.., ref fty) => {
2472+
ty::TyFnDef(def_id, .., ref fty) => {
24732473
// HACK(eddyb) ignore self in the definition (see above).
24742474
let expected_arg_tys = self.expected_types_for_fn_args(sp, expected,
24752475
fty.sig.0.output,
24762476
&fty.sig.0.inputs[1..]);
2477+
24772478
self.check_argument_types(sp, &fty.sig.0.inputs[1..], &expected_arg_tys[..],
2478-
args_no_rcvr, fty.sig.0.variadic, tuple_arguments);
2479+
args_no_rcvr, fty.sig.0.variadic, tuple_arguments,
2480+
self.tcx.map.span_if_local(def_id));
24792481
fty.sig.0.output
24802482
}
24812483
_ => {
@@ -2493,7 +2495,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
24932495
expected_arg_tys: &[Ty<'tcx>],
24942496
args: &'gcx [hir::Expr],
24952497
variadic: bool,
2496-
tuple_arguments: TupleArgumentsFlag) {
2498+
tuple_arguments: TupleArgumentsFlag,
2499+
def_span: Option<Span>) {
24972500
let tcx = self.tcx;
24982501

24992502
// Grab the argument types, supplying fresh type variables
@@ -2528,9 +2531,9 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
25282531
sp
25292532
};
25302533

2531-
fn parameter_count_error<'tcx>(sess: &Session, sp: Span, fn_inputs: &[Ty<'tcx>],
2532-
expected_count: usize, arg_count: usize, error_code: &str,
2533-
variadic: bool) {
2534+
fn parameter_count_error<'tcx>(sess: &Session, sp: Span, expected_count: usize,
2535+
arg_count: usize, error_code: &str, variadic: bool,
2536+
def_span: Option<Span>) {
25342537
let mut err = sess.struct_span_err_with_code(sp,
25352538
&format!("this function takes {}{} parameter{} but {} parameter{} supplied",
25362539
if variadic {"at least "} else {""},
@@ -2540,18 +2543,12 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
25402543
if arg_count == 1 {" was"} else {"s were"}),
25412544
error_code);
25422545

2543-
let input_types = fn_inputs.iter().map(|i| format!("{:?}", i)).collect::<Vec<String>>();
2544-
if input_types.len() > 1 {
2545-
err.note("the following parameter types were expected:");
2546-
err.note(&input_types.join(", "));
2547-
} else if input_types.len() > 0 {
2548-
err.note(&format!("the following parameter type was expected: {}",
2549-
input_types[0]));
2550-
} else {
2551-
err.span_label(sp, &format!("expected {}{} parameter{}",
2552-
if variadic {"at least "} else {""},
2553-
expected_count,
2554-
if expected_count == 1 {""} else {"s"}));
2546+
err.span_label(sp, &format!("expected {}{} parameter{}",
2547+
if variadic {"at least "} else {""},
2548+
expected_count,
2549+
if expected_count == 1 {""} else {"s"}));
2550+
if let Some(def_s) = def_span {
2551+
err.span_label(def_s, &format!("defined here"));
25552552
}
25562553
err.emit();
25572554
}
@@ -2560,8 +2557,8 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
25602557
let tuple_type = self.structurally_resolved_type(sp, fn_inputs[0]);
25612558
match tuple_type.sty {
25622559
ty::TyTuple(arg_types) if arg_types.len() != args.len() => {
2563-
parameter_count_error(tcx.sess, sp_args, fn_inputs, arg_types.len(), args.len(),
2564-
"E0057", false);
2560+
parameter_count_error(tcx.sess, sp_args, arg_types.len(), args.len(),
2561+
"E0057", false, def_span);
25652562
expected_arg_tys = &[];
25662563
self.err_args(args.len())
25672564
}
@@ -2589,14 +2586,14 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
25892586
if supplied_arg_count >= expected_arg_count {
25902587
fn_inputs.to_vec()
25912588
} else {
2592-
parameter_count_error(tcx.sess, sp_args, fn_inputs, expected_arg_count,
2593-
supplied_arg_count, "E0060", true);
2589+
parameter_count_error(tcx.sess, sp_args, expected_arg_count,
2590+
supplied_arg_count, "E0060", true, def_span);
25942591
expected_arg_tys = &[];
25952592
self.err_args(supplied_arg_count)
25962593
}
25972594
} else {
2598-
parameter_count_error(tcx.sess, sp_args, fn_inputs, expected_arg_count,
2599-
supplied_arg_count, "E0061", false);
2595+
parameter_count_error(tcx.sess, sp_args, expected_arg_count,
2596+
supplied_arg_count, "E0061", false, def_span);
26002597
expected_arg_tys = &[];
26012598
self.err_args(supplied_arg_count)
26022599
};

src/test/compile-fail/E0060.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,11 @@
1010

1111
extern "C" {
1212
fn printf(_: *const u8, ...) -> u32;
13+
//~^ NOTE defined here
1314
}
1415

1516
fn main() {
1617
unsafe { printf(); }
1718
//~^ ERROR E0060
18-
//~| NOTE the following parameter type was expected: *const u8
19+
//~| expected at least 1 parameter
1920
}

src/test/compile-fail/E0061.rs

+4-3
Original file line numberDiff line numberDiff line change
@@ -9,16 +9,17 @@
99
// except according to those terms.
1010

1111
fn f(a: u16, b: &str) {}
12+
//~^ NOTE defined here
1213

1314
fn f2(a: u16) {}
15+
//~^ NOTE defined here
1416

1517
fn main() {
1618
f(0);
1719
//~^ ERROR E0061
18-
//~| NOTE the following parameter types were expected:
19-
//~| NOTE u16, &str
20+
//~| expected 2 parameters
2021

2122
f2();
2223
//~^ ERROR E0061
23-
//~| NOTE the following parameter type was expected: u16
24+
//~| expected 1 parameter
2425
}

src/test/compile-fail/issue-18819.rs

+3-3
Original file line numberDiff line numberDiff line change
@@ -19,12 +19,12 @@ impl Foo for X {
1919
}
2020

2121
fn print_x(_: &Foo<Item=bool>, extra: &str) {
22+
//~^ NOTE defined here
2223
println!("{}", extra);
2324
}
2425

2526
fn main() {
2627
print_x(X);
27-
//~^ ERROR this function takes 2 parameters but 1 parameter was supplied
28-
//~| NOTE the following parameter types were expected:
29-
//~| NOTE &Foo<Item=bool>, &str
28+
//~^ ERROR E0061
29+
//~| NOTE expected 2 parameters
3030
}

src/test/compile-fail/issue-3044.rs

+1-3
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,5 @@ fn main() {
1414
needlesArr.iter().fold(|x, y| {
1515
});
1616
//~^^ ERROR this function takes 2 parameters but 1 parameter was supplied
17-
//~| NOTE the following parameter types were expected
18-
//~| NOTE _, _
19-
// the first error is, um, non-ideal.
17+
//~| NOTE expected 2 parameters
2018
}

src/test/compile-fail/issue-4935.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111
// Regression test for issue #4935
1212

1313
fn foo(a: usize) {}
14+
//~^ defined here
1415
fn main() { foo(5, 6) }
1516
//~^ ERROR this function takes 1 parameter but 2 parameters were supplied
16-
//~| NOTE the following parameter type was expected
17+
//~| NOTE expected 1 parameter

src/test/compile-fail/method-call-err-msg.rs

+5-3
Original file line numberDiff line numberDiff line change
@@ -13,19 +13,21 @@
1313
pub struct Foo;
1414
impl Foo {
1515
fn zero(self) -> Foo { self }
16+
//~^ NOTE defined here
1617
fn one(self, _: isize) -> Foo { self }
18+
//~^ NOTE defined here
1719
fn two(self, _: isize, _: isize) -> Foo { self }
20+
//~^ NOTE defined here
1821
}
1922

2023
fn main() {
2124
let x = Foo;
2225
x.zero(0) //~ ERROR this function takes 0 parameters but 1 parameter was supplied
2326
//~^ NOTE expected 0 parameters
2427
.one() //~ ERROR this function takes 1 parameter but 0 parameters were supplied
25-
//~^ NOTE the following parameter type was expected
28+
//~^ NOTE expected 1 parameter
2629
.two(0); //~ ERROR this function takes 2 parameters but 1 parameter was supplied
27-
//~^ NOTE the following parameter types were expected
28-
//~| NOTE isize, isize
30+
//~^ NOTE expected 2 parameters
2931

3032
let y = Foo;
3133
y.zero()

src/test/compile-fail/not-enough-arguments.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -13,12 +13,12 @@
1313
// unrelated errors.
1414

1515
fn foo(a: isize, b: isize, c: isize, d:isize) {
16+
//~^ NOTE defined here
1617
panic!();
1718
}
1819

1920
fn main() {
2021
foo(1, 2, 3);
2122
//~^ ERROR this function takes 4 parameters but 3
22-
//~| NOTE the following parameter types were expected:
23-
//~| NOTE isize, isize, isize, isize
23+
//~| NOTE expected 4 parameters
2424
}

src/test/compile-fail/overloaded-calls-bad.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -41,8 +41,8 @@ fn main() {
4141
//~| NOTE found type
4242
let ans = s();
4343
//~^ ERROR this function takes 1 parameter but 0 parameters were supplied
44-
//~| NOTE the following parameter type was expected
44+
//~| NOTE expected 1 parameter
4545
let ans = s("burma", "shave");
4646
//~^ ERROR this function takes 1 parameter but 2 parameters were supplied
47-
//~| NOTE the following parameter type was expected
47+
//~| NOTE expected 1 parameter
4848
}

src/test/compile-fail/variadic-ffi-3.rs

+4-4
Original file line numberDiff line numberDiff line change
@@ -10,18 +10,18 @@
1010

1111
extern {
1212
fn foo(f: isize, x: u8, ...);
13+
//~^ defined here
14+
//~| defined here
1315
}
1416

1517
extern "C" fn bar(f: isize, x: u8) {}
1618

1719
fn main() {
1820
unsafe {
1921
foo(); //~ ERROR: this function takes at least 2 parameters but 0 parameters were supplied
20-
//~^ NOTE the following parameter types were expected:
21-
//~| NOTE isize, u8
22+
//~| NOTE expected at least 2 parameters
2223
foo(1); //~ ERROR: this function takes at least 2 parameters but 1 parameter was supplied
23-
//~^ NOTE the following parameter types were expected:
24-
//~| NOTE isize, u8
24+
//~| NOTE expected at least 2 parameters
2525

2626
let x: unsafe extern "C" fn(f: isize, x: u8) = foo;
2727
//~^ ERROR: mismatched types

src/test/ui/span/E0057.stderr

+2-6
Original file line numberDiff line numberDiff line change
@@ -2,17 +2,13 @@ error[E0057]: this function takes 1 parameter but 0 parameters were supplied
22
--> $DIR/E0057.rs:13:13
33
|
44
13 | let a = f(); //~ ERROR E0057
5-
| ^^^
6-
|
7-
= note: the following parameter type was expected: (_,)
5+
| ^^^ expected 1 parameter
86

97
error[E0057]: this function takes 1 parameter but 2 parameters were supplied
108
--> $DIR/E0057.rs:15:15
119
|
1210
15 | let c = f(2, 3); //~ ERROR E0057
13-
| ^^^^
14-
|
15-
= note: the following parameter type was expected: (_,)
11+
| ^^^^ expected 1 parameter
1612

1713
error: aborting due to 2 previous errors
1814

0 commit comments

Comments
 (0)