summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSom Snytt <som.snytt@gmail.com>2016-05-11 14:32:50 -0700
committerSom Snytt <som.snytt@gmail.com>2016-05-13 23:00:56 -0700
commit40b42ae71779fb333259674b05f28de45219939d (patch)
tree0eed0a7dbcd29375d5d8b32f093e96fe5d36a10b
parenta6d5eb507bbeac2055a224a15fd76e7f9425520b (diff)
downloadscala-40b42ae71779fb333259674b05f28de45219939d.tar.gz
scala-40b42ae71779fb333259674b05f28de45219939d.tar.bz2
scala-40b42ae71779fb333259674b05f28de45219939d.zip
SI-8667 Caret at bad arg
Pick the first excessive positional arg for the caret. Note that erroring on named args doesn't do the obvious thing in this regard. If `k` was removed from the signature, then `f(k=1, i=2, j=3)` doesn't tell us much about the wrong arg, because naming takes the `k=1` as an assignment, `i` as duplicate naming. No arg is deemed extra, though further inspection of the conflicting args might get there. Since assignment syntax in parens is more|less deprecated (?), no more effort is done here.
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala18
-rw-r--r--src/compiler/scala/tools/nsc/typechecker/Typers.scala7
-rw-r--r--test/files/neg/eta-expand-star.check2
-rw-r--r--test/files/neg/macro-invalidusage-badargs.check2
-rw-r--r--test/files/neg/multi-array.check2
-rw-r--r--test/files/neg/protected-constructors.check7
-rw-r--r--test/files/neg/t1112.check2
-rw-r--r--test/files/neg/t1523.check2
-rw-r--r--test/files/neg/t6920.check2
-rw-r--r--test/files/neg/t7157.check24
-rw-r--r--test/files/neg/t8006.check2
-rw-r--r--test/files/neg/t8035-no-adapted-args.check2
-rw-r--r--test/files/neg/t8667.check56
-rw-r--r--test/files/neg/t8667.scala4
-rw-r--r--test/files/neg/t876.check2
15 files changed, 79 insertions, 55 deletions
diff --git a/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala b/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala
index e1055144f8..6b30d3834c 100644
--- a/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/ContextErrors.scala
@@ -538,7 +538,14 @@ trait ContextErrors {
def NamedAndDefaultArgumentsNotSupportedForMacros(tree: Tree, fun: Tree) =
NormalTypeError(tree, "macro applications do not support named and/or default arguments")
- def TooManyArgsNamesDefaultsError(tree: Tree, fun: Tree, expected: Int, supplied: Int, unknowns: List[Name]) = {
+ def TooManyArgsNamesDefaultsError(tree: Tree, fun: Tree, formals: List[Type], args: List[Tree], namelessArgs: List[Tree], argPos: Array[Int]) = {
+ val expected = formals.size
+ val supplied = args.size
+ // pick a caret. For f(k=1,i=2,j=3), argPos[0,-1,1] b/c `k=1` taken as arg0
+ val excessive = {
+ val i = argPos.indexWhere(_ >= expected)
+ if (i < 0) tree else args(i min (supplied - 1))
+ }
val msg = {
val badappl = {
val excess = supplied - expected
@@ -548,13 +555,16 @@ trait ContextErrors {
else if (excess < 3 && expected <= 5) s"too many arguments ($supplied) for $target"
else if (expected > 10) s"$supplied arguments but expected $expected for $target"
else {
- val oneOf =
+ val more =
if (excess == 1) "one more argument"
else if (excess > 0) s"$excess more arguments"
else "too many arguments"
- s"$oneOf than can be applied to $target"
+ s"$more than can be applied to $target"
}
}
+ val unknowns = (namelessArgs zip args) collect {
+ case (_: Assign, AssignOrNamedArg(Ident(name), _)) => name
+ }
val suppl =
unknowns.size match {
case 0 => ""
@@ -563,7 +573,7 @@ trait ContextErrors {
}
s"${badappl}${suppl}"
}
- NormalTypeError(tree, msg)
+ NormalTypeError(excessive, msg)
}
// can it still happen? see test case neg/overloaded-unapply.scala
diff --git a/src/compiler/scala/tools/nsc/typechecker/Typers.scala b/src/compiler/scala/tools/nsc/typechecker/Typers.scala
index 1d24d8c232..286de993db 100644
--- a/src/compiler/scala/tools/nsc/typechecker/Typers.scala
+++ b/src/compiler/scala/tools/nsc/typechecker/Typers.scala
@@ -3331,11 +3331,8 @@ trait Typers extends Adaptations with Tags with TypersTracking with PatternTyper
duplErrorTree(WrongNumberOfArgsError(tree, fun))
} else if (lencmp > 0) {
tryTupleApply orElse duplErrorTree {
- val (namelessArgs, _) = removeNames(Typer.this)(args, params)
- val wrongs = (namelessArgs zip args) collect {
- case (_: Assign, AssignOrNamedArg(Ident(name), _)) => name
- }
- TooManyArgsNamesDefaultsError(tree, fun, expected = formals.size, supplied = args.size, wrongs)
+ val (namelessArgs, argPos) = removeNames(Typer.this)(args, params)
+ TooManyArgsNamesDefaultsError(tree, fun, formals, args, namelessArgs, argPos)
}
} else if (lencmp == 0) {
// we don't need defaults. names were used, so this application is transformed
diff --git a/test/files/neg/eta-expand-star.check b/test/files/neg/eta-expand-star.check
index f25e0a41ff..eba1721014 100644
--- a/test/files/neg/eta-expand-star.check
+++ b/test/files/neg/eta-expand-star.check
@@ -1,4 +1,4 @@
eta-expand-star.scala:6: error: too many arguments (2) for method apply: (v1: Seq[T])Unit in trait Function1
g(1, 2)
- ^
+ ^
one error found
diff --git a/test/files/neg/macro-invalidusage-badargs.check b/test/files/neg/macro-invalidusage-badargs.check
index 2f5f6d1064..ee549c45cb 100644
--- a/test/files/neg/macro-invalidusage-badargs.check
+++ b/test/files/neg/macro-invalidusage-badargs.check
@@ -15,5 +15,5 @@ Unspecified value parameter x.
^
Macros_Test_2.scala:9: error: too many arguments (2) for macro method foo: (x: Int)Int
foo(4, 2)
- ^
+ ^
5 errors found
diff --git a/test/files/neg/multi-array.check b/test/files/neg/multi-array.check
index a71f9b864a..06ffdc9fbc 100644
--- a/test/files/neg/multi-array.check
+++ b/test/files/neg/multi-array.check
@@ -1,4 +1,4 @@
multi-array.scala:7: error: too many arguments (2) for constructor Array: (_length: Int)Array[T]
val a: Array[Int] = new Array(10, 10)
- ^
+ ^
one error found
diff --git a/test/files/neg/protected-constructors.check b/test/files/neg/protected-constructors.check
index 5c880cb672..0279f5815d 100644
--- a/test/files/neg/protected-constructors.check
+++ b/test/files/neg/protected-constructors.check
@@ -1,6 +1,6 @@
protected-constructors.scala:17: error: no arguments allowed for nullary constructor Foo1: ()dingus.Foo1
val foo1 = new Foo1("abc")
- ^
+ ^
protected-constructors.scala:18: error: constructor Foo2 in class Foo2 cannot be accessed in object P
Access to protected constructor Foo2 not permitted because
enclosing object P in package hungus is not a subclass of
@@ -19,4 +19,7 @@ protected-constructors.scala:15: error: class Foo3 in object Ding cannot be acce
object Ding in package dingus where target is defined
class Bar3 extends Ding.Foo3("abc")
^
-four errors found
+protected-constructors.scala:15: error: no arguments allowed for nullary constructor Object: ()Object
+ class Bar3 extends Ding.Foo3("abc")
+ ^
+5 errors found
diff --git a/test/files/neg/t1112.check b/test/files/neg/t1112.check
index 9c1254d176..e6058bf176 100644
--- a/test/files/neg/t1112.check
+++ b/test/files/neg/t1112.check
@@ -1,4 +1,4 @@
t1112.scala:12: error: too many arguments (2) for method call: (p: Int)(f: => Test.this.Type1)Unit
call(0,() => System.out.println("here we are"))
- ^
+ ^
one error found
diff --git a/test/files/neg/t1523.check b/test/files/neg/t1523.check
index 656845a457..273d0f8cf7 100644
--- a/test/files/neg/t1523.check
+++ b/test/files/neg/t1523.check
@@ -1,4 +1,4 @@
t1523.scala:4: error: 25 more arguments than can be applied to method bug: (x: Any)Any
def go() = bug("a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a", "a")
- ^
+ ^
one error found
diff --git a/test/files/neg/t6920.check b/test/files/neg/t6920.check
index 4e33aca3bc..d10abff03c 100644
--- a/test/files/neg/t6920.check
+++ b/test/files/neg/t6920.check
@@ -2,5 +2,5 @@ t6920.scala:9: error: too many arguments (2) for method applyDynamicNamed: (valu
error after rewriting to CompilerError.this.test.applyDynamicNamed("crushTheCompiler")(scala.Tuple2("a", 1), scala.Tuple2("b", 2))
possible cause: maybe a wrong Dynamic method signature?
test.crushTheCompiler(a = 1, b = 2)
- ^
+ ^
one error found
diff --git a/test/files/neg/t7157.check b/test/files/neg/t7157.check
index a043c5d403..0b81394946 100644
--- a/test/files/neg/t7157.check
+++ b/test/files/neg/t7157.check
@@ -1,22 +1,22 @@
Test_2.scala:5: error: no arguments allowed for nullary macro method m1_0_0: ()Unit
m1_0_0(1)
- ^
+ ^
Test_2.scala:6: error: no arguments allowed for nullary macro method m1_0_0: ()Unit
m1_0_0(1, 2)
- ^
+ ^
Test_2.scala:7: error: no arguments allowed for nullary macro method m1_0_0: ()Unit
m1_0_0(1, 2, 3)
- ^
+ ^
Test_2.scala:9: error: not enough arguments for macro method m1_1_1: (x: Int)Unit.
Unspecified value parameter x.
m1_1_1()
^
Test_2.scala:11: error: too many arguments (2) for macro method m1_1_1: (x: Int)Unit
m1_1_1(1, 2)
- ^
+ ^
Test_2.scala:12: error: too many arguments (3) for macro method m1_1_1: (x: Int)Unit
m1_1_1(1, 2, 3)
- ^
+ ^
Test_2.scala:14: error: not enough arguments for macro method m1_2_2: (x: Int, y: Int)Unit.
Unspecified value parameters x, y.
m1_2_2()
@@ -27,7 +27,7 @@ Unspecified value parameter y.
^
Test_2.scala:17: error: too many arguments (3) for macro method m1_2_2: (x: Int, y: Int)Unit
m1_2_2(1, 2, 3)
- ^
+ ^
Test_2.scala:24: error: not enough arguments for macro method m1_1_inf: (x: Int, y: Int*)Unit.
Unspecified value parameters x, y.
m1_1_inf()
@@ -42,23 +42,23 @@ Unspecified value parameters y, z.
^
Test_2.scala:35: error: no arguments allowed for nullary macro method m2_0_0: ()Unit
m2_0_0()(1)
- ^
+ ^
Test_2.scala:36: error: no arguments allowed for nullary macro method m2_0_0: ()Unit
m2_0_0()(1, 2)
- ^
+ ^
Test_2.scala:37: error: no arguments allowed for nullary macro method m2_0_0: ()Unit
m2_0_0()(1, 2, 3)
- ^
+ ^
Test_2.scala:39: error: not enough arguments for macro method m2_1_1: (x: Int)Unit.
Unspecified value parameter x.
m2_1_1()()
^
Test_2.scala:41: error: too many arguments (2) for macro method m2_1_1: (x: Int)Unit
m2_1_1()(1, 2)
- ^
+ ^
Test_2.scala:42: error: too many arguments (3) for macro method m2_1_1: (x: Int)Unit
m2_1_1()(1, 2, 3)
- ^
+ ^
Test_2.scala:44: error: not enough arguments for macro method m2_2_2: (x: Int, y: Int)Unit.
Unspecified value parameters x, y.
m2_2_2()()
@@ -69,7 +69,7 @@ Unspecified value parameter y.
^
Test_2.scala:47: error: too many arguments (3) for macro method m2_2_2: (x: Int, y: Int)Unit
m2_2_2()(1, 2, 3)
- ^
+ ^
Test_2.scala:54: error: not enough arguments for macro method m2_1_inf: (x: Int, y: Int*)Unit.
Unspecified value parameters x, y.
m2_1_inf()()
diff --git a/test/files/neg/t8006.check b/test/files/neg/t8006.check
index 4e130670e4..6152d0fba3 100644
--- a/test/files/neg/t8006.check
+++ b/test/files/neg/t8006.check
@@ -2,5 +2,5 @@ t8006.scala:3: error: too many arguments (2) for method applyDynamicNamed: (valu
error after rewriting to X.this.d.applyDynamicNamed("meth")(scala.Tuple2("value1", 10), scala.Tuple2("value2", 100))
possible cause: maybe a wrong Dynamic method signature?
d.meth(value1 = 10, value2 = 100) // two arguments here, but only one is allowed
- ^
+ ^
one error found
diff --git a/test/files/neg/t8035-no-adapted-args.check b/test/files/neg/t8035-no-adapted-args.check
index 4b3cb39c76..0115dddc91 100644
--- a/test/files/neg/t8035-no-adapted-args.check
+++ b/test/files/neg/t8035-no-adapted-args.check
@@ -6,7 +6,7 @@ t8035-no-adapted-args.scala:4: warning: No automatic adaptation here: use explic
^
t8035-no-adapted-args.scala:4: error: too many arguments (3) for method f: (x: (Int, Int, Int))Int
f(1, 2, 3)
- ^
+ ^
t8035-no-adapted-args.scala:5: warning: No automatic adaptation here: use explicit parentheses.
signature: Test.f[T](x: T): Int
given arguments: <none>
diff --git a/test/files/neg/t8667.check b/test/files/neg/t8667.check
index 4c3bcb78c8..82451ee5d6 100644
--- a/test/files/neg/t8667.check
+++ b/test/files/neg/t8667.check
@@ -1,7 +1,7 @@
t8667.scala:6: error: too many arguments (3) for constructor C: (a: Int, b: Int)C
Note that 'c' is not a parameter name of the invoked method.
def c2 = new C(a = 42, b = 17, c = 5)
- ^
+ ^
t8667.scala:7: error: unknown parameter name: c
def c3 = new C(b = 42, a = 17, c = 5)
^
@@ -25,9 +25,13 @@ t8667.scala:10: error: too many arguments (3) for constructor C: (a: Int, b: Int
Note that 'c' is not a parameter name of the invoked method.
def c6 = new C(a = 42, c = 17, b = 5)
^
+t8667.scala:11: error: parameter 'a' is already specified at parameter position 1
+Note that 'c' is not a parameter name of the invoked method.
+ def c7 = new C(c = 42, a = 17, b = 5)
+ ^
t8667.scala:11: error: too many arguments (3) for constructor C: (a: Int, b: Int)C
Note that 'c' is not a parameter name of the invoked method.
- def c7 = new C(42, 17, c = 5)
+ def c7 = new C(c = 42, a = 17, b = 5)
^
t8667.scala:12: error: parameter 'b' is already specified at parameter position 2
def c8 = new C(42, 17, b = 5)
@@ -42,38 +46,46 @@ Note that 'c' is not a parameter name of the invoked method.
t8667.scala:13: error: too many arguments (4) for constructor C: (a: Int, b: Int)C
Note that 'c', 'd' are not parameter names of the invoked method.
def c9 = new C(a = 42, c = 17, d = 3, b = 5)
- ^
+ ^
t8667.scala:14: error: too many arguments (4) for constructor C: (a: Int, b: Int)C
Note that 'd', 'c' are not parameter names of the invoked method.
def c0 = new C(42, 17, d = 3, c = 5)
- ^
-t8667.scala:24: error: no arguments allowed for nullary method f0: ()Int
+ ^
+t8667.scala:25: error: no arguments allowed for nullary method f0: ()Int
f0(1)
- ^
-t8667.scala:25: error: too many arguments (2) for method f1: (i: Int)Int
+ ^
+t8667.scala:26: error: too many arguments (2) for method f1: (i: Int)Int
f1(1, 2)
- ^
-t8667.scala:26: error: too many arguments (3) for method f1: (i: Int)Int
+ ^
+t8667.scala:27: error: too many arguments (3) for method f1: (i: Int)Int
f1(1, 2, 3)
- ^
-t8667.scala:27: error: 3 more arguments than can be applied to method f1: (i: Int)Int
- f1(1, 2, 3, 4)
- ^
+ ^
t8667.scala:28: error: 3 more arguments than can be applied to method f1: (i: Int)Int
+ f1(1, 2, 3, 4)
+ ^
+t8667.scala:29: error: 3 more arguments than can be applied to method f1: (i: Int)Int
Note that 'j' is not a parameter name of the invoked method.
f1(1, j = 2, 3, 4)
- ^
-t8667.scala:29: error: 3 more arguments than can be applied to method f1: (i: Int)Int
+ ^
+t8667.scala:30: error: 3 more arguments than can be applied to method f1: (i: Int)Int
Note that 'j', 'k' are not parameter names of the invoked method.
f1(1, j = 2, k = 3, 4)
+ ^
+t8667.scala:31: error: parameter 'i' is already specified at parameter position 1
+Note that 'k' is not a parameter name of the invoked method.
+ f2(k = 1, i = 2, j = 3)
+ ^
+t8667.scala:31: error: too many arguments (3) for method f2: (i: Int, j: Int)Int
+Note that 'k' is not a parameter name of the invoked method.
+ f2(k = 1, i = 2, j = 3)
^
-t8667.scala:30: error: one more argument than can be applied to method f6: (i: Int, j: Int, k: Int, l: Int, m: Int, n: Int)Int
+t8667.scala:32: error: one more argument than can be applied to method f6: (i: Int, j: Int, k: Int, l: Int, m: Int, n: Int)Int
f6(1, 2, 3, 4, 5, 6, 7)
- ^
-t8667.scala:31: error: 2 more arguments than can be applied to method f6: (i: Int, j: Int, k: Int, l: Int, m: Int, n: Int)Int
+ ^
+t8667.scala:33: error: 2 more arguments than can be applied to method f6: (i: Int, j: Int, k: Int, l: Int, m: Int, n: Int)Int
f6(1, 2, 3, 4, 5, 6, 7, 8)
- ^
-t8667.scala:32: error: 15 arguments but expected 12 for method f12: (i: Int, j: Int, k: Int, l: Int, m: Int, n: Int, o: Int, p: Int, q: Int, r: Int, s: Int, t: Int)Int
+ ^
+t8667.scala:34: error: 15 arguments but expected 12 for method f12: (i: Int, j: Int, k: Int, l: Int, m: Int, n: Int, o: Int, p: Int, q: Int, r: Int, s: Int, t: Int)Int
f12(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15)
- ^
-23 errors found
+ ^
+26 errors found
diff --git a/test/files/neg/t8667.scala b/test/files/neg/t8667.scala
index fe17eac84f..d55582ca6b 100644
--- a/test/files/neg/t8667.scala
+++ b/test/files/neg/t8667.scala
@@ -8,7 +8,7 @@ trait T {
def c4 = new C(b = 42, a = 17, 5)
def c5 = new C(a = 42, c = 17)
def c6 = new C(a = 42, c = 17, b = 5)
- def c7 = new C(42, 17, c = 5)
+ def c7 = new C(c = 42, a = 17, b = 5)
def c8 = new C(42, 17, b = 5)
def c9 = new C(a = 42, c = 17, d = 3, b = 5)
def c0 = new C(42, 17, d = 3, c = 5)
@@ -17,6 +17,7 @@ trait T {
trait X {
def f0() = 42
def f1(i: Int) = 42
+ def f2(i: Int, j: Int) = 42
def f6(i: Int, j: Int, k: Int, l: Int, m: Int, n: Int) = 42
def f12(i: Int, j: Int, k: Int, l: Int, m: Int, n: Int, o: Int, p: Int, q: Int, r: Int, s: Int, t: Int) = 42
@@ -27,6 +28,7 @@ trait X {
f1(1, 2, 3, 4)
f1(1, j = 2, 3, 4)
f1(1, j = 2, k = 3, 4)
+ f2(k = 1, i = 2, j = 3)
f6(1, 2, 3, 4, 5, 6, 7)
f6(1, 2, 3, 4, 5, 6, 7, 8)
f12(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15)
diff --git a/test/files/neg/t876.check b/test/files/neg/t876.check
index 91dcbfd288..7df2e126a6 100644
--- a/test/files/neg/t876.check
+++ b/test/files/neg/t876.check
@@ -1,4 +1,4 @@
t876.scala:25: error: too many arguments (2) for method apply: (key: AssertionError.A)manager.B in class HashMap
assert(manager.map(A2) == List(manager.map(A2, A1)))
- ^
+ ^
one error found