6313164: javac generates code that fails byte code verification for the varargs feature
Method applicability check should fail if formal varargs element type is not accessible Reviewed-by: jjg
This commit is contained in:
parent
6647b73cc8
commit
1e776bc78a
@ -60,6 +60,7 @@ public class Check {
|
||||
|
||||
private final Names names;
|
||||
private final Log log;
|
||||
private final Resolve rs;
|
||||
private final Symtab syms;
|
||||
private final Enter enter;
|
||||
private final Infer infer;
|
||||
@ -91,6 +92,7 @@ public class Check {
|
||||
|
||||
names = Names.instance(context);
|
||||
log = Log.instance(context);
|
||||
rs = Resolve.instance(context);
|
||||
syms = Symtab.instance(context);
|
||||
enter = Enter.instance(context);
|
||||
infer = Infer.instance(context);
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1999, 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -485,11 +485,8 @@ public class Infer {
|
||||
@Override
|
||||
public Type inst(List<Type> inferred, Types types) throws NoInstanceException {
|
||||
List<Type> formals = types.subst(mt2.argtypes, tvars, inferred);
|
||||
if (!rs.argumentsAcceptable(capturedArgs, formals,
|
||||
allowBoxing, useVarargs, warn)) {
|
||||
// inferred method is not applicable
|
||||
throw invalidInstanceException.setMessage("inferred.do.not.conform.to.params", formals, argtypes);
|
||||
}
|
||||
// check that actuals conform to inferred formals
|
||||
checkArgumentsAcceptable(env, capturedArgs, formals, allowBoxing, useVarargs, warn);
|
||||
// check that inferred bounds conform to their bounds
|
||||
checkWithinBounds(all_tvars,
|
||||
types.subst(inferredTypes, tvars, inferred), warn);
|
||||
@ -500,17 +497,27 @@ public class Infer {
|
||||
}};
|
||||
return mt2;
|
||||
}
|
||||
else if (!rs.argumentsAcceptable(capturedArgs, mt.getParameterTypes(), allowBoxing, useVarargs, warn)) {
|
||||
// inferred method is not applicable
|
||||
throw invalidInstanceException.setMessage("inferred.do.not.conform.to.params", mt.getParameterTypes(), argtypes);
|
||||
}
|
||||
else {
|
||||
// check that actuals conform to inferred formals
|
||||
checkArgumentsAcceptable(env, capturedArgs, mt.getParameterTypes(), allowBoxing, useVarargs, warn);
|
||||
// return instantiated version of method type
|
||||
return mt;
|
||||
}
|
||||
}
|
||||
//where
|
||||
|
||||
private void checkArgumentsAcceptable(Env<AttrContext> env, List<Type> actuals, List<Type> formals,
|
||||
boolean allowBoxing, boolean useVarargs, Warner warn) {
|
||||
try {
|
||||
rs.checkRawArgumentsAcceptable(env, actuals, formals,
|
||||
allowBoxing, useVarargs, warn);
|
||||
}
|
||||
catch (Resolve.InapplicableMethodException ex) {
|
||||
// inferred method is not applicable
|
||||
throw invalidInstanceException.setMessage(ex.getDiagnostic());
|
||||
}
|
||||
}
|
||||
|
||||
/** Try to instantiate argument type `that' to given type `to'.
|
||||
* If this fails, try to insantiate `that' to `to' where
|
||||
* every occurrence of a type variable in `tvars' is replaced
|
||||
|
@ -331,7 +331,7 @@ public class Resolve {
|
||||
throws Infer.InferenceException {
|
||||
boolean polymorphicSignature = m.isPolymorphicSignatureGeneric() && allowMethodHandles;
|
||||
if (useVarargs && (m.flags() & VARARGS) == 0)
|
||||
throw inapplicableMethodException.setMessage(null);
|
||||
throw inapplicableMethodException.setMessage();
|
||||
Type mt = types.memberType(site, m);
|
||||
|
||||
// tvars is the list of formal type variables for which type arguments
|
||||
@ -386,7 +386,7 @@ public class Resolve {
|
||||
useVarargs,
|
||||
warn);
|
||||
|
||||
checkRawArgumentsAcceptable(argtypes, mt.getParameterTypes(),
|
||||
checkRawArgumentsAcceptable(env, argtypes, mt.getParameterTypes(),
|
||||
allowBoxing, useVarargs, warn);
|
||||
return mt;
|
||||
}
|
||||
@ -411,19 +411,21 @@ public class Resolve {
|
||||
|
||||
/** Check if a parameter list accepts a list of args.
|
||||
*/
|
||||
boolean argumentsAcceptable(List<Type> argtypes,
|
||||
boolean argumentsAcceptable(Env<AttrContext> env,
|
||||
List<Type> argtypes,
|
||||
List<Type> formals,
|
||||
boolean allowBoxing,
|
||||
boolean useVarargs,
|
||||
Warner warn) {
|
||||
try {
|
||||
checkRawArgumentsAcceptable(argtypes, formals, allowBoxing, useVarargs, warn);
|
||||
checkRawArgumentsAcceptable(env, argtypes, formals, allowBoxing, useVarargs, warn);
|
||||
return true;
|
||||
} catch (InapplicableMethodException ex) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
void checkRawArgumentsAcceptable(List<Type> argtypes,
|
||||
void checkRawArgumentsAcceptable(Env<AttrContext> env,
|
||||
List<Type> argtypes,
|
||||
List<Type> formals,
|
||||
boolean allowBoxing,
|
||||
boolean useVarargs,
|
||||
@ -460,6 +462,14 @@ public class Resolve {
|
||||
elt);
|
||||
argtypes = argtypes.tail;
|
||||
}
|
||||
//check varargs element type accessibility
|
||||
if (!isAccessible(env, elt)) {
|
||||
Symbol location = env.enclClass.sym;
|
||||
throw inapplicableMethodException.setMessage("inaccessible.varargs.type",
|
||||
elt,
|
||||
Kinds.kindName(location),
|
||||
location);
|
||||
}
|
||||
}
|
||||
return;
|
||||
}
|
||||
@ -474,6 +484,10 @@ public class Resolve {
|
||||
this.diagnostic = null;
|
||||
this.diags = diags;
|
||||
}
|
||||
InapplicableMethodException setMessage() {
|
||||
this.diagnostic = null;
|
||||
return this;
|
||||
}
|
||||
InapplicableMethodException setMessage(String key) {
|
||||
this.diagnostic = key != null ? diags.fragment(key) : null;
|
||||
return this;
|
||||
@ -482,6 +496,10 @@ public class Resolve {
|
||||
this.diagnostic = key != null ? diags.fragment(key, args) : null;
|
||||
return this;
|
||||
}
|
||||
InapplicableMethodException setMessage(JCDiagnostic diag) {
|
||||
this.diagnostic = diag;
|
||||
return this;
|
||||
}
|
||||
|
||||
public JCDiagnostic getDiagnostic() {
|
||||
return diagnostic;
|
||||
|
@ -831,6 +831,10 @@ compiler.misc.varargs.trustme.on.non.varargs.meth=\
|
||||
compiler.misc.varargs.trustme.on.virtual.varargs=\
|
||||
Instance method {0} is not final.
|
||||
|
||||
# 0: type, 1: kind, 2: symbol
|
||||
compiler.misc.inaccessible.varargs.type=\
|
||||
formal varargs element type {0} is not accessible from {1} {2}
|
||||
|
||||
# In the following string, {1} will always be the detail message from
|
||||
# java.io.IOException.
|
||||
# 0: symbol, 1: string
|
||||
@ -1564,11 +1568,6 @@ compiler.misc.inferred.do.not.conform.to.bounds=\
|
||||
inferred: {0}\n\
|
||||
bound(s): {1}
|
||||
|
||||
compiler.misc.inferred.do.not.conform.to.params=\
|
||||
actual arguments do not conform to inferred formal arguments\n\
|
||||
required: {0}\n\
|
||||
found: {1}
|
||||
|
||||
# 0: symbol
|
||||
compiler.misc.diamond=\
|
||||
{0}<>
|
||||
|
@ -63,7 +63,6 @@ compiler.misc.fatal.err.cant.locate.meth # Resolve, from Lower
|
||||
compiler.misc.fatal.err.cant.close.loader # JavacProcessingEnvironment
|
||||
compiler.misc.file.does.not.contain.package
|
||||
compiler.misc.illegal.start.of.class.file
|
||||
compiler.misc.inferred.do.not.conform.to.params # UNUSED (hard to see if very complex inference scenario might require this though, so leaving it in, as per JLS3)
|
||||
compiler.misc.kindname.annotation
|
||||
compiler.misc.kindname.enum
|
||||
compiler.misc.kindname.package
|
||||
|
@ -0,0 +1,31 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
// key: compiler.misc.inaccessible.varargs.type
|
||||
// key: compiler.err.cant.apply.symbol.1
|
||||
|
||||
import p1.B;
|
||||
|
||||
class InaccessibleVarargsType {
|
||||
{ new B().foo(new B(), new B()); }
|
||||
}
|
@ -0,0 +1,28 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package p1;
|
||||
|
||||
class A {
|
||||
A() { }
|
||||
}
|
@ -0,0 +1,29 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package p1;
|
||||
|
||||
public class B extends A {
|
||||
public B() {}
|
||||
public void foo(A... args) { }
|
||||
}
|
@ -1,2 +1,2 @@
|
||||
T6638712c.java:16:9: compiler.err.cant.apply.symbol.1: kindname.method, sort, T[],java.util.Comparator<? super T>, java.lang.Enum[],java.util.Comparator<java.lang.Enum<?>>, kindname.class, T6638712c, (compiler.misc.inferred.do.not.conform.to.params: java.lang.Enum[],java.util.Comparator<? super java.lang.Enum>, java.lang.Enum[],java.util.Comparator<java.lang.Enum<?>>)
|
||||
T6638712c.java:16:9: compiler.err.cant.apply.symbol.1: kindname.method, sort, T[],java.util.Comparator<? super T>, java.lang.Enum[],java.util.Comparator<java.lang.Enum<?>>, kindname.class, T6638712c, (compiler.misc.no.conforming.assignment.exists: java.util.Comparator<java.lang.Enum<?>>, java.util.Comparator<? super java.lang.Enum>)
|
||||
1 error
|
||||
|
@ -1,2 +1,2 @@
|
||||
T6638712d.java:16:9: compiler.err.cant.apply.symbol.1: kindname.method, m, U,java.util.List<java.util.List<U>>, int,java.util.List<java.util.List<java.lang.String>>, kindname.class, T6638712d, (compiler.misc.inferred.do.not.conform.to.params: java.lang.String,java.util.List<java.util.List<java.lang.String>>, int,java.util.List<java.util.List<java.lang.String>>)
|
||||
T6638712d.java:16:9: compiler.err.cant.apply.symbol.1: kindname.method, m, U,java.util.List<java.util.List<U>>, int,java.util.List<java.util.List<java.lang.String>>, kindname.class, T6638712d, (compiler.misc.no.conforming.assignment.exists: int, java.lang.String)
|
||||
1 error
|
||||
|
18
langtools/test/tools/javac/varargs/6313164/T6313164.java
Normal file
18
langtools/test/tools/javac/varargs/6313164/T6313164.java
Normal file
@ -0,0 +1,18 @@
|
||||
/*
|
||||
* @test /nodynamiccopyright/
|
||||
* @bug 6313164
|
||||
* @author mcimadamore
|
||||
* @summary javac generates code that fails byte code verification for the varargs feature
|
||||
* @compile/fail/ref=T6313164.out -XDrawDiagnostics T6313164.java
|
||||
*/
|
||||
import p1.*;
|
||||
|
||||
class T6313164 {
|
||||
{ B b = new B();
|
||||
b.foo1(new B(), new B()); //error - A not accesible
|
||||
b.foo2(new B(), new B()); //ok - A not accessible, but foo2(Object...) applicable
|
||||
b.foo3(null, null); //error - A (inferred) not accesible
|
||||
b.foo4(null, null); //error - A (inferred in 15.12.2.8 - no resolution backtrack) not accesible
|
||||
b.foo4(new B(), new C()); //ok - A (inferred in 15.12.2.7) not accessible, but foo4(Object...) applicable
|
||||
}
|
||||
}
|
6
langtools/test/tools/javac/varargs/6313164/T6313164.out
Normal file
6
langtools/test/tools/javac/varargs/6313164/T6313164.out
Normal file
@ -0,0 +1,6 @@
|
||||
T6313164.java:12:8: compiler.err.cant.apply.symbol.1: kindname.method, foo1, p1.A[], p1.B,p1.B, kindname.class, p1.B, (compiler.misc.inaccessible.varargs.type: p1.A, kindname.class, T6313164)
|
||||
T6313164.java:14:13: compiler.err.invalid.inferred.types: X, (compiler.misc.inaccessible.varargs.type: p1.A, kindname.class, T6313164)
|
||||
T6313164.java:15:13: compiler.err.invalid.inferred.types: X, (compiler.misc.inaccessible.varargs.type: p1.A, kindname.class, T6313164)
|
||||
- compiler.note.unchecked.filename: B.java
|
||||
- compiler.note.unchecked.recompile
|
||||
3 errors
|
28
langtools/test/tools/javac/varargs/6313164/p1/A.java
Normal file
28
langtools/test/tools/javac/varargs/6313164/p1/A.java
Normal file
@ -0,0 +1,28 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package p1;
|
||||
|
||||
class A {
|
||||
A() { }
|
||||
}
|
35
langtools/test/tools/javac/varargs/6313164/p1/B.java
Normal file
35
langtools/test/tools/javac/varargs/6313164/p1/B.java
Normal file
@ -0,0 +1,35 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package p1;
|
||||
|
||||
public class B extends A {
|
||||
public B() {}
|
||||
public void foo1(A... args) { }
|
||||
public void foo2(A... args) { }
|
||||
public void foo2(Object... args) { }
|
||||
public <X extends A> void foo3(X... args) { }
|
||||
public <X extends A> void foo4(X... args) { }
|
||||
public void foo4(Object... args) { }
|
||||
|
||||
}
|
26
langtools/test/tools/javac/varargs/6313164/p1/C.java
Normal file
26
langtools/test/tools/javac/varargs/6313164/p1/C.java
Normal file
@ -0,0 +1,26 @@
|
||||
/*
|
||||
* Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU General Public License version 2 only, as
|
||||
* published by the Free Software Foundation.
|
||||
*
|
||||
* This code is distributed in the hope that it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
||||
* version 2 for more details (a copy is included in the LICENSE file that
|
||||
* accompanied this code).
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License version
|
||||
* 2 along with this work; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
|
||||
*
|
||||
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
|
||||
* or visit www.oracle.com if you need additional information or have any
|
||||
* questions.
|
||||
*/
|
||||
|
||||
package p1;
|
||||
|
||||
public class C extends A { }
|
Loading…
x
Reference in New Issue
Block a user