From joe.darcy at oracle.com Tue Mar 7 09:27:52 2017 From: joe.darcy at oracle.com (joe darcy) Date: Tue, 7 Mar 2017 01:27:52 -0800 Subject: JDK 9 RFR of JDK-8176266: Mae visitUnknown specification more explicit Message-ID: <07e7c5ce-aafd-4751-9f83-c549d662548d@oracle.com> Hello, The various visitUnknown methods in the javax.lang.model API do not explicitly state they pass down their arguments to the new exception. This detail should be made explicit. Please review the patch below. Thanks, -Joe diff -r 099bb085017a src/java.compiler/share/classes/javax/lang/model/element/ModuleElement.java --- a/src/java.compiler/share/classes/javax/lang/model/element/ModuleElement.java Mon Mar 06 08:57:41 2017 -0800 +++ b/src/java.compiler/share/classes/javax/lang/model/element/ModuleElement.java Tue Mar 07 01:27:26 2017 -0800 @@ -251,7 +251,7 @@ * @param p a visitor-specified parameter * @return a visitor-specified result * @throws UnknownDirectiveException a visitor implementation may optionally throw this exception - * @implSpec This implementation throws {@code UnknownDirectiveException}. + * @implSpec This implementation throws {@code new UnknownDirectiveException(d, p)}. */ default R visitUnknown(Directive d, P p) { throw new UnknownDirectiveException(d, p); diff -r 099bb085017a src/java.compiler/share/classes/javax/lang/model/util/AbstractAnnotationValueVisitor6.java --- a/src/java.compiler/share/classes/javax/lang/model/util/AbstractAnnotationValueVisitor6.java Mon Mar 06 08:57:41 2017 -0800 +++ b/src/java.compiler/share/classes/javax/lang/model/util/AbstractAnnotationValueVisitor6.java Tue Mar 07 01:27:26 2017 -0800 @@ -106,7 +106,7 @@ * * @implSpec The default implementation of this method in {@code * AbstractAnnotationValueVisitor6} will always throw {@code - * UnknownAnnotationValueException}. This behavior is not + * new UnknownAnnotationValueException(av, p)}. This behavior is not * required of a subclass. * * @param av {@inheritDoc} diff -r 099bb085017a src/java.compiler/share/classes/javax/lang/model/util/AbstractElementVisitor6.java --- a/src/java.compiler/share/classes/javax/lang/model/util/AbstractElementVisitor6.java Mon Mar 06 08:57:41 2017 -0800 +++ b/src/java.compiler/share/classes/javax/lang/model/util/AbstractElementVisitor6.java Tue Mar 07 01:27:26 2017 -0800 @@ -111,7 +111,7 @@ * * @implSpec The default implementation of this method in * {@code AbstractElementVisitor6} will always throw - * {@code UnknownElementException}. + * {@code new UnknownElementException(e, p)}. * This behavior is not required of a subclass. * * @param e {@inheritDoc} diff -r 099bb085017a src/java.compiler/share/classes/javax/lang/model/util/AbstractTypeVisitor6.java --- a/src/java.compiler/share/classes/javax/lang/model/util/AbstractTypeVisitor6.java Mon Mar 06 08:57:41 2017 -0800 +++ b/src/java.compiler/share/classes/javax/lang/model/util/AbstractTypeVisitor6.java Tue Mar 07 01:27:26 2017 -0800 @@ -142,7 +142,7 @@ * * @implSpec The default implementation of this method in {@code * AbstractTypeVisitor6} will always throw {@code - * UnknownTypeException}. This behavior is not required of a + * new UnknownTypeException(t, p)}. This behavior is not required of a * subclass. * * @param t {@inheritDoc} -------------- next part -------------- An HTML attachment was scrubbed... URL: From jan.lahoda at oracle.com Tue Mar 7 09:49:28 2017 From: jan.lahoda at oracle.com (Jan Lahoda) Date: Tue, 7 Mar 2017 10:49:28 +0100 Subject: JDK 9 RFR of JDK-8176266: Mae visitUnknown specification more explicit In-Reply-To: <07e7c5ce-aafd-4751-9f83-c549d662548d@oracle.com> References: <07e7c5ce-aafd-4751-9f83-c549d662548d@oracle.com> Message-ID: <58BE8228.7020106@oracle.com> Seems OK to me. Jan On 7.3.2017 10:27, joe darcy wrote: > Hello, > > The various visitUnknown methods in the javax.lang.model API do not > explicitly state they pass down their arguments to the new exception. > > This detail should be made explicit. > > Please review the patch below. > > Thanks, > > -Joe > > > diff -r 099bb085017a > src/java.compiler/share/classes/javax/lang/model/element/ModuleElement.java > --- > a/src/java.compiler/share/classes/javax/lang/model/element/ModuleElement.java > Mon Mar 06 08:57:41 2017 -0800 > +++ > b/src/java.compiler/share/classes/javax/lang/model/element/ModuleElement.java > Tue Mar 07 01:27:26 2017 -0800 > @@ -251,7 +251,7 @@ > * @param p a visitor-specified parameter > * @return a visitor-specified result > * @throws UnknownDirectiveException a visitor implementation > may optionally throw this exception > - * @implSpec This implementation throws {@code > UnknownDirectiveException}. > + * @implSpec This implementation throws {@code new > UnknownDirectiveException(d, p)}. > */ > default R visitUnknown(Directive d, P p) { > throw new UnknownDirectiveException(d, p); > diff -r 099bb085017a > src/java.compiler/share/classes/javax/lang/model/util/AbstractAnnotationValueVisitor6.java > --- > a/src/java.compiler/share/classes/javax/lang/model/util/AbstractAnnotationValueVisitor6.java > Mon Mar 06 08:57:41 2017 -0800 > +++ > b/src/java.compiler/share/classes/javax/lang/model/util/AbstractAnnotationValueVisitor6.java > Tue Mar 07 01:27:26 2017 -0800 > @@ -106,7 +106,7 @@ > * > * @implSpec The default implementation of this method in {@code > * AbstractAnnotationValueVisitor6} will always throw {@code > - * UnknownAnnotationValueException}. This behavior is not > + * new UnknownAnnotationValueException(av, p)}. This behavior is not > * required of a subclass. > * > * @param av {@inheritDoc} > diff -r 099bb085017a > src/java.compiler/share/classes/javax/lang/model/util/AbstractElementVisitor6.java > --- > a/src/java.compiler/share/classes/javax/lang/model/util/AbstractElementVisitor6.java > Mon Mar 06 08:57:41 2017 -0800 > +++ > b/src/java.compiler/share/classes/javax/lang/model/util/AbstractElementVisitor6.java > Tue Mar 07 01:27:26 2017 -0800 > @@ -111,7 +111,7 @@ > * > * @implSpec The default implementation of this method in > * {@code AbstractElementVisitor6} will always throw > - * {@code UnknownElementException}. > + * {@code new UnknownElementException(e, p)}. > * This behavior is not required of a subclass. > * > * @param e {@inheritDoc} > diff -r 099bb085017a > src/java.compiler/share/classes/javax/lang/model/util/AbstractTypeVisitor6.java > --- > a/src/java.compiler/share/classes/javax/lang/model/util/AbstractTypeVisitor6.java > Mon Mar 06 08:57:41 2017 -0800 > +++ > b/src/java.compiler/share/classes/javax/lang/model/util/AbstractTypeVisitor6.java > Tue Mar 07 01:27:26 2017 -0800 > @@ -142,7 +142,7 @@ > * > * @implSpec The default implementation of this method in {@code > * AbstractTypeVisitor6} will always throw {@code > - * UnknownTypeException}. This behavior is not required of a > + * new UnknownTypeException(t, p)}. This behavior is not required of a > * subclass. > * > * @param t {@inheritDoc} > From bsrbnd at gmail.com Tue Mar 7 17:29:20 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Tue, 7 Mar 2017 18:29:20 +0100 Subject: [PATCH] 8035271: Incorrect code attribute indentation In-Reply-To: References: <58936F47.60105@oracle.com> Message-ID: Hi, Does this patch need to be improved? Thanks, Bernard 2017-02-06 15:02 GMT+01:00 B. Blaser : > Jonathan, > > 2017-02-02 18:41 GMT+01:00 Jonathan Gibbons : >> Bernard, >> >> In other tests with significant amounts of golden text, we have found it >> more >> readable to use \n in the golden strings, and use a single .replaceAll >> on the string to change the \n to the platform newline character. This >> avoids having to use + LS + at the end of each line. >> >> I will look at your changeset in full context, but comments like >> "// Same as CodeWriter.write()" may be meaningful now, but may be less >> relevant a year or two down the road, prompting questions like "why does >> this need to be stated?". >> >> Separately, I note that the window of opportunity for fixes like this in JDK >> 9 >> is rapidly closing, and at some point, we will have to push such fixes to >> the >> JDK 10 repos that were recently opened. >> >> -- Jon > > Thanks for your answer, I agree with your comments. > Please, find next the updated patch. > > Bernard > >> On 02/02/2017 09:05 AM, B. Blaser wrote: >>> >>> Hi, >>> >>> Next is a small fix to preserve the same code attribute indentation >>> for all javap options (issue 8035271), along with a test. >>> >>> Bernard > > diff --git a/src/jdk.jdeps/share/classes/com/sun/tools/javap/ClassWriter.java > b/src/jdk.jdeps/share/classes/com/sun/tools/javap/ClassWriter.java > --- a/src/jdk.jdeps/share/classes/com/sun/tools/javap/ClassWriter.java > +++ b/src/jdk.jdeps/share/classes/com/sun/tools/javap/ClassWriter.java > @@ -571,13 +571,17 @@ > } else if (code != null) { > if (options.showDisassembled) { > println("Code:"); > + indent(+1); > codeWriter.writeInstrs(code); > codeWriter.writeExceptionTable(code); > + indent(-1); > } > > if (options.showLineAndLocalVariableTables) { > + indent(+1); > attrWriter.write(code, > code.attributes.get(Attribute.LineNumberTable), constant_pool); > attrWriter.write(code, > code.attributes.get(Attribute.LocalVariableTable), constant_pool); > + indent(-1); > } > } > > diff --git a/test/tools/javap/CodeAttributeIndentation.java > b/test/tools/javap/CodeAttributeIndentation.java > new file mode 100644 > --- /dev/null > +++ b/test/tools/javap/CodeAttributeIndentation.java > @@ -0,0 +1,65 @@ > +/* > + * @test > + * @bug 8035271 > + * @summary Same code attribute indentation for all options. > + * @library /tools/lib > + * @modules jdk.compiler/com.sun.tools.javac.api > + * jdk.compiler/com.sun.tools.javac.main > + * jdk.jdeps/com.sun.tools.javap > + * @build toolbox.ToolBox toolbox.JavacTask toolbox.JavapTask > + * @run main CodeAttributeIndentation > + */ > + > +import toolbox.ToolBox; > +import toolbox.JavacTask; > +import toolbox.JavapTask; > +import toolbox.Task.OutputKind; > + > +public class CodeAttributeIndentation { > + public static void main(String... args) { > + String LS = System.getProperty("line.separator"); > + > + String src = ( > + "public class A {\n" + > + " public void a() {}\n" + > + "}" > + ).replaceAll("\n", LS); > + > + String expected = ( > + "Compiled from \"A.java\"\n" + > + "public class A {\n" + > + " public A();\n" + > + " Code:\n" + > + " 0: aload_0\n" + > + " 1: invokespecial #1 " + > + "// Method java/lang/Object.\"\":()V\n" + > + " 4: return\n" + > + " LineNumberTable:\n" + > + " line 1: 0\n" + > + " LocalVariableTable:\n" + > + " Start Length Slot Name Signature\n" + > + " 0 5 0 this LA;\n" + > + "\n" + > + " public void a();\n" + > + " Code:\n" + > + " 0: return\n" + > + " LineNumberTable:\n" + > + " line 2: 0\n" + > + " LocalVariableTable:\n" + > + " Start Length Slot Name Signature\n" + > + " 0 1 0 this LA;\n" + > + "}\n" > + ).replaceAll("\n", LS); > + > + ToolBox tb = new ToolBox(); > + > + new JavacTask(tb).options("-g").sources(src).run(); > + > + String actual = new JavapTask(tb).options("-c", > "-l").classes("A.class") > + .run().getOutput(OutputKind.DIRECT); > + > + if (!actual.equals(expected)) > + throw new AssertionError("Incorrect code attribute indentation: " + > + LS + actual); > + } > +} From joe.darcy at oracle.com Fri Mar 10 01:19:54 2017 From: joe.darcy at oracle.com (joe darcy) Date: Thu, 9 Mar 2017 17:19:54 -0800 Subject: JDK 9 RFR of DK-8176477: Use DirectiveVisitor to print module information Message-ID: <9658c592-8cc9-b040-356f-e1817079f2b0@oracle.com> Hello, The printing processor's support for modules ( JDK-8173609 ) was added before the directive visitor was added ( JDK-8175118 ). The printing implementation should be refactored to use the directive visitor. Please review the webrev implementation that refactoring: http://cr.openjdk.java.net/~darcy/8176477.0/ Thanks, -Joe From jonathan.gibbons at oracle.com Fri Mar 10 02:06:34 2017 From: jonathan.gibbons at oracle.com (Jonathan Gibbons) Date: Thu, 09 Mar 2017 18:06:34 -0800 Subject: JDK 9 RFR of DK-8176477: Use DirectiveVisitor to print module information In-Reply-To: <9658c592-8cc9-b040-356f-e1817079f2b0@oracle.com> References: <9658c592-8cc9-b040-356f-e1817079f2b0@oracle.com> Message-ID: <58C20A2A.7060908@oracle.com> Nice ;-) -- Jon On 03/09/2017 05:19 PM, joe darcy wrote: > Hello, > > The printing processor's support for modules ( JDK-8173609 ) was added > before the directive visitor was added ( JDK-8175118 ). > > The printing implementation should be refactored to use the directive > visitor. Please review the webrev implementation that refactoring: > > http://cr.openjdk.java.net/~darcy/8176477.0/ > > Thanks, > > -Joe > From joe.darcy at oracle.com Fri Mar 10 05:40:20 2017 From: joe.darcy at oracle.com (joe darcy) Date: Thu, 9 Mar 2017 21:40:20 -0800 Subject: JDK-8176482: Use of DirectiveVisitor needs @DefinedBy annotation for RunCodingRules.java Message-ID: <12a3e979-985c-383a-236a-0d5ec6619074@oracle.com> Hello, *sigh* Sometimes it pays to run all the test, even ones where there is no way they could fail! The patch below correct an oversight in the recently-pushed 8176477: "Use DirectiveVisitor to print module information" which neglected to include the @DefinedBy annotation it is use of the DirectiveVisitor type. Thanks, -Joe --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/processing/PrintingProcessor.java Thu Mar 09 18:33:47 2017 -0800 +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/processing/PrintingProcessor.java Thu Mar 09 21:32:17 2017 -0800 @@ -334,7 +334,7 @@ this.writer = writer; } - @Override + @Override @DefinedBy(Api.LANGUAGE_MODEL) public Void visitExports(ExportsDirective d, Void p) { // "exports package-name [to module-name-list]" writer.print("exports "); @@ -343,7 +343,7 @@ return null; } - @Override + @Override @DefinedBy(Api.LANGUAGE_MODEL) public Void visitOpens(OpensDirective d, Void p) { // opens package-name [to module-name-list] writer.print("opens "); @@ -352,7 +352,7 @@ return null; } - @Override + @Override @DefinedBy(Api.LANGUAGE_MODEL) public Void visitProvides(ProvidesDirective d, Void p) { // provides service-name with implementation-name writer.print("provides "); @@ -362,7 +362,7 @@ return null; } - @Override + @Override @DefinedBy(Api.LANGUAGE_MODEL) public Void visitRequires(RequiresDirective d, Void p) { // requires (static|transitive)* module-name writer.print("requires "); @@ -374,7 +374,7 @@ return null; } - @Override + @Override @DefinedBy(Api.LANGUAGE_MODEL) public Void visitUses(UsesDirective d, Void p) { // uses service-name writer.print("uses "); From jan.lahoda at oracle.com Fri Mar 10 07:02:50 2017 From: jan.lahoda at oracle.com (Jan Lahoda) Date: Fri, 10 Mar 2017 08:02:50 +0100 Subject: JDK-8176482: Use of DirectiveVisitor needs @DefinedBy annotation for RunCodingRules.java In-Reply-To: <12a3e979-985c-383a-236a-0d5ec6619074@oracle.com> References: <12a3e979-985c-383a-236a-0d5ec6619074@oracle.com> Message-ID: <58C24F9A.40008@oracle.com> Seems OK. Jan On 10.3.2017 06:40, joe darcy wrote: > Hello, > > *sigh* > > Sometimes it pays to run all the test, even ones where there is no way > they could fail! > > The patch below correct an oversight in the recently-pushed 8176477: > "Use DirectiveVisitor to print module information" which neglected to > include the @DefinedBy annotation it is use of the DirectiveVisitor type. > > Thanks, > > -Joe > > --- > a/src/jdk.compiler/share/classes/com/sun/tools/javac/processing/PrintingProcessor.java > Thu Mar 09 18:33:47 2017 -0800 > +++ > b/src/jdk.compiler/share/classes/com/sun/tools/javac/processing/PrintingProcessor.java > Thu Mar 09 21:32:17 2017 -0800 > @@ -334,7 +334,7 @@ > this.writer = writer; > } > > - @Override > + @Override @DefinedBy(Api.LANGUAGE_MODEL) > public Void visitExports(ExportsDirective d, Void p) { > // "exports package-name [to module-name-list]" > writer.print("exports "); > @@ -343,7 +343,7 @@ > return null; > } > > - @Override > + @Override @DefinedBy(Api.LANGUAGE_MODEL) > public Void visitOpens(OpensDirective d, Void p) { > // opens package-name [to module-name-list] > writer.print("opens "); > @@ -352,7 +352,7 @@ > return null; > } > > - @Override > + @Override @DefinedBy(Api.LANGUAGE_MODEL) > public Void visitProvides(ProvidesDirective d, Void p) { > // provides service-name with implementation-name > writer.print("provides "); > @@ -362,7 +362,7 @@ > return null; > } > > - @Override > + @Override @DefinedBy(Api.LANGUAGE_MODEL) > public Void visitRequires(RequiresDirective d, Void p) { > // requires (static|transitive)* module-name > writer.print("requires "); > @@ -374,7 +374,7 @@ > return null; > } > > - @Override > + @Override @DefinedBy(Api.LANGUAGE_MODEL) > public Void visitUses(UsesDirective d, Void p) { > // uses service-name > writer.print("uses "); > From georgiy.rakov at oracle.com Fri Mar 10 20:02:09 2017 From: georgiy.rakov at oracle.com (Georgiy Rakov) Date: Fri, 10 Mar 2017 23:02:09 +0300 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? Message-ID: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> Hello, let's consider following code: class MyType {} class MyList { MyList copyThis() { return null; } } class Foo { Foo(MyType a){ } } public class Test26 { public static void main(String argv[]) { MyList l1 = new MyList<>(); m2(l1, m1( new Foo<>(new MyType()){ } ).copyThis()); } public static MyList m2(MyList l1, MyList l2) { return null; } public static MyList m1(U item) { return null; } } it fails to compile by javac from JDK 9 build 160 with following error: Error:(15, 11) java: incompatible types: inference variable T has incompatible equality constraints ,Foo But it seems that this code should compile successfully because: 1. When performing invocation type inference for m1 invocation, a temporary method is chosen according to following assertion from 18.2.1: If the expression is a class instance creation expression or a method invocation expression, the constraint reduces to the bound set B3 which would be used to determine the expression's invocation type when targeting T, as defined in ?18.5.2. (For a class instance creation expression, the corresponding "method" used for inference is defined in ?15.9.3). 2. The temporary method return type is an anonymous class superclass as it's specified by following assertions from 15.9.3 JLS 9 draft: ... If C is an anonymous class, let D be the superclass or superinterface of C named by the class instance creation expression. The return type of mj is ?j applied to D. 3. So the return type of the temporary method is Foo. 4. Unchecked conversion is necessary in order for constructor Foo to be applicable so the return type D is erased and should be Foo. 5. Thus m1 inference variable U should be inferred as Foo and m1 return type should be inferred as MyList. 6. Finally m2 inference variable T should be inferred as Foo with no incompatible constraints. Is it javac bug? Thank you, Georgiy. -------------- next part -------------- class MyType {} class MyList { MyList copyThis() { return null; } } class Foo { Foo(MyType a){ } } public class Test26 { public static void main(String argv[]) { MyList l1 = new MyList<>(); m2(l1, m1( new Foo<>(new MyType()){ } ).copyThis()); } public static MyList m2(MyList l1, MyList l2) { return null; } public static MyList m1(U item) { return null; } } From maurizio.cimadamore at oracle.com Fri Mar 10 21:46:19 2017 From: maurizio.cimadamore at oracle.com (Maurizio Cimadamore) Date: Fri, 10 Mar 2017 21:46:19 +0000 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> Message-ID: <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> Hi Georgiy - thanks for the report. Just so that I understand - is this a regression or is it a new test and that's the behavior you are seeing with the latest build? I'm asking because I don't recall recent changes in this area. That said, I think your analysis looks correct - the spec draft calls for the anonymous inner class non-denotable type to be 'normalized'. Maurizio On 10/03/17 20:02, Georgiy Rakov wrote: > class MyType {} > > class MyList { > MyList copyThis() { return null; } > } > > class Foo { > Foo(MyType a){ } > } > > public class Test26 { > public static void main(String argv[]) { > MyList l1 = new MyList<>(); > m2(l1, m1( > new Foo<>(new MyType()){ } > ).copyThis()); > } > public static MyList m2(MyList l1, MyList l2) { > return null; } > public static MyList m1(U item) { return null; } > } From jonathan.gibbons at oracle.com Sat Mar 11 01:52:53 2017 From: jonathan.gibbons at oracle.com (Jonathan Gibbons) Date: Fri, 10 Mar 2017 17:52:53 -0800 Subject: RFR: 8176492 @since value errors in java.compiler module Message-ID: <58C35875.1050205@oracle.com> Please review the following simple update to fix some errors in the @since tags in the java.compiler module. JBS: https://bugs.openjdk.java.net/browse/JDK-8176492 Webrev: http://cr.openjdk.java.net/~jjg/8176492/webrev.00/ -- Jon From joe.darcy at oracle.com Sat Mar 11 14:34:37 2017 From: joe.darcy at oracle.com (joe darcy) Date: Sat, 11 Mar 2017 06:34:37 -0800 Subject: RFR: 8176492 @since value errors in java.compiler module In-Reply-To: <58C35875.1050205@oracle.com> References: <58C35875.1050205@oracle.com> Message-ID: <40aa52a7-3b50-9b2c-cfc1-a45776b0f0ea@oracle.com> Looks good; thanks, -Joe On 3/10/2017 5:52 PM, Jonathan Gibbons wrote: > Please review the following simple update to fix some errors in the > @since tags in the java.compiler module. > > JBS: https://bugs.openjdk.java.net/browse/JDK-8176492 > Webrev: http://cr.openjdk.java.net/~jjg/8176492/webrev.00/ > > -- Jon From bsrbnd at gmail.com Sat Mar 11 15:05:04 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Sat, 11 Mar 2017 16:05:04 +0100 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> Message-ID: Hi, On 10 March 2017 at 22:46, Maurizio Cimadamore wrote: > Hi Georgiy - thanks for the report. Just so that I understand - is this a > regression or is it a new test and that's the behavior you are seeing with > the latest build? I'm asking because I don't recall recent changes in this > area. > > That said, I think your analysis looks correct - the spec draft calls for > the anonymous inner class non-denotable type to be 'normalized'. > > Maurizio The problem seems to be present since build 82, 136, 152 and rev a21e5b9dc5c3 (1.5 month ago). Next is a patch that corrects this specific case upon rev a21e5b9dc5c3 (needs to be well tested). It 'normalizes' T when checking for same type (Types.isSameType(), Types.SameTypeVisitor.visitClassType() and Types.SameTypeVisitor.visitUndetVar()). Bernard diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java @@ -1022,6 +1022,20 @@ isSameTypeStrict.visit(t, s) : isSameTypeLoose.visit(t, s); } + private Type normalize(Type t) { + if (t.tsym.name.isEmpty()) { + // Anonymous class + ClassType norm = (ClassType) t.tsym.type; + if (norm == null) + return null; + else if (norm.interfaces_field != null && norm.interfaces_field.nonEmpty()) + return norm.interfaces_field.head; + else + return norm.supertype_field; + } + else + return t; + } // where abstract class SameTypeVisitor extends TypeRelation { @@ -1070,7 +1084,7 @@ @Override public Boolean visitClassType(ClassType t, Type s) { - if (t == s) + if (normalize(t) == normalize(s)) return true; if (s.isPartial()) @@ -1152,7 +1166,7 @@ return true; } - t.addBound(InferenceBound.EQ, s, Types.this); + t.addBound(InferenceBound.EQ, normalize(s), Types.this); return true; } > On 10/03/17 20:02, Georgiy Rakov wrote: >> >> class MyType {} >> >> class MyList { >> MyList copyThis() { return null; } >> } >> >> class Foo { >> Foo(MyType a){ } >> } >> >> public class Test26 { >> public static void main(String argv[]) { >> MyList l1 = new MyList<>(); >> m2(l1, m1( >> new Foo<>(new MyType()){ } >> ).copyThis()); >> } >> public static MyList m2(MyList l1, MyList l2) { return >> null; } >> public static MyList m1(U item) { return null; } >> } > > From maurizio.cimadamore at oracle.com Sat Mar 11 21:49:34 2017 From: maurizio.cimadamore at oracle.com (Maurizio Cimadamore) Date: Sat, 11 Mar 2017 21:49:34 +0000 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> Message-ID: On 11/03/17 15:05, B. Blaser wrote: > Hi, > > On 10 March 2017 at 22:46, Maurizio Cimadamore > wrote: >> Hi Georgiy - thanks for the report. Just so that I understand - is this a >> regression or is it a new test and that's the behavior you are seeing with >> the latest build? I'm asking because I don't recall recent changes in this >> area. >> >> That said, I think your analysis looks correct - the spec draft calls for >> the anonymous inner class non-denotable type to be 'normalized'. >> >> Maurizio > The problem seems to be present since build 82, 136, 152 and rev > a21e5b9dc5c3 (1.5 month ago). Uhm - I looked at a21e5b9dc5c3, and all I found is this: http://hg.openjdk.java.net/jdk9/dev/langtools/rev/a21e5b9dc5c3 Which seems unlikely to cause inference issues? > > Next is a patch that corrects this specific case upon rev a21e5b9dc5c3 > (needs to be well tested). > It 'normalizes' T when checking for same type (Types.isSameType(), > Types.SameTypeVisitor.visitClassType() and > Types.SameTypeVisitor.visitUndetVar()). I believe the issue should be addressed in a more direct way - as per Georgiy's evaluation, the spec draft says that the type of new Foo<>() { ... } is simply Foo, not an anonymous type. So normalization should never be needed during type-checking. Maurizio > > Bernard > > diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > @@ -1022,6 +1022,20 @@ > isSameTypeStrict.visit(t, s) : > isSameTypeLoose.visit(t, s); > } > + private Type normalize(Type t) { > + if (t.tsym.name.isEmpty()) { > + // Anonymous class > + ClassType norm = (ClassType) t.tsym.type; > + if (norm == null) > + return null; > + else if (norm.interfaces_field != null && > norm.interfaces_field.nonEmpty()) > + return norm.interfaces_field.head; > + else > + return norm.supertype_field; > + } > + else > + return t; > + } > // where > abstract class SameTypeVisitor extends TypeRelation { > > @@ -1070,7 +1084,7 @@ > > @Override > public Boolean visitClassType(ClassType t, Type s) { > - if (t == s) > + if (normalize(t) == normalize(s)) > return true; > > if (s.isPartial()) > @@ -1152,7 +1166,7 @@ > return true; > } > > - t.addBound(InferenceBound.EQ, s, Types.this); > + t.addBound(InferenceBound.EQ, normalize(s), Types.this); > > return true; > } > >> On 10/03/17 20:02, Georgiy Rakov wrote: >>> class MyType {} >>> >>> class MyList { >>> MyList copyThis() { return null; } >>> } >>> >>> class Foo { >>> Foo(MyType a){ } >>> } >>> >>> public class Test26 { >>> public static void main(String argv[]) { >>> MyList l1 = new MyList<>(); >>> m2(l1, m1( >>> new Foo<>(new MyType()){ } >>> ).copyThis()); >>> } >>> public static MyList m2(MyList l1, MyList l2) { return >>> null; } >>> public static MyList m1(U item) { return null; } >>> } >> From forax at univ-mlv.fr Mon Mar 13 07:05:29 2017 From: forax at univ-mlv.fr (Remi Forax) Date: Mon, 13 Mar 2017 08:05:29 +0100 (CET) Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> Message-ID: <2050655766.36864.1489388729659.JavaMail.zimbra@u-pem.fr> Hi Maurizio, ----- Mail original ----- > De: "Maurizio Cimadamore" > ?: "B. Blaser" > Cc: compiler-dev at openjdk.java.net > Envoy?: Samedi 11 Mars 2017 22:49:34 > Objet: Re: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous > class type? > On 11/03/17 15:05, B. Blaser wrote: >> Hi, >> >> On 10 March 2017 at 22:46, Maurizio Cimadamore >> wrote: >>> Hi Georgiy - thanks for the report. Just so that I understand - is this a >>> regression or is it a new test and that's the behavior you are seeing with >>> the latest build? I'm asking because I don't recall recent changes in this >>> area. >>> >>> That said, I think your analysis looks correct - the spec draft calls for >>> the anonymous inner class non-denotable type to be 'normalized'. >>> >>> Maurizio >> The problem seems to be present since build 82, 136, 152 and rev >> a21e5b9dc5c3 (1.5 month ago). > Uhm - I looked at a21e5b9dc5c3, and all I found is this: > > http://hg.openjdk.java.net/jdk9/dev/langtools/rev/a21e5b9dc5c3 > > Which seems unlikely to cause inference issues? >> >> Next is a patch that corrects this specific case upon rev a21e5b9dc5c3 >> (needs to be well tested). >> It 'normalizes' T when checking for same type (Types.isSameType(), >> Types.SameTypeVisitor.visitClassType() and >> Types.SameTypeVisitor.visitUndetVar()). > I believe the issue should be addressed in a more direct way - as per > Georgiy's evaluation, the spec draft says that the type of > > new Foo<>() { ... } > > is simply Foo, not an anonymous type. So normalization should never be > needed during type-checking. You can not do that ! new Object() { } is typed as the anonymous inner class, not Object, the goal of the inference, at least for the average guy, is to fill the blank, the resulting type has to be either the anonymous inner class or we should remove this feature. > > Maurizio R?mi >> >> Bernard >> >> diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >> b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >> --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >> +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >> @@ -1022,6 +1022,20 @@ >> isSameTypeStrict.visit(t, s) : >> isSameTypeLoose.visit(t, s); >> } >> + private Type normalize(Type t) { >> + if (t.tsym.name.isEmpty()) { >> + // Anonymous class >> + ClassType norm = (ClassType) t.tsym.type; >> + if (norm == null) >> + return null; >> + else if (norm.interfaces_field != null && >> norm.interfaces_field.nonEmpty()) >> + return norm.interfaces_field.head; >> + else >> + return norm.supertype_field; >> + } >> + else >> + return t; >> + } >> // where >> abstract class SameTypeVisitor extends TypeRelation { >> >> @@ -1070,7 +1084,7 @@ >> >> @Override >> public Boolean visitClassType(ClassType t, Type s) { >> - if (t == s) >> + if (normalize(t) == normalize(s)) >> return true; >> >> if (s.isPartial()) >> @@ -1152,7 +1166,7 @@ >> return true; >> } >> >> - t.addBound(InferenceBound.EQ, s, Types.this); >> + t.addBound(InferenceBound.EQ, normalize(s), Types.this); >> >> return true; >> } >> >>> On 10/03/17 20:02, Georgiy Rakov wrote: >>>> class MyType {} >>>> >>>> class MyList { >>>> MyList copyThis() { return null; } >>>> } >>>> >>>> class Foo { >>>> Foo(MyType a){ } >>>> } >>>> >>>> public class Test26 { >>>> public static void main(String argv[]) { >>>> MyList l1 = new MyList<>(); >>>> m2(l1, m1( >>>> new Foo<>(new MyType()){ } >>>> ).copyThis()); >>>> } >>>> public static MyList m2(MyList l1, MyList l2) { return >>>> null; } >>>> public static MyList m1(U item) { return null; } >>>> } From srikanth.adayapalam at oracle.com Mon Mar 13 07:54:03 2017 From: srikanth.adayapalam at oracle.com (Srikanth) Date: Mon, 13 Mar 2017 13:24:03 +0530 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: <2050655766.36864.1489388729659.JavaMail.zimbra@u-pem.fr> References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> <2050655766.36864.1489388729659.JavaMail.zimbra@u-pem.fr> Message-ID: <58C6501B.2050309@oracle.com> https://bugs.openjdk.java.net/browse/JDK-8133936 seems to have some wordings that explains the rationale. Srikanth On Monday 13 March 2017 12:35 PM, Remi Forax wrote: > Hi Maurizio, > > ----- Mail original ----- >> De: "Maurizio Cimadamore" >> ?: "B. Blaser" >> Cc: compiler-dev at openjdk.java.net >> Envoy?: Samedi 11 Mars 2017 22:49:34 >> Objet: Re: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous >> class type? >> On 11/03/17 15:05, B. Blaser wrote: >>> Hi, >>> >>> On 10 March 2017 at 22:46, Maurizio Cimadamore >>> wrote: >>>> Hi Georgiy - thanks for the report. Just so that I understand - is this a >>>> regression or is it a new test and that's the behavior you are seeing with >>>> the latest build? I'm asking because I don't recall recent changes in this >>>> area. >>>> >>>> That said, I think your analysis looks correct - the spec draft calls for >>>> the anonymous inner class non-denotable type to be 'normalized'. >>>> >>>> Maurizio >>> The problem seems to be present since build 82, 136, 152 and rev >>> a21e5b9dc5c3 (1.5 month ago). >> Uhm - I looked at a21e5b9dc5c3, and all I found is this: >> >> http://hg.openjdk.java.net/jdk9/dev/langtools/rev/a21e5b9dc5c3 >> >> Which seems unlikely to cause inference issues? >>> Next is a patch that corrects this specific case upon rev a21e5b9dc5c3 >>> (needs to be well tested). >>> It 'normalizes' T when checking for same type (Types.isSameType(), >>> Types.SameTypeVisitor.visitClassType() and >>> Types.SameTypeVisitor.visitUndetVar()). >> I believe the issue should be addressed in a more direct way - as per >> Georgiy's evaluation, the spec draft says that the type of >> >> new Foo<>() { ... } >> >> is simply Foo, not an anonymous type. So normalization should never be >> needed during type-checking. > You can not do that ! > > new Object() { } is typed as the anonymous inner class, not Object, > the goal of the inference, at least for the average guy, is to fill the blank, > the resulting type has to be either the anonymous inner class or we should remove this feature. > >> Maurizio > R?mi > >>> Bernard >>> >>> diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >>> b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >>> --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >>> +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java >>> @@ -1022,6 +1022,20 @@ >>> isSameTypeStrict.visit(t, s) : >>> isSameTypeLoose.visit(t, s); >>> } >>> + private Type normalize(Type t) { >>> + if (t.tsym.name.isEmpty()) { >>> + // Anonymous class >>> + ClassType norm = (ClassType) t.tsym.type; >>> + if (norm == null) >>> + return null; >>> + else if (norm.interfaces_field != null && >>> norm.interfaces_field.nonEmpty()) >>> + return norm.interfaces_field.head; >>> + else >>> + return norm.supertype_field; >>> + } >>> + else >>> + return t; >>> + } >>> // where >>> abstract class SameTypeVisitor extends TypeRelation { >>> >>> @@ -1070,7 +1084,7 @@ >>> >>> @Override >>> public Boolean visitClassType(ClassType t, Type s) { >>> - if (t == s) >>> + if (normalize(t) == normalize(s)) >>> return true; >>> >>> if (s.isPartial()) >>> @@ -1152,7 +1166,7 @@ >>> return true; >>> } >>> >>> - t.addBound(InferenceBound.EQ, s, Types.this); >>> + t.addBound(InferenceBound.EQ, normalize(s), Types.this); >>> >>> return true; >>> } >>> >>>> On 10/03/17 20:02, Georgiy Rakov wrote: >>>>> class MyType {} >>>>> >>>>> class MyList { >>>>> MyList copyThis() { return null; } >>>>> } >>>>> >>>>> class Foo { >>>>> Foo(MyType a){ } >>>>> } >>>>> >>>>> public class Test26 { >>>>> public static void main(String argv[]) { >>>>> MyList l1 = new MyList<>(); >>>>> m2(l1, m1( >>>>> new Foo<>(new MyType()){ } >>>>> ).copyThis()); >>>>> } >>>>> public static MyList m2(MyList l1, MyList l2) { return >>>>> null; } >>>>> public static MyList m1(U item) { return null; } >>>>> } From bsrbnd at gmail.com Mon Mar 13 12:00:33 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Mon, 13 Mar 2017 13:00:33 +0100 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: <58C6501B.2050309@oracle.com> References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> <2050655766.36864.1489388729659.JavaMail.zimbra@u-pem.fr> <58C6501B.2050309@oracle.com> Message-ID: Hi, On 13 March 2017 at 08:54, Srikanth wrote: > https://bugs.openjdk.java.net/browse/JDK-8133936 seems to have some wordings > that explains the > rationale. > > Srikanth There is a small difference between Georgiy's example and jdk 8133936 as shown in the commented example here under. Georgiy's said: "4. Unchecked conversion is necessary in order for constructor Foo to be applicable so the return type D is erased and should be Foo." Which relates to Daniel's comment on jdk 8133936: "If C is an anonymous class, then the chosen constructor is the constructor of the anonymous class. The return type is the anonymous class type." Then: - in Georgiy's example, the constructor's return type is chosen (due to unchecked conversion) and javac fails. - in jdk 8133936 example, the mj's return type is chosen and javac succeeds. The question is: - Is this right to use the constructor's return type in Georgiy's example instead of mj's return type? Bernard class List { List() {} List getThis() { return new List(); } } class MyType {} class Foo { // public Foo(T a1){} public Foo(MyType a1){} } public class Test25 { public static List m1(T item) { List l = new List(); return l; } public static void m2(List list1, List list2) { } public static void test() { // m2(new List>(), m1(new Foo<>("str"){ }).getThis()); m2(new List(), m1(new Foo<>(new MyType()){ }).getThis()); } } From bsrbnd at gmail.com Mon Mar 13 14:13:47 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Mon, 13 Mar 2017 15:13:47 +0100 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> <2050655766.36864.1489388729659.JavaMail.zimbra@u-pem.fr> <58C6501B.2050309@oracle.com> Message-ID: On 13 March 2017 at 13:00, B. Blaser wrote: > Hi, > > On 13 March 2017 at 08:54, Srikanth wrote: >> https://bugs.openjdk.java.net/browse/JDK-8133936 seems to have some wordings >> that explains the >> rationale. >> >> Srikanth > > There is a small difference between Georgiy's example and jdk 8133936 > as shown in the commented example here under. > > Georgiy's said: > > "4. Unchecked conversion is necessary in order for constructor Foo to be > applicable so the return type D is erased and should be Foo." > > Which relates to Daniel's comment on jdk 8133936: > > "If C is an anonymous class, then the chosen constructor is the constructor of > the anonymous class. The return type is the anonymous class type." > > Then: > - in Georgiy's example, the constructor's return type is chosen (due > to unchecked conversion) and javac fails. > - in jdk 8133936 example, the mj's return type is chosen and javac succeeds. > > The question is: > - Is this right to use the constructor's return type in Georgiy's > example instead of mj's return type? To resume: - if Foo isn't generic (or erased), the constructor's return type is used. For example: class Foo {} m2(new List(), m1(new Foo(){ }).getThis()); also fails to compile. - if Foo is generic, the mj's return type Foo is used. Which seems to be compliant with JLS 15.9.3; but the behavior isn't absolutely orthogonal between generic and non-generic types as it seems to be driven by inference needs... See Daniel's comment on jdk 8133936: "This is pretty messy, but there's a reason for it: we can't really talk about a class type '[anonymous Foo<___>]' until we can fill in the blank." Bernard > class List { > List() {} > List getThis() { > return new List(); > } > } > class MyType {} > class Foo { > // public Foo(T a1){} > public Foo(MyType a1){} > } > public class Test25 { > public static List m1(T item) { > List l = new List(); > return l; > } > public static void m2(List list1, List list2) { } > public static void test() { > // m2(new List>(), m1(new Foo<>("str"){ }).getThis()); > m2(new List(), m1(new Foo<>(new MyType()){ }).getThis()); > } > } From georgiy.rakov at oracle.com Mon Mar 13 14:45:39 2017 From: georgiy.rakov at oracle.com (Georgiy Rakov) Date: Mon, 13 Mar 2017 17:45:39 +0300 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> Message-ID: <86e2e42f-3232-f3f3-bfa4-26e0021fba11@oracle.com> Hi Maurizio, this example can be considered as a new test which resulted from correcting existing test stemmed from Dan's comment in JDK-8133936. This behavior is reproduced on JDK build 160. As it follows from your reply it's likely to be a javac issue, so I've filed a bug: JDK-8176577. Thanks, Georgiy. On 11.03.2017 0:46, Maurizio Cimadamore wrote: > Hi Georgiy - thanks for the report. Just so that I understand - is > this a regression or is it a new test and that's the behavior you are > seeing with the latest build? I'm asking because I don't recall recent > changes in this area. > > That said, I think your analysis looks correct - the spec draft calls > for the anonymous inner class non-denotable type to be 'normalized'. > > Maurizio > > On 10/03/17 20:02, Georgiy Rakov wrote: >> class MyType {} >> >> class MyList { >> MyList copyThis() { return null; } >> } >> >> class Foo { >> Foo(MyType a){ } >> } >> >> public class Test26 { >> public static void main(String argv[]) { >> MyList l1 = new MyList<>(); >> m2(l1, m1( >> new Foo<>(new MyType()){ } >> ).copyThis()); >> } >> public static MyList m2(MyList l1, MyList l2) { >> return null; } >> public static MyList m1(U item) { return null; } >> } > From daniel.smith at oracle.com Mon Mar 13 19:12:01 2017 From: daniel.smith at oracle.com (Dan Smith) Date: Mon, 13 Mar 2017 13:12:01 -0600 Subject: Anonymous class instance creation expression with diamond compatibility constraint is reduced to anonymous class type? In-Reply-To: <86e2e42f-3232-f3f3-bfa4-26e0021fba11@oracle.com> References: <9cc0d943-062d-df46-a6fa-417b33997ea2@oracle.com> <94203846-8ab8-08b7-b7df-6fb06fcdede1@oracle.com> <86e2e42f-3232-f3f3-bfa4-26e0021fba11@oracle.com> Message-ID: > On Mar 13, 2017, at 8:45 AM, Georgiy Rakov wrote: > > Hi Maurizio, > > this example can be considered as a new test which resulted from correcting existing test stemmed from Dan's comment in JDK-8133936. This behavior is reproduced on JDK build 160. > > As it follows from your reply it's likely to be a javac issue, so I've filed a bug: JDK-8176577. To clarify some confusion in this thread: I agree with Georgiy's interpretation of the spec. The test program he provided should compile. This is consistent with my comment on JDK-8133936. ?Dan From stuart.marks at oracle.com Tue Mar 14 03:35:00 2017 From: stuart.marks at oracle.com (Stuart Marks) Date: Mon, 13 Mar 2017 20:35:00 -0700 Subject: RFR 9 (xs): 8171395 (jdeprscan) add comments to L10N message file Message-ID: <402f0b3e-32bf-bfba-34d4-5f4b0e2a75ae@oracle.com> Hi Leo, all, Please review this small changeset to the jdeprscan resource properties file. It simply adds some comments to explain the various format elements, to help out with translation. Patch appended below. Thanks, s'marks # HG changeset patch # User smarks # Date 1489457980 25200 # Mon Mar 13 19:19:40 2017 -0700 # Node ID 9a523636445575e5b174ed78e8f0779b4cae8fd2 # Parent 6b51827c339c267f484248c9bd10e6bc9fe00703 8171395: (jdeprscan) add comments to L10N message file Reviewed-by: XXX diff -r 6b51827c339c -r 9a5236364455 src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/resources/jdeprscan.properties --- a/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/resources/jdeprscan.properties Fri Mar 10 09:52:49 2017 -0800 +++ b/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/resources/jdeprscan.properties Mon Mar 13 19:19:40 2017 -0700 @@ -75,24 +75,52 @@ scan.process.class=Processing class {0}... +# The "removal tag": empty for normal deprecations, +# nonempty for removal deprecations; do not translate. scan.dep.normal= scan.dep.removal=(forRemoval=true) scan.err.exception=error: unexpected exception {0} scan.err.noclass=error: cannot find class {0} scan.err.nofile=error: cannot find file {0} + +# 0: class name, 1: method name, 2: parameter and return types scan.err.nomethod=error: cannot resolve Methodref {0}.{1}:{2} scan.head.jar=Jar file {0}: scan.head.dir=Directory {0}: +# In all of the messages below, 0 and 1 are as follows: +# 0: type kind (class, interface, enum, or annotation type) +# 1: type name +# The last element is generally a "removal tag"; see above. + +# 2: class name, 3: removal tag scan.out.extends={0} {1} extends deprecated class {2} {3} + +# 2: interface name, 3: removal tag scan.out.implements={0} {1} implements deprecated interface {2} {3} + +# 2: class name, 3: removal tag scan.out.usesclass={0} {1} uses deprecated class {2} {3} + +# 2: class name, 3: method name, 4: method parameter and return types, 5: removal tag scan.out.usesmethod={0} {1} uses deprecated method {2}::{3}{4} {5} + +# 2: class name, 3: method name, 4: method parameter and return types, 5: removal tag scan.out.usesintfmethod={0} {1} uses deprecated method {2}::{3}{4} {5} + +# 2: class name, 3: field name, 4: removal tag scan.out.usesfield={0} {1} uses deprecated field {2}::{3} {4} + +# 2: field name, 3: type name, 4: removal tag scan.out.hasfield={0} {1} has field named {2} of deprecated type {3} {4} + +# 2: method name, 3: parameter type, 4: removal tag scan.out.methodparmtype={0} {1} has method named {2} having deprecated parameter type {3} {4} + +# 2: method name, 3: return type, 4: removal tag scan.out.methodrettype={0} {1} has method named {2} having deprecated return type {3} {4} + +# 2: class name, 3: method name, 4: method parameter and return types, 5: removal tag scan.out.methodoverride={0} {1} overrides deprecated method {2}::{3}{4} {5} From bsrbnd at gmail.com Thu Mar 16 12:20:48 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Thu, 16 Mar 2017 13:20:48 +0100 Subject: JDK 8159439: NPEForModuleInfoWithNonZeroSuperClassTest updated Message-ID: Hi, I've noticed that running the javac tests using the "jtreg" target of "build.xml" seems not to take care of the "ProblemList.txt" (is this normal?). For example, tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.java is run and fails (but not with the expected output)... Nevertheless, the reason why it's on the problem list seems to be outdated as asmtools 6.0 includes the module handling. But a recent change in com.sun.tools.javac.jvm.ModuleNameReader.readModuleName() checks the "super_class" field when reading the module name. Which makes this test fail with another message as the expected one. I think this test could probably be removed from the "ProblemList.txt" and the expected output updated as below. Any comment is welcome. Thanks, Bernard diff --git a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out --- a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out +++ b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out @@ -1,2 +1,2 @@ -- compiler.err.cant.access: mod.module-info, (compiler.misc.bad.class.file.header: module-info.class, (compiler.misc.module.info.invalid.super.class)) +- compiler.err.cant.access: .module-info, (compiler.misc.bad.class.file.header: module-info.class, (compiler.misc.module.name.mismatch: mod/module-info, )) 1 error From forax at univ-mlv.fr Thu Mar 16 14:32:38 2017 From: forax at univ-mlv.fr (Remi Forax) Date: Thu, 16 Mar 2017 15:32:38 +0100 (CET) Subject: RFR 8175013: Add @Generated Annotation In-Reply-To: <868d6884-e9b9-bd56-2cd2-57509ad66ce4@oracle.com> References: <000ED8F1-BAFD-4459-8A32-8479C3E9C451@oracle.com> <868d6884-e9b9-bd56-2cd2-57509ad66ce4@oracle.com> Message-ID: <1192828114.938599.1489674758835.JavaMail.zimbra@u-pem.fr> And deprecate the old. Maybe it will be done as a part of another commit given javax.annotation.Generated is in another workspace. so i've added compiler-dev, since this will be commited to langtools. R?mi ----- Mail original ----- > De: "Alan Bateman" > ?: "Lance Andersen" , "core-libs-dev" > Envoy?: Jeudi 16 Mars 2017 14:51:43 > Objet: Re: RFR 8175013: Add @Generated Annotation > On 16/03/2017 13:42, Lance Andersen wrote: >> Hi all, >> >> Per the discussion [1], please find the webrev for adding a replacement >> annotation for javax.annotation.Generated . >> >> > It would be good to have a link from the old @Generated to the new. > > -Alan From lance.andersen at oracle.com Thu Mar 16 14:51:29 2017 From: lance.andersen at oracle.com (Lance Andersen) Date: Thu, 16 Mar 2017 10:51:29 -0400 Subject: RFR 8175013: Add @Generated Annotation In-Reply-To: <1192828114.938599.1489674758835.JavaMail.zimbra@u-pem.fr> References: <000ED8F1-BAFD-4459-8A32-8479C3E9C451@oracle.com> <868d6884-e9b9-bd56-2cd2-57509ad66ce4@oracle.com> <1192828114.938599.1489674758835.JavaMail.zimbra@u-pem.fr> Message-ID: <2BA2E92D-CF96-4165-9683-ECBB165E20EC@oracle.com> Hi Remi, > On Mar 16, 2017, at 10:32 AM, Remi Forax wrote: > > And deprecate the old. We will be deprecating the Java EE modules in Java SE so in a sense that is happening. It would require an MR to common annotations to deprecate the annotation in javax.annotation. and the Java EE folks do not have an MR planned at this time for that JSR Best Lance > > Maybe it will be done as a part of another commit given javax.annotation.Generated is in another workspace. > > so i've added compiler-dev, since this will be commited to langtools. > > R?mi > > ----- Mail original ----- >> De: "Alan Bateman" >> ?: "Lance Andersen" , "core-libs-dev" >> Envoy?: Jeudi 16 Mars 2017 14:51:43 >> Objet: Re: RFR 8175013: Add @Generated Annotation > >> On 16/03/2017 13:42, Lance Andersen wrote: >>> Hi all, >>> >>> Per the discussion [1], please find the webrev for adding a replacement >>> annotation for javax.annotation.Generated . >>> >>> >> It would be good to have a link from the old @Generated to the new. >> >> -Alan Lance Andersen| Principal Member of Technical Staff | +1.781.442.2037 Oracle Java Engineering 1 Network Drive Burlington, MA 01803 Lance.Andersen at oracle.com -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: oracle_sig_logo.gif Type: image/gif Size: 658 bytes Desc: not available URL: From jonathan.gibbons at oracle.com Thu Mar 16 15:23:14 2017 From: jonathan.gibbons at oracle.com (Jonathan Gibbons) Date: Thu, 16 Mar 2017 08:23:14 -0700 Subject: JDK 8159439: NPEForModuleInfoWithNonZeroSuperClassTest updated In-Reply-To: References: Message-ID: <451d2055-f578-3632-ed3d-efd4fd4f2a32@oracle.com> It sounds like build.xml should be updated to use the problem list. I don't how how common it is to use that target, which is probably why this has slipped through. If the test can be fixed and removed from the problem list, that would be good. -- Jon On 3/16/17 5:20 AM, B. Blaser wrote: > Hi, > > I've noticed that running the javac tests using the "jtreg" target of > "build.xml" seems not to take care of the "ProblemList.txt" (is this > normal?). For example, > tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.java > is run and fails (but not with the expected output)... > > Nevertheless, the reason why it's on the problem list seems to be > outdated as asmtools 6.0 includes the module handling. But a recent > change in com.sun.tools.javac.jvm.ModuleNameReader.readModuleName() > checks the "super_class" field when reading the module name. Which > makes this test fail with another message as the expected one. > > I think this test could probably be removed from the "ProblemList.txt" > and the expected output updated as below. Any comment is welcome. > > Thanks, > Bernard > > diff --git a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out > b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out > --- a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out > +++ b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out > @@ -1,2 +1,2 @@ > -- compiler.err.cant.access: mod.module-info, > (compiler.misc.bad.class.file.header: module-info.class, > (compiler.misc.module.info.invalid.super.class)) > +- compiler.err.cant.access: .module-info, > (compiler.misc.bad.class.file.header: module-info.class, > (compiler.misc.module.name.mismatch: mod/module-info, )) > 1 error From ronshapiro at google.com Thu Mar 16 15:44:02 2017 From: ronshapiro at google.com (Ron Shapiro) Date: Thu, 16 Mar 2017 15:44:02 +0000 Subject: RFR 8175013: Add @Generated Annotation In-Reply-To: <2BA2E92D-CF96-4165-9683-ECBB165E20EC@oracle.com> References: <000ED8F1-BAFD-4459-8A32-8479C3E9C451@oracle.com> <868d6884-e9b9-bd56-2cd2-57509ad66ce4@oracle.com> <1192828114.938599.1489674758835.JavaMail.zimbra@u-pem.fr> <2BA2E92D-CF96-4165-9683-ECBB165E20EC@oracle.com> Message-ID: Are there any plans to make the new @Generated annotation have CLASS retention? We have a number of compile-time tools that would like to know when files are generated. No need at runtime, but it would be good to have this information stick around. On Thu, Mar 16, 2017 at 7:52 AM Lance Andersen wrote: Hi Remi, On Mar 16, 2017, at 10:32 AM, Remi Forax wrote: And deprecate the old. We will be deprecating the Java EE modules in Java SE so in a sense that is happening. It would require an MR to common annotations to deprecate the annotation in javax.annotation. and the Java EE folks do not have an MR planned at this time for that JSR Best Lance Maybe it will be done as a part of another commit given javax.annotation.Generated is in another workspace. so i've added compiler-dev, since this will be commited to langtools. R?mi ----- Mail original ----- De: "Alan Bateman" ?: "Lance Andersen" , "core-libs-dev" < core-libs-dev at openjdk.java.net> Envoy?: Jeudi 16 Mars 2017 14:51:43 Objet: Re: RFR 8175013: Add @Generated Annotation On 16/03/2017 13:42, Lance Andersen wrote: Hi all, Per the discussion [1], please find the webrev for adding a replacement annotation for javax.annotation.Generated . It would be good to have a link from the old @Generated to the new. -Alan Lance Andersen| Principal Member of Technical Staff | +1.781.442.2037 <(781)%20442-2037> Oracle Java Engineering 1 Network Drive Burlington, MA 01803 Lance.Andersen at oracle.com -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: oracle_sig_logo.gif Type: image/gif Size: 658 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: oracle_sig_logo.gif Type: image/gif Size: 658 bytes Desc: not available URL: From Alan.Bateman at oracle.com Thu Mar 16 20:01:22 2017 From: Alan.Bateman at oracle.com (Alan Bateman) Date: Thu, 16 Mar 2017 20:01:22 +0000 Subject: RFR 8175013: Add @Generated Annotation In-Reply-To: References: <000ED8F1-BAFD-4459-8A32-8479C3E9C451@oracle.com> <868d6884-e9b9-bd56-2cd2-57509ad66ce4@oracle.com> <1192828114.938599.1489674758835.JavaMail.zimbra@u-pem.fr> <2BA2E92D-CF96-4165-9683-ECBB165E20EC@oracle.com> Message-ID: On 16/03/2017 15:44, Ron Shapiro wrote: > Are there any plans to make the new @Generated annotation have CLASS > retention? We have a number of compile-time tools that would like to > know when files are generated. No need at runtime, but it would be > good to have this information stick around. > JSR-250 has had @Generated fro 10+ years and it would be useful to see if they have had any similar feedback. -Alan -------------- next part -------------- An HTML attachment was scrubbed... URL: From maurizio.cimadamore at oracle.com Thu Mar 16 22:23:02 2017 From: maurizio.cimadamore at oracle.com (Maurizio Cimadamore) Date: Thu, 16 Mar 2017 22:23:02 +0000 Subject: JDK 8159439: NPEForModuleInfoWithNonZeroSuperClassTest updated In-Reply-To: <451d2055-f578-3632-ed3d-efd4fd4f2a32@oracle.com> References: <451d2055-f578-3632-ed3d-efd4fd4f2a32@oracle.com> Message-ID: <8d2865eb-f643-b382-f61d-d84dc3438c1b@oracle.com> On 16/03/17 15:23, Jonathan Gibbons wrote: > It sounds like build.xml should be updated to use the problem list. > > I don't how how common it is to use that target, which is probably > why this has slipped through. My bad - I did not update the target to use the problem list file when I wrote the new modularized ant build. I will look into this (for 10). Maurizio > > If the test can be fixed and removed from the problem list, that > would be good. > > -- Jon > > > On 3/16/17 5:20 AM, B. Blaser wrote: >> Hi, >> >> I've noticed that running the javac tests using the "jtreg" target of >> "build.xml" seems not to take care of the "ProblemList.txt" (is this >> normal?). For example, >> tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.java >> >> is run and fails (but not with the expected output)... >> >> Nevertheless, the reason why it's on the problem list seems to be >> outdated as asmtools 6.0 includes the module handling. But a recent >> change in com.sun.tools.javac.jvm.ModuleNameReader.readModuleName() >> checks the "super_class" field when reading the module name. Which >> makes this test fail with another message as the expected one. >> >> I think this test could probably be removed from the "ProblemList.txt" >> and the expected output updated as below. Any comment is welcome. >> >> Thanks, >> Bernard >> >> diff --git >> a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >> b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >> >> --- >> a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >> +++ >> b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >> @@ -1,2 +1,2 @@ >> -- compiler.err.cant.access: mod.module-info, >> (compiler.misc.bad.class.file.header: module-info.class, >> (compiler.misc.module.info.invalid.super.class)) >> +- compiler.err.cant.access: .module-info, >> (compiler.misc.bad.class.file.header: module-info.class, >> (compiler.misc.module.name.mismatch: mod/module-info, )) >> 1 error > From luke.hutch at gmail.com Fri Mar 17 02:55:02 2017 From: luke.hutch at gmail.com (Luke Hutchison) Date: Thu, 16 Mar 2017 19:55:02 -0700 Subject: Type inference across method chains Message-ID: I have been trying to figure out why type inference doesn't work across method chaining (see the code example below). I finally came across these old messages on lambda-dev: On Tue Jul 16 15:08:05 PDT 2013, Dan Smith wrote: > Without ruling out the possibility of enhancements that address situations like this, [...] the status quo is that when you type a dot, the compiler has to completely type-check the stuff to the left before it can proceed. Inference can do a lot of cool tricks with context, but will not be influenced by "context" that occurs after the dot. [ Archive link: http://mail.openjdk.java.net/pipermail/lambda-dev/2013-July/010544.html ] On Wed Jul 24 12:41:03 PDT 2013, John Rose wrote: > The reason I'm wildly waving this flag is that (I think) I have seen this phenomenon active during the design of streams APIs, ongoing now. [ Archive link: http://mail.openjdk.java.net/pipermail/lambda-dev/2013-July/010629.html ] Method chaining really is getting much more common in Java, with the advent of APIs like Java 8 streaming, Apache Spark and Apache Flink. Type inference across chained calls in Flink seems to work sometimes, but not always, which is frustrating. You end up having to add type declarations in lots of places that shouldn't need them, or breaking method chains into separate declarations so that the compiler can understand the types. Based on Dan Smith's comments in the above thread, it seems that it was decided that the numerous complex steps involved in receiver method resolution had to all be completed before parameter type inference. However, it seems that if the entire graph of all possible method signatures and all type constraints were built before any inference were performed, then all of these steps could be performed simultaneously and iteratively until convergence: in other words, all the types and methods in a method call chain could be solved as a single constraint satisfaction problem. If in the process of solving this constraint satisfaction problem, it was discovered that there is no single satisfying assignment of types to type variables, and/or if this did not result in a single method definition being selected per method name, then a type error would be reported. Based on the discussion in the thread above, it sounds like the reason this hasn't been done yet is due to the complexity of the current compiler design, not because it's not actually possible to do this? Some example code: the method test1() below really should typecheck OK, but gives an error on (l + 1) in Java 8. Providing types for the lambda params in test2() allows the types to propagate one method call further along the chain, but it is frustrating to always have to do that. Breaking up the chaining into two declarations in test3() allows the typechecking to work for both operations, but this defeats the purpose. // Compile with these Maven dependencies: // https://flink.apache.org/downloads.html#maven-dependencies package com.rentlogic.buildingscores.flink; import org.apache.flink.api.java.DataSet; import org.apache.flink.api.java.ExecutionEnvironment; import org.apache.flink.api.java.tuple.Tuple2; import org.apache.flink.util.Collector; public class TestMethodChainInference { private static ExecutionEnvironment env = ExecutionEnvironment.getExecutionEnvironment(); private static DataSet strs = env.fromElements("a", "xy", "pqr"); // Type of l resolved as Object, so (l + 1) gives a type error public static void test1(String[] args) { DataSet strLenPlusOne = strs .flatMap((s, out) -> out.collect(s.length())) .flatMap((l, out) -> out.collect(l + 1)); // ERROR } // No error public static void test2(String[] args) { DataSet strLenPlusOne = strs .flatMap((String s, Collector out)-> out.collect(s.length())) .flatMap((l, out) -> out.collect(l + 1)); } // No error public static void test3(String[] args) { DataSet strLen = strs .flatMap((s, out) -> out.collect(s.length())); DataSet strLenPlusOne = strLen .flatMap((l, out) -> out.collect(l + 1)); } } -------------- next part -------------- An HTML attachment was scrubbed... URL: From huaming.li at oracle.com Fri Mar 17 03:15:30 2017 From: huaming.li at oracle.com (Hamlin Li) Date: Fri, 17 Mar 2017 11:15:30 +0800 Subject: how to tell 2 methods are override-equivalent Message-ID: Hi, ( I'm not sure if this is the right alias to ask the question, please help forward if necessary. ) I have a question about telling whether one method is subsignature of another one. My situation is, 1. there is a TypeElement *t1 *which represents java.net.URL, and a ExecutableElement *m1* which represents getContent(java.lang.Class**[]), 2. there is a String *t2* which is "java.net.URL", and another String *m2 *which is "getContent(java.lang.Class[])". The difference between m1 and m2 is that, m1 is an instance of ExecutableElement, m2 is an instance of String; there is a wildcard type argument in m1. Is there a way to tell whether m1 and m2 are override-equivalent, m2 is subsignature of m1? I suppose I should use javax.lang.model.util.Types.isSubsignature(ExecutableType m1, ExecutableType m2), but I don't know how can I convert ExecutableElement *m1* and String *m2* to**ExecutableType. Or I'm in wrong direction? Thank you -Hamlin -------------- next part -------------- An HTML attachment was scrubbed... URL: From lance.andersen at oracle.com Fri Mar 17 11:36:47 2017 From: lance.andersen at oracle.com (Lance Andersen) Date: Fri, 17 Mar 2017 07:36:47 -0400 Subject: RFR 8175013: Add @Generated Annotation In-Reply-To: References: <000ED8F1-BAFD-4459-8A32-8479C3E9C451@oracle.com> <868d6884-e9b9-bd56-2cd2-57509ad66ce4@oracle.com> <1192828114.938599.1489674758835.JavaMail.zimbra@u-pem.fr> <2BA2E92D-CF96-4165-9683-ECBB165E20EC@oracle.com> Message-ID: <3011A872-C43A-4771-86F9-99C9B14D7535@oracle.com> I have update the webrev to remove MODULE as a Target for now as javax.annotations.processing uses the JDK 8 compiler during the build process. http://cr.openjdk.java.net/~lancea/8175013/webrev.01 Given where we are in the JDK 9 timeline, I prefer to not to change the Retention value. We can have a discussion for JDK 10 regarding the merits of changing the value. Right now the intent is to have a replacement for the JSR 250 flavor of this annotation to provide for an easier transition. Best Lance > On Mar 16, 2017, at 4:01 PM, Alan Bateman wrote: > > On 16/03/2017 15:44, Ron Shapiro wrote: >> Are there any plans to make the new @Generated annotation have CLASS retention? We have a number of compile-time tools that would like to know when files are generated. No need at runtime, but it would be good to have this information stick around. >> > JSR-250 has had @Generated fro 10+ years and it would be useful to see if they have had any similar feedback. > > -Alan Lance Andersen| Principal Member of Technical Staff | +1.781.442.2037 Oracle Java Engineering 1 Network Drive Burlington, MA 01803 Lance.Andersen at oracle.com -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: oracle_sig_logo.gif Type: image/gif Size: 658 bytes Desc: not available URL: From vicente.romero at oracle.com Fri Mar 17 13:08:21 2017 From: vicente.romero at oracle.com (Vicente Romero) Date: Fri, 17 Mar 2017 09:08:21 -0400 Subject: how to tell 2 methods are override-equivalent In-Reply-To: References: Message-ID: Hi Hamlin, How do you obtain m2? I mean at some point it should have been obtained from an executable element or similar. In the worst case you can always generate a simple test case and try to compile it for example: class Test { void getContent(java.lang.Class[] c) {} void getContent(java.lang.Class[] c) {} } this one will fail saying that both methods have the same erasure, HTH, Vicente On 03/16/2017 11:15 PM, Hamlin Li wrote: > > Hi, > > ( I'm not sure if this is the right alias to ask the question, please > help forward if necessary. ) > > I have a question about telling whether one method is subsignature of > another one. My situation is, > > 1. there is a TypeElement *t1 *which represents java.net.URL, and a > ExecutableElement *m1* which represents > getContent(java.lang.Class**[]), > > 2. there is a String *t2* which is "java.net.URL", and another String > *m2 *which is "getContent(java.lang.Class[])". > > The difference between m1 and m2 is that, m1 is an instance of > ExecutableElement, m2 is an instance of String; there is a wildcard > type argument in m1. > > > Is there a way to tell whether m1 and m2 are override-equivalent, m2 > is subsignature of m1? > > I suppose I should use > javax.lang.model.util.Types.isSubsignature(ExecutableType m1, > ExecutableType m2), but I don't know how can I convert > ExecutableElement *m1* and String *m2* to**ExecutableType. > > Or I'm in wrong direction? > > > Thank you > > -Hamlin > -------------- next part -------------- An HTML attachment was scrubbed... URL: From bsrbnd at gmail.com Fri Mar 17 13:40:01 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Fri, 17 Mar 2017 14:40:01 +0100 Subject: JDK 8159439: NPEForModuleInfoWithNonZeroSuperClassTest updated In-Reply-To: <8d2865eb-f643-b382-f61d-d84dc3438c1b@oracle.com> References: <451d2055-f578-3632-ed3d-efd4fd4f2a32@oracle.com> <8d2865eb-f643-b382-f61d-d84dc3438c1b@oracle.com> Message-ID: On 16 March 2017 at 23:23, Maurizio Cimadamore wrote: > > > On 16/03/17 15:23, Jonathan Gibbons wrote: >> >> It sounds like build.xml should be updated to use the problem list. >> >> I don't how how common it is to use that target, which is probably >> why this has slipped through. > > My bad - I did not update the target to use the problem list file when I > wrote the new modularized ant build. I will look into this (for 10). > > Maurizio Great! I also had to include a "pathelement" to "asmtools.jar" as below (which could eventually be pushed to 9 as it seems harmless). The "timeoutFactor" isn't absolutely necessary but useful when the tests are run on a slower CPU. Bernard diff --git a/make/build.xml b/make/build.xml --- a/make/build.xml +++ b/make/build.xml @@ -332,6 +332,7 @@ + @@ -359,6 +360,7 @@ agentvm="@{agentvm}" verbose="@{verbose}" failonerror="false" resultproperty="jtreg.@{name}.result" vmoptions="${coverage.options} @{extra.jvmargs} ${xpatch.noquotes.cmd}"> + >> If the test can be fixed and removed from the problem list, that >> would be good. >> >> -- Jon >> >> >> On 3/16/17 5:20 AM, B. Blaser wrote: >>> >>> Hi, >>> >>> I've noticed that running the javac tests using the "jtreg" target of >>> "build.xml" seems not to take care of the "ProblemList.txt" (is this >>> normal?). For example, >>> >>> tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.java >>> is run and fails (but not with the expected output)... >>> >>> Nevertheless, the reason why it's on the problem list seems to be >>> outdated as asmtools 6.0 includes the module handling. But a recent >>> change in com.sun.tools.javac.jvm.ModuleNameReader.readModuleName() >>> checks the "super_class" field when reading the module name. Which >>> makes this test fail with another message as the expected one. >>> >>> I think this test could probably be removed from the "ProblemList.txt" >>> and the expected output updated as below. Any comment is welcome. >>> >>> Thanks, >>> Bernard >>> >>> diff --git >>> a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >>> >>> b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >>> --- >>> a/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >>> +++ >>> b/test/tools/javac/modules/T8159439/NPEForModuleInfoWithNonZeroSuperClassTest.out >>> @@ -1,2 +1,2 @@ >>> -- compiler.err.cant.access: mod.module-info, >>> (compiler.misc.bad.class.file.header: module-info.class, >>> (compiler.misc.module.info.invalid.super.class)) >>> +- compiler.err.cant.access: .module-info, >>> (compiler.misc.bad.class.file.header: module-info.class, >>> (compiler.misc.module.name.mismatch: mod/module-info, )) >>> 1 error >> >> > From brian.goetz at oracle.com Fri Mar 17 20:19:52 2017 From: brian.goetz at oracle.com (Brian Goetz) Date: Fri, 17 Mar 2017 16:19:52 -0400 Subject: Type inference across method chains In-Reply-To: References: Message-ID: <4552c359-34ef-0935-6e5d-f3c3eb9b43ed@oracle.com> Its a pretty big overstatement to say "type inference doesn't work across method chaining." As is inevitable with type inference, there will be limits, and people will always complain about the marginal example, and say "but this example could be accommodated too, with a more complex inference algorithm." And that's usually correct, but then there will be new cases at the margin, about which people will complain. So let's not fool ourselves that this is "the last case" -- it's just "the next case." There's nothing magic about type inference; it's just constraint solving. The choices one has in designing a type inference algorithm amount to: what constraints to use, and over what scope to solve. There are also a number of hidden trade-offs besides complexity. For example, the larger the scope over which constraints are solved, the more likely error messages will be something like "there was an error somewhere in Foo.java -- which users find unhelpful. So, with that, let's look at your example. The cases which make people complain "type inference doesn't work under chaining" invariably reduce to the case where there is a generic method used as a receiver for a chained invocation, and whose generic type parameters cannot be solved directly from its arguments, but instead would need type information that would have to be back-propagated from later links in the chain (which generally further require information from the target type.) As you correctly point out, there are simple workarounds, such as using explicit lambdas or exact method refs (test2), breaking up the chain (test3), or providing explicit type witnesses (not shown.) > Type inference across chained calls in Flink seems to work sometimes, > but not always, which is frustrating. "sometimes but not always" is a fact of life with type inference; let's not pretend that "always" is a place we could get to. It's just a question of where to draw the line, and accept that there will always be something just over the line. > Method chaining really is getting much more common in Java, with the > advent of APIs like Java 8 streaming, Apache Spark and Apache Flink. > You say this like you think we're not aware of this, or indeed that enabling broader use of chaining in APIs wasn't, like, one of the major goals of the work we did in Java 8 on type inference! The reality is: there will always be limitations, and they will always be annoying when you encounter them. > > Based on the discussion in the thread above, it sounds like the reason > this hasn't been done yet is due to the complexity of the current > compiler design, not because it's not actually possible to do this? > It is indeed not impossible. But, as you say, it adds additional complexity to a type inference algorithm that has already grown quite complex (and which now interacts heavily with another complex mechanism, overload selection). Could we take one more step, and move the corner cases further out to the margins, at the cost of greater complexity (and perhaps decreased usability)? Yes, we could. In Java 8, we chose to leave it here, which I think was a sensible choice. We might someday come back to look at this -- but right now, it seems like this is not the highest-return use of limited and highly specialized resources. On 3/16/2017 10:55 PM, Luke Hutchison wrote: > I have been trying to figure out why type inference doesn't work > across method chaining (see the code example below). I finally came > across these old messages on lambda-dev: > > On Tue Jul 16 15:08:05 PDT 2013, Dan Smith wrote: > > Without ruling out the possibility of enhancements that address > situations like this, [...] the status quo is that when you type a > dot, the compiler has to completely type-check the stuff to the left > before it can proceed. Inference can do a lot of cool tricks with > context, but will not be influenced by "context" that occurs after the > dot. > [ Archive link: > http://mail.openjdk.java.net/pipermail/lambda-dev/2013-July/010544.html ] > > On Wed Jul 24 12:41:03 PDT 2013, John Rose wrote: > > The reason I'm wildly waving this flag is that (I think) I have seen > this phenomenon active during the design of streams APIs, ongoing now. > [ Archive link: > http://mail.openjdk.java.net/pipermail/lambda-dev/2013-July/010629.html ] > > Method chaining really is getting much more common in Java, with the > advent of APIs like Java 8 streaming, Apache Spark and Apache Flink. > > Type inference across chained calls in Flink seems to work sometimes, > but not always, which is frustrating. You end up having to add type > declarations in lots of places that shouldn't need them, or breaking > method chains into separate declarations so that the compiler can > understand the types. > > Based on Dan Smith's comments in the above thread, it seems that it > was decided that the numerous complex steps involved in receiver > method resolution had to all be completed before parameter type > inference. However, it seems that if the entire graph of all possible > method signatures and all type constraints were built before any > inference were performed, then all of these steps could be performed > simultaneously and iteratively until convergence: in other words, all > the types and methods in a method call chain could be solved as a > single constraint satisfaction problem. If in the process of solving > this constraint satisfaction problem, it was discovered that there is > no single satisfying assignment of types to type variables, and/or if > this did not result in a single method definition being selected per > method name, then a type error would be reported. > > Based on the discussion in the thread above, it sounds like the reason > this hasn't been done yet is due to the complexity of the current > compiler design, not because it's not actually possible to do this? > > Some example code: the method test1() below really should typecheck > OK, but gives an error on (l + 1) in Java 8. Providing types for the > lambda params in test2() allows the types to propagate one method call > further along the chain, but it is frustrating to always have to do > that. Breaking up the chaining into two declarations in test3() allows > the typechecking to work for both operations, but this defeats the > purpose. > > > // Compile with these Maven dependencies: > // https://flink.apache.org/downloads.html#maven-dependencies > > package com.rentlogic.buildingscores.flink; > > import org.apache.flink.api.java.DataSet; > import org.apache.flink.api.java.ExecutionEnvironment; > import org.apache.flink.api.java.tuple.Tuple2; > import org.apache.flink.util.Collector; > > public class TestMethodChainInference { > private static ExecutionEnvironment env = > ExecutionEnvironment.getExecutionEnvironment(); > > private static DataSet strs = env.fromElements("a", > "xy", "pqr"); > > // Type of l resolved as Object, so (l + 1) gives a type error > public static void test1(String[] args) { > DataSet strLenPlusOne = strs > .flatMap((s, out) -> out.collect(s.length())) > .flatMap((l, out) -> out.collect(l + 1)); // ERROR > } > > // No error > public static void test2(String[] args) { > DataSet strLenPlusOne = strs > .flatMap((String s, Collector out)-> out.collect(s.length())) > .flatMap((l, out) -> out.collect(l + 1)); > } > > // No error > public static void test3(String[] args) { > DataSet strLen = strs > .flatMap((s, out) -> out.collect(s.length())); > DataSet strLenPlusOne = strLen > .flatMap((l, out) -> out.collect(l + 1)); > } > } > > > > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From luke.hutch at gmail.com Fri Mar 17 20:41:35 2017 From: luke.hutch at gmail.com (Luke Hutchison) Date: Fri, 17 Mar 2017 13:41:35 -0700 Subject: Type inference across method chains In-Reply-To: <4552c359-34ef-0935-6e5d-f3c3eb9b43ed@oracle.com> References: <4552c359-34ef-0935-6e5d-f3c3eb9b43ed@oracle.com> Message-ID: On Fri, Mar 17, 2017 at 1:19 PM, Brian Goetz wrote: > So let's not fool ourselves that this is "the last case" -- it's just "the > next case." > [...] > So, with that, let's look at your example. The cases which make people > complain "type inference doesn't work under chaining" invariably reduce to > the case where there is a generic method used as a receiver for a chained > invocation, and whose generic type parameters cannot be solved directly > from its arguments, but instead would need type information that would have > to be back-propagated from later links in the chain (which generally > further require information from the target type.) > Right, nonetheless, if this single "next case" were solved via bidirectional propagation of type information, rather than the current situation where method overloading before the dot is solved before type inference after the dot, I would argue that this would solve a large majority of remaining real-world cases where an expression should quite obviously typecheck (according to human judgment) but does not. It would certainly cause streaming APIs to work significantly better with generics. This seems to be the most obvious weakness in the current type inference algorithm. It is indeed not impossible. But, as you say, it adds additional > complexity to a type inference algorithm that has already grown quite > complex (and which now interacts heavily with another complex mechanism, > overload selection). Could we take one more step, and move the corner > cases further out to the margins, at the cost of greater complexity (and > perhaps decreased usability)? Yes, we could. In Java 8, we chose to leave > it here, which I think was a sensible choice. > > We might someday come back to look at this -- but right now, it seems like > this is not the highest-return use of limited and highly specialized > resources. > Can you please address in concrete terms, for this specific request only (i.e. for back-propagation of type information before the final decision about method overloading is made, as opposed to "for all cases" or "for the last case") -- just how difficult solving this would be, and what the technical limitations would be given the current type inference algorithm? -------------- next part -------------- An HTML attachment was scrubbed... URL: From brian.goetz at oracle.com Fri Mar 17 21:40:46 2017 From: brian.goetz at oracle.com (Brian Goetz) Date: Fri, 17 Mar 2017 17:40:46 -0400 Subject: Type inference across method chains In-Reply-To: References: <4552c359-34ef-0935-6e5d-f3c3eb9b43ed@oracle.com> Message-ID: <1f7b42cb-43fa-e8c6-92b5-df571739b288@oracle.com> On 3/17/2017 4:41 PM, Luke Hutchison wrote: > Right, nonetheless, if this single "next case" were solved via > bidirectional propagation of type information, rather than the current > situation where method overloading before the dot is solved before > type inference after the dot, I would argue that this would solve a > large majority of remaining real-world cases You may be right, but bear in mind that it *always* looks this way. You forgot the implicit "...that I currently know of" that needs to trail this sentence. The definition of "real world" is implicitly bounded by "the stuff that works now", and always moves. (Ten years ago, chaining was not considered a real world case at all.) > Can you please address in concrete terms, for this specific request > only (i.e. for back-propagation of type information before the final > decision about method overloading is made, as opposed to "for all > cases" or "for the last case") -- just how difficult solving this > would be, and what the technical limitations would be given the > current type inference algorithm? I know you probably don't think you're asking this, but you're basically asking "can you solve the problem (or try until you give up), and then explain what you did." So, that's not really practical, as much as I'd love to have a simple answer I can pull out that fits on a page and is accessible to non-type-system-experts. Suffice to say it's doable, but it's not trivial, and the risks are not trivial. Also, bear in mind that "how difficult" is only one (and in reality, probably the least important) dimension of the problem. "How difficult" corresponds to "how much will it cost Oracle", which is certainly a reasonable input into the decision process, but far from the only one. How about what incremental perceived complexity for the users would it create? What damage would it do to scrutability of diagnostics? What are the compatibility risks? (Adding new constraints into type inference algorithms can often cause something that was previously solvable to become overconstrained, breaking existing code.) What is the consequence for the specification? For implementors like Eclipse that have to implement from the specification? In what ways might it interact with other features, present or future? -------------- next part -------------- An HTML attachment was scrubbed... URL: From bsrbnd at gmail.com Sat Mar 18 18:32:30 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Sat, 18 Mar 2017 19:32:30 +0100 Subject: question about JDK-8063054 (incorrect raw type warnings for method references) In-Reply-To: <532edc20-8715-4b17-15a0-36b99f23bed9@oracle.com> References: <532edc20-8715-4b17-15a0-36b99f23bed9@oracle.com> Message-ID: Hi, On 16 February 2017 at 11:35, Maurizio Cimadamore wrote: > > > On 16/02/17 02:33, Liam Miller-Cushon wrote: >> >> I think the fix might be as simple as replacing >> `!desc.getParameterTypes().head.isParameterized()` with something that >> handles capture variables. > > Hi Liam, > I think your analysis is correct - isParameterized would not work for > non-class types, so something else is required here. I believe intersection > types like Serializable & Comparable might also end up with the same > problem - and, presumably, synthetic inner class types. > > Maurizio Regarding Daniel's JBS comment, I think the condition should be made on isRaw() instead of isParameterized(). The following example wouldn't produce any warning: class Test2 { interface Consumer { void accept(T arg); } interface Parent

{ void foo(); } interface Child extends Parent {} static void m(T arg, Consumer f) {} public void test(Child c) { m(c, Parent::foo); } } Then, we could add a check on the bound of the captured type variable, as below. Liam's example wouldn't produce any warning but the following one would: class Test3 { void test(Box b) { Object o = b.map(Box::get).get(); } interface Func { T apply(S arg); } interface Box { T get(); Box map(Func f); } } Any comment is welcome. Thanks, Bernard diff -r 43a83431f19d src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java Wed Mar 15 15:46:43 2017 +0100 +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java Sat Mar 18 19:01:02 2017 +0100 @@ -2962,9 +2962,15 @@ if (that.getMode() == ReferenceMode.INVOKE && TreeInfo.isStaticSelector(that.expr, names) && - that.kind.isUnbound() && - !desc.getParameterTypes().head.isParameterized()) { - chk.checkRaw(that.expr, localEnv); + that.kind.isUnbound()) { + + Type t = desc.getParameterTypes().head; + if (t.isRaw() || + t.getTag() == TYPEVAR && + ((TypeVar)t).isCaptured() && + ((TypeVar)t).bound.isRaw()) { + chk.checkRaw(that.expr, localEnv); + } } if (that.sym.isStatic() && TreeInfo.isStaticSelector(that.expr, names) && From huaming.li at oracle.com Mon Mar 20 02:13:28 2017 From: huaming.li at oracle.com (Hamlin Li) Date: Mon, 20 Mar 2017 10:13:28 +0800 Subject: how to tell 2 methods are override-equivalent In-Reply-To: References: Message-ID: Hi Vicente, Thank you for responding, please check the comments inline. On 2017/3/17 21:08, Vicente Romero wrote: > Hi Hamlin, > > How do you obtain m2? I mean at some point it should have been > obtained from an executable element or similar. I have a java doclet which scans jdk versions iteratively, m2 was got in previous round of run of the tool , then it's stored in a file (for example when scan jdk 1.8 source code), then parsed and retrieved from the file again (for example when scan jdk 9 source code). > In the worst case you can always generate a simple test case and try > to compile it for example: > > class Test { > void getContent(java.lang.Class[] c) {} > void getContent(java.lang.Class[] c) {} > } > > this one will fail saying that both methods have the same erasure, Yes, it should fail. In my situation, "getContent(java.lang.Class[] c) {}" is the code in jdk 1.8, "getContent(java.lang.Class[] c) {}" is the corresponding code in jdk 9. When I scan jdk 9 source code, I need to tell that getContent(java.lang.Class[] c) and getContent(java.lang.Class[] c) are in fact the same method, rather than 2 different methods. Thank you -Hamlin > > HTH, > Vicente > > On 03/16/2017 11:15 PM, Hamlin Li wrote: >> >> Hi, >> >> ( I'm not sure if this is the right alias to ask the question, please >> help forward if necessary. ) >> >> I have a question about telling whether one method is subsignature of >> another one. My situation is, >> >> 1. there is a TypeElement *t1 *which represents java.net.URL, and a >> ExecutableElement *m1* which represents >> getContent(java.lang.Class**[]), >> >> 2. there is a String *t2* which is "java.net.URL", and another String >> *m2 *which is "getContent(java.lang.Class[])". >> >> The difference between m1 and m2 is that, m1 is an instance of >> ExecutableElement, m2 is an instance of String; there is a wildcard >> type argument in m1. >> >> >> Is there a way to tell whether m1 and m2 are override-equivalent, m2 >> is subsignature of m1? >> >> I suppose I should use >> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >> ExecutableType m2), but I don't know how can I convert >> ExecutableElement *m1* and String *m2* to**ExecutableType. >> >> Or I'm in wrong direction? >> >> >> Thank you >> >> -Hamlin >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From jan.lahoda at oracle.com Tue Mar 21 09:51:04 2017 From: jan.lahoda at oracle.com (Jan Lahoda) Date: Tue, 21 Mar 2017 10:51:04 +0100 Subject: JD 9 RFR: JDK-8177311: Denied access when named module accesses unreferences package from the unnamed module Message-ID: <58D0F788.80403@oracle.com> Hi, I'd like to ask for a review for: Bug: https://bugs.openjdk.java.net/browse/JDK-8177311 http://mail.openjdk.java.net/pipermail/jdk9-dev/2017-March/005672.html Webrev: http://cr.openjdk.java.net/~jlahoda/8177311/webrev.00/ The problem is this: in Resolve.isAccessible when checks if a module can access types from other modules does: currModule.visiblePackages.get(p.fullname) == p But if "p" is from an unnamed module, then it may or may not be in the visiblePackages (depending on whether Symtab.lookupPackage was called on the given package in the context of currModule), as unnamed module packages are computed lazily. So this check may fail incorrectly. The proposal here is to add one more check for the dependency on the unnamed module. How does this look? Thanks, Jan From jonathan.gibbons at oracle.com Tue Mar 21 21:28:09 2017 From: jonathan.gibbons at oracle.com (Jonathan Gibbons) Date: Tue, 21 Mar 2017 14:28:09 -0700 Subject: how to tell 2 methods are override-equivalent In-Reply-To: References: Message-ID: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> Hamlin, Use Element.asType() to move from the Element world to the TypeMirror world. http://download.java.net/java/jdk9/docs/api/javax/lang/model/element/Element.html#asType-- Use Types.asElement(TypeMirror) to go in the reverse direction, from a TypeMirror to an Element. http://download.java.net/java/jdk9/docs/api/javax/lang/model/util/Types.html#asElement-javax.lang.model.type.TypeMirror- but note the reverse direction is lossy and may throw exceptions: e.g. for type "int", there is no direct element equivalent; for type List, the element will be the declaration List -- Jon On 3/16/17 8:15 PM, Hamlin Li wrote: > > Hi, > > ( I'm not sure if this is the right alias to ask the question, please > help forward if necessary. ) > > I have a question about telling whether one method is subsignature of > another one. My situation is, > > 1. there is a TypeElement *t1 *which represents java.net.URL, and a > ExecutableElement *m1* which represents > getContent(java.lang.Class**[]), > > 2. there is a String *t2* which is "java.net.URL", and another String > *m2 *which is "getContent(java.lang.Class[])". > > The difference between m1 and m2 is that, m1 is an instance of > ExecutableElement, m2 is an instance of String; there is a wildcard > type argument in m1. > > > Is there a way to tell whether m1 and m2 are override-equivalent, m2 > is subsignature of m1? > > I suppose I should use > javax.lang.model.util.Types.isSubsignature(ExecutableType m1, > ExecutableType m2), but I don't know how can I convert > ExecutableElement *m1* and String *m2* to**ExecutableType. > > Or I'm in wrong direction? > > > Thank you > > -Hamlin > -------------- next part -------------- An HTML attachment was scrubbed... URL: From martinrb at google.com Tue Mar 21 21:50:26 2017 From: martinrb at google.com (Martin Buchholz) Date: Tue, 21 Mar 2017 14:50:26 -0700 Subject: how to tell 2 methods are override-equivalent In-Reply-To: References: Message-ID: My ancient script findMissingSince examined the generated javadoc for various jdk revisions and parsed the resulting html via regexes (despite http://stackoverflow.com/questions/1732348/regex-match-open-tags-except-xhtml-self-contained-tags ). Whether using hacky regexes or "proper" tools aware of the java language, there is a need to compare method signatures. Erasure-equivalent methods are the "same" method. (As always, it would be nice if the resulting code were available to anyone.) On Sun, Mar 19, 2017 at 7:13 PM, Hamlin Li wrote: > Hi Vicente, > Thank you for responding, please check the comments inline. > > On 2017/3/17 21:08, Vicente Romero wrote: > > Hi Hamlin, > > How do you obtain m2? I mean at some point it should have been obtained > from an executable element or similar. > > I have a java doclet which scans jdk versions iteratively, m2 was got in > previous round of run of the tool , then it's stored in a file (for example > when scan jdk 1.8 source code), then parsed and retrieved from the file > again (for example when scan jdk 9 source code). > > In the worst case you can always generate a simple test case and try to > compile it for example: > > class Test { > void getContent(java.lang.Class[] c) {} > void getContent(java.lang.Class[] c) {} > } > > this one will fail saying that both methods have the same erasure, > > Yes, it should fail. > In my situation, "getContent(java.lang.Class[] c) {}" is the code in jdk > 1.8, "getContent(java.lang.Class[] c) {}" is the corresponding code in > jdk 9. When I scan jdk 9 source code, I need to tell that > getContent(java.lang.Class[] c) and getContent(java.lang.Class[] c) > are in fact the same method, rather than 2 different methods. > > Thank you > -Hamlin > > > HTH, > Vicente > > On 03/16/2017 11:15 PM, Hamlin Li wrote: > > Hi, > > ( I'm not sure if this is the right alias to ask the question, please help > forward if necessary. ) > > I have a question about telling whether one method is subsignature of > another one. My situation is, > > 1. there is a TypeElement *t1 *which represents java.net.URL, and a > ExecutableElement *m1* which represents getContent(java.lang.Class**[]), > > > 2. there is a String *t2* which is "java.net.URL", and another String *m2 > *which is "getContent(java.lang.Class[])". > > The difference between m1 and m2 is that, m1 is an instance of > ExecutableElement, m2 is an instance of String; there is a wildcard type > argument in m1. > > > Is there a way to tell whether m1 and m2 are override-equivalent, m2 is > subsignature of m1? > > I suppose I should use javax.lang.model.util.Types.isSubsignature(ExecutableType > m1, ExecutableType m2), but I don't know how can I convert > ExecutableElement *m1* and String *m2* to ExecutableType. > > Or I'm in wrong direction? > > > Thank you > > -Hamlin > > > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From jonathan.gibbons at oracle.com Wed Mar 22 00:50:12 2017 From: jonathan.gibbons at oracle.com (Jonathan Gibbons) Date: Tue, 21 Mar 2017 17:50:12 -0700 Subject: how to tell 2 methods are override-equivalent In-Reply-To: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> References: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> Message-ID: <58D1CA44.8000503@oracle.com> Hamlin, Note that while it is relative easy to convert a string containing a type name (such as "java.net.URL") to an Element and/or TypeMirror, in general it will not be possible to convert a string like "getContent(java.lang.Class[])" to a Element or TypeMirror, because the string as written does not contain sufficient information. Even if you did provide more info, you would still have to be careful to evaluate the string in the same compilation context as that to which you are comparing it, for the comparison to have any chance of succeeding. Given your other message mentioning a doclet, you are effectively asking to be able to compile fragments of code (i.e. strings) in the context of your doclet, and that is not possible with the existing public API. -- Jon On 03/21/2017 02:28 PM, Jonathan Gibbons wrote: > > Hamlin, > > Use Element.asType() to move from the Element world to the TypeMirror > world. > http://download.java.net/java/jdk9/docs/api/javax/lang/model/element/Element.html#asType-- > > Use Types.asElement(TypeMirror) to go in the reverse direction, from a > TypeMirror to an Element. > http://download.java.net/java/jdk9/docs/api/javax/lang/model/util/Types.html#asElement-javax.lang.model.type.TypeMirror- > but note the reverse direction is lossy and may throw exceptions: > e.g. for type "int", there is no direct element equivalent; for > type List, the element will be the declaration List > > -- Jon > > On 3/16/17 8:15 PM, Hamlin Li wrote: >> >> Hi, >> >> ( I'm not sure if this is the right alias to ask the question, please >> help forward if necessary. ) >> >> I have a question about telling whether one method is subsignature of >> another one. My situation is, >> >> 1. there is a TypeElement *t1 *which represents java.net.URL, and a >> ExecutableElement *m1* which represents >> getContent(java.lang.Class**[]), >> >> 2. there is a String *t2* which is "java.net.URL", and another String >> *m2 *which is "getContent(java.lang.Class[])". >> >> The difference between m1 and m2 is that, m1 is an instance of >> ExecutableElement, m2 is an instance of String; there is a wildcard >> type argument in m1. >> >> >> Is there a way to tell whether m1 and m2 are override-equivalent, m2 >> is subsignature of m1? >> >> I suppose I should use >> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >> ExecutableType m2), but I don't know how can I convert >> ExecutableElement *m1* and String *m2* to**ExecutableType. >> >> Or I'm in wrong direction? >> >> >> Thank you >> >> -Hamlin >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From huaming.li at oracle.com Wed Mar 22 08:57:36 2017 From: huaming.li at oracle.com (Hamlin Li) Date: Wed, 22 Mar 2017 16:57:36 +0800 Subject: how to tell 2 methods are override-equivalent In-Reply-To: <58D1CA44.8000503@oracle.com> References: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> <58D1CA44.8000503@oracle.com> Message-ID: <7880d229-f32f-d2e0-34fd-da3b8ab34748@oracle.com> On 2017/3/22 8:50, Jonathan Gibbons wrote: > Hamlin, > > Note that while it is relative easy to convert a string containing a > type name (such as "java.net.URL") to an Element and/or TypeMirror, in > general it will not be possible to convert a string like > "getContent(java.lang.Class[])" to a Element or TypeMirror, because > the string as written does not contain sufficient information. > > Even if you did provide more info, you would still have to be careful > to evaluate the string in the same compilation context as that to > which you are comparing it, for the comparison to have any chance of > succeeding. Hi Jon, Thank you for explanation. > Given your other message mentioning a doclet, you are effectively > asking to be able to compile fragments of code (i.e. strings) in the > context of your doclet, and that is not possible with the existing > public API. Although it's bad news to me, it saves my time from continuing work in this direction. :-) I will try to find some workaround solve the issue. Thank you -Hamlin > -- Jon > > On 03/21/2017 02:28 PM, Jonathan Gibbons wrote: >> >> Hamlin, >> >> Use Element.asType() to move from the Element world to the TypeMirror >> world. >> http://download.java.net/java/jdk9/docs/api/javax/lang/model/element/Element.html#asType-- >> >> Use Types.asElement(TypeMirror) to go in the reverse direction, from >> a TypeMirror to an Element. >> http://download.java.net/java/jdk9/docs/api/javax/lang/model/util/Types.html#asElement-javax.lang.model.type.TypeMirror- >> but note the reverse direction is lossy and may throw exceptions: >> e.g. for type "int", there is no direct element equivalent; for >> type List, the element will be the declaration List >> >> -- Jon >> >> On 3/16/17 8:15 PM, Hamlin Li wrote: >>> >>> Hi, >>> >>> ( I'm not sure if this is the right alias to ask the question, >>> please help forward if necessary. ) >>> >>> I have a question about telling whether one method is subsignature >>> of another one. My situation is, >>> >>> 1. there is a TypeElement *t1 *which represents java.net.URL, and a >>> ExecutableElement *m1* which represents >>> getContent(java.lang.Class**[]), >>> >>> 2. there is a String *t2* which is "java.net.URL", and another >>> String *m2 *which is "getContent(java.lang.Class[])". >>> >>> The difference between m1 and m2 is that, m1 is an instance of >>> ExecutableElement, m2 is an instance of String; there is a wildcard >>> type argument in m1. >>> >>> >>> Is there a way to tell whether m1 and m2 are override-equivalent, m2 >>> is subsignature of m1? >>> >>> I suppose I should use >>> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >>> ExecutableType m2), but I don't know how can I convert >>> ExecutableElement *m1* and String *m2* to**ExecutableType. >>> >>> Or I'm in wrong direction? >>> >>> >>> Thank you >>> >>> -Hamlin >>> >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From huaming.li at oracle.com Wed Mar 22 09:07:31 2017 From: huaming.li at oracle.com (Hamlin Li) Date: Wed, 22 Mar 2017 17:07:31 +0800 Subject: how to tell 2 methods are override-equivalent In-Reply-To: References: Message-ID: <3c93620e-7576-249c-ec57-066287eb821f@oracle.com> Hi Martin, On 2017/3/22 5:50, Martin Buchholz wrote: > My ancient script findMissingSince examined the generated javadoc for > various jdk revisions and parsed the resulting html via regexes > (despite > http://stackoverflow.com/questions/1732348/regex-match-open-tags-except-xhtml-self-contained-tags > ). Thank you for the information. I find some information about findMissingSince at https://bugs.openjdk.java.net/browse/JDK-6367207, but can not find the valid code. > > Whether using hacky regexes or "proper" tools aware of the java > language, there is a need to compare method signatures. > Erasure-equivalent methods are the "same" method. Agree, it's the issue I'm trying to resolve. > > (As always, it would be nice if the resulting code were available to > anyone.) Agree, I will try to open it when it's good time. For now, it's not mature enough, there are some issues to solve, enhancements to do, and the design/implementation is specific for jdk. When the functionality is ready, I will discuss with stakeholders and management about it. Thank you -Hamlin > > > On Sun, Mar 19, 2017 at 7:13 PM, Hamlin Li > wrote: > > Hi Vicente, > > Thank you for responding, please check the comments inline. > > On 2017/3/17 21:08, Vicente Romero wrote: >> Hi Hamlin, >> >> How do you obtain m2? I mean at some point it should have been >> obtained from an executable element or similar. > I have a java doclet which scans jdk versions iteratively, m2 was > got in previous round of run of the tool , then it's stored in a > file (for example when scan jdk 1.8 source code), then parsed and > retrieved from the file again (for example when scan jdk 9 source > code). >> In the worst case you can always generate a simple test case and >> try to compile it for example: >> >> class Test { >> void getContent(java.lang.Class[] c) {} >> void getContent(java.lang.Class[] c) {} >> } >> >> this one will fail saying that both methods have the same erasure, > Yes, it should fail. > In my situation, "getContent(java.lang.Class[] c) {}" is the code > in jdk 1.8, "getContent(java.lang.Class[] c) {}" is the > corresponding code in jdk 9. When I scan jdk 9 source code, I need > to tell that getContent(java.lang.Class[] c) and > getContent(java.lang.Class[] c) are in fact the same method, > rather than 2 different methods. > > Thank you > -Hamlin >> >> HTH, >> Vicente >> >> On 03/16/2017 11:15 PM, Hamlin Li wrote: >>> >>> Hi, >>> >>> ( I'm not sure if this is the right alias to ask the question, >>> please help forward if necessary. ) >>> >>> I have a question about telling whether one method is >>> subsignature of another one. My situation is, >>> >>> 1. there is a TypeElement *t1 *which represents java.net.URL, >>> and a ExecutableElement *m1* which represents >>> getContent(java.lang.Class**[]), >>> >>> 2. there is a String *t2* which is "java.net.URL", and another >>> String *m2 *which is "getContent(java.lang.Class[])". >>> >>> The difference between m1 and m2 is that, m1 is an instance of >>> ExecutableElement, m2 is an instance of String; there is a >>> wildcard type argument in m1. >>> >>> >>> Is there a way to tell whether m1 and m2 are >>> override-equivalent, m2 is subsignature of m1? >>> >>> I suppose I should use >>> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >>> ExecutableType m2), but I don't know how can I convert >>> ExecutableElement *m1* and String *m2* to**ExecutableType. >>> >>> Or I'm in wrong direction? >>> >>> >>> Thank you >>> >>> -Hamlin >>> >> > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From vicente.romero at oracle.com Wed Mar 22 14:01:17 2017 From: vicente.romero at oracle.com (Vicente Romero) Date: Wed, 22 Mar 2017 10:01:17 -0400 Subject: how to tell 2 methods are override-equivalent In-Reply-To: <7880d229-f32f-d2e0-34fd-da3b8ab34748@oracle.com> References: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> <58D1CA44.8000503@oracle.com> <7880d229-f32f-d2e0-34fd-da3b8ab34748@oracle.com> Message-ID: Hi Hamlin On 03/22/2017 04:57 AM, Hamlin Li wrote: > > On 2017/3/22 8:50, Jonathan Gibbons wrote: >> Hamlin, >> >> Note that while it is relative easy to convert a string containing a >> type name (such as "java.net.URL") to an Element and/or TypeMirror, >> in general it will not be possible to convert a string like >> "getContent(java.lang.Class[])" to a Element or TypeMirror, because >> the string as written does not contain sufficient information. >> >> Even if you did provide more info, you would still have to be careful >> to evaluate the string in the same compilation context as that to >> which you are comparing it, for the comparison to have any chance of >> succeeding. > Hi Jon, > > Thank you for explanation. >> Given your other message mentioning a doclet, you are effectively >> asking to be able to compile fragments of code (i.e. strings) in the >> context of your doclet, and that is not possible with the existing >> public API. > Although it's bad news to me, it saves my time from continuing work in > this direction. :-) > I will try to find some workaround solve the issue. If you have access to the method's descriptor, I believe that you could use it to convert from the method descriptor to the types you need for your comparison, please let me know if you want to explore that option, Vicente > > Thank you > -Hamlin >> -- Jon >> >> On 03/21/2017 02:28 PM, Jonathan Gibbons wrote: >>> >>> Hamlin, >>> >>> Use Element.asType() to move from the Element world to the >>> TypeMirror world. >>> http://download.java.net/java/jdk9/docs/api/javax/lang/model/element/Element.html#asType-- >>> >>> Use Types.asElement(TypeMirror) to go in the reverse direction, from >>> a TypeMirror to an Element. >>> http://download.java.net/java/jdk9/docs/api/javax/lang/model/util/Types.html#asElement-javax.lang.model.type.TypeMirror- >>> but note the reverse direction is lossy and may throw exceptions: >>> e.g. for type "int", there is no direct element equivalent; for >>> type List, the element will be the declaration List >>> >>> -- Jon >>> >>> On 3/16/17 8:15 PM, Hamlin Li wrote: >>>> >>>> Hi, >>>> >>>> ( I'm not sure if this is the right alias to ask the question, >>>> please help forward if necessary. ) >>>> >>>> I have a question about telling whether one method is subsignature >>>> of another one. My situation is, >>>> >>>> 1. there is a TypeElement *t1 *which represents java.net.URL, and a >>>> ExecutableElement *m1* which represents >>>> getContent(java.lang.Class**[]), >>>> >>>> 2. there is a String *t2* which is "java.net.URL", and another >>>> String *m2 *which is "getContent(java.lang.Class[])". >>>> >>>> The difference between m1 and m2 is that, m1 is an instance of >>>> ExecutableElement, m2 is an instance of String; there is a wildcard >>>> type argument in m1. >>>> >>>> >>>> Is there a way to tell whether m1 and m2 are override-equivalent, >>>> m2 is subsignature of m1? >>>> >>>> I suppose I should use >>>> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >>>> ExecutableType m2), but I don't know how can I convert >>>> ExecutableElement *m1* and String *m2* to**ExecutableType. >>>> >>>> Or I'm in wrong direction? >>>> >>>> >>>> Thank you >>>> >>>> -Hamlin >>>> >>> >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From bsrbnd at gmail.com Wed Mar 22 22:04:42 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Wed, 22 Mar 2017 23:04:42 +0100 Subject: question about JDK-8063054 (incorrect raw type warnings for method references) In-Reply-To: References: <532edc20-8715-4b17-15a0-36b99f23bed9@oracle.com> Message-ID: On 18 March 2017 at 19:32, B. Blaser wrote: > Hi, > > On 16 February 2017 at 11:35, Maurizio Cimadamore > wrote: >> >> >> On 16/02/17 02:33, Liam Miller-Cushon wrote: >>> >>> I think the fix might be as simple as replacing >>> `!desc.getParameterTypes().head.isParameterized()` with something that >>> handles capture variables. >> >> Hi Liam, >> I think your analysis is correct - isParameterized would not work for >> non-class types, so something else is required here. I believe intersection >> types like Serializable & Comparable might also end up with the same >> problem - and, presumably, synthetic inner class types. >> >> Maurizio Here are two more examples producing a warning that should probably be avoided (am I right?). The first one involves an intersection type and the second one an anonymous class: class Test5 { > void test(Box b) { Number n = b.map(Box::get).get(); } interface Func { T apply(S arg); } interface Box { T get(); Box map(Func f); } interface A {} } class Test6 { interface Consumer { void accept(T arg); } interface Parent

{ void foo(); } interface Child extends Parent {} static void m(T arg, Consumer f) {} public void test(Child c) { m(new Child() { public void foo() {} }, Parent::foo); } } I had to write (here under) a method Types.isRaw() using a type visitor to handle captured type variables, intersection types and anonymous classes. How does this look, did I miss anything? Thanks, Bernard diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java @@ -227,6 +227,52 @@ }; // + public boolean isRaw(Type t) { + return t != null && isRaw.visit(t); + } + // where + private final UnaryVisitor isRaw = new UnaryVisitor() { + @Override + public Boolean visitType(Type t, Void ignored) { + return t.isRaw(); + } + + @Override + public Boolean visitClassType(ClassType t, Void ignored) { + if (t.isIntersection()) { + for (Type u: ((IntersectionClassType) t).getComponents()) + if (isRaw(u)) + return true; + + return false; + } + else if (t.tsym.name.isEmpty()) { + // Anonymous + if (t.interfaces_field != null) { + for (Type i: t.interfaces_field) + if (isRaw(i)) + return true; + } + else if (t.supertype_field != null && isRaw(t.supertype_field)) + return true; + + return false; + } + + return t.isRaw(); + } + + @Override + public Boolean visitTypeVar(TypeVar t, Void ignored) { + return t.bound != null && isRaw(t.bound); + } + + @Override + public Boolean visitCapturedType(CapturedType t, Void ignored) { + return t.bound != null && isRaw(t.bound); + } + }; + // /** * Return the least specific subtype of t that starts with symbol diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java @@ -2963,7 +2963,7 @@ if (that.getMode() == ReferenceMode.INVOKE && TreeInfo.isStaticSelector(that.expr, names) && that.kind.isUnbound() && - !desc.getParameterTypes().head.isParameterized()) { + types.isRaw(desc.getParameterTypes().head)) { chk.checkRaw(that.expr, localEnv); } > Regarding Daniel's JBS comment, I think the condition should be made > on isRaw() instead of isParameterized(). > The following example wouldn't produce any warning: > > class Test2 { > interface Consumer { void accept(T arg); } > interface Parent

{ void foo(); } > interface Child extends Parent {} > static void m(T arg, Consumer f) {} > public void test(Child c) { m(c, Parent::foo); } > } > > Then, we could add a check on the bound of the captured type variable, > as below. Liam's example wouldn't produce any warning but the > following one would: > > class Test3 { > void test(Box b) { > Object o = b.map(Box::get).get(); > } > interface Func { T apply(S arg); } > interface Box { > T get(); > Box map(Func f); > } > } > > Any comment is welcome. > Thanks, > Bernard > > diff -r 43a83431f19d > src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > Wed Mar 15 15:46:43 2017 +0100 > +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > Sat Mar 18 19:01:02 2017 +0100 > @@ -2962,9 +2962,15 @@ > > if (that.getMode() == ReferenceMode.INVOKE && > TreeInfo.isStaticSelector(that.expr, names) && > - that.kind.isUnbound() && > - !desc.getParameterTypes().head.isParameterized()) { > - chk.checkRaw(that.expr, localEnv); > + that.kind.isUnbound()) { > + > + Type t = desc.getParameterTypes().head; > + if (t.isRaw() || > + t.getTag() == TYPEVAR && > + ((TypeVar)t).isCaptured() && > + ((TypeVar)t).bound.isRaw()) { > + chk.checkRaw(that.expr, localEnv); > + } > } > > if (that.sym.isStatic() && > TreeInfo.isStaticSelector(that.expr, names) && From maurizio.cimadamore at oracle.com Thu Mar 23 11:58:02 2017 From: maurizio.cimadamore at oracle.com (Maurizio Cimadamore) Date: Thu, 23 Mar 2017 11:58:02 +0000 Subject: question about JDK-8063054 (incorrect raw type warnings for method references) In-Reply-To: References: <532edc20-8715-4b17-15a0-36b99f23bed9@oracle.com> Message-ID: <9ad253e7-30bc-f574-8f77-25ca406e5bf6@oracle.com> Hi Bernard, your patch looks good, I think it handles all the problematic cases I can think of. My only reservation is in making isRaw a member of Types, which would hint that that's the definition of a raw type as per JLS 4.8, which it is not. Ultimately, this routine is only used by the logic for checking method references, as an heuristics to try and see if the signature of the functional descriptor contains enough information to allow inference of the parameters of the 'raw' method reference receiver type. Reading closer from the spec (15.13.1), I see the following statement: "In the second search, if P_1 , ..., P_n is not empty and P_1 is a subtype of /ReferenceType/, then the method reference expression is treated as if it were a method invocation expression with argument expressions of types P_2 , ..., P_n . If /ReferenceType/ is a raw type, and there exists a parameterization of this type, G|<|...|>|, that is a supertype of P_1 , the type to search is the result of capture conversion (?5.1.10 ) applied to G|<|...|>|; *otherwise, the type to search is the same as the type of the first search*. Again, the type arguments, if any, are given by the method reference expression." I think the lines in bold are the ones we need to pay attention to; in other words, if the receiver type is raw and the type of the first search is identical to the type of the second search, then it means no inference occurred. I think something like this could easily be achieved w/o any visitors, with something like this: if (that.getMode() == ReferenceMode.INVOKE && TreeInfo.isStaticSelector(that.expr, names) && that.kind.isUnbound() && types.isSameTypes(lookupHelper.site, that.expr.type) { chk.checkRaw(that.expr, localEnv); } I did some quick tests and this simple patch seems to remove the undesired warnings in the examples we have seen so far, but retains them where they are truly deserved. What do you think? Maurizio On 22/03/17 22:04, B. Blaser wrote: > On 18 March 2017 at 19:32, B. Blaser wrote: >> Hi, >> >> On 16 February 2017 at 11:35, Maurizio Cimadamore >> wrote: >>> >>> On 16/02/17 02:33, Liam Miller-Cushon wrote: >>>> I think the fix might be as simple as replacing >>>> `!desc.getParameterTypes().head.isParameterized()` with something that >>>> handles capture variables. >>> Hi Liam, >>> I think your analysis is correct - isParameterized would not work for >>> non-class types, so something else is required here. I believe intersection >>> types like Serializable & Comparable might also end up with the same >>> problem - and, presumably, synthetic inner class types. >>> >>> Maurizio > Here are two more examples producing a warning that should probably be > avoided (am I right?). The first one involves an intersection type and > the second one an anonymous class: > > class Test5 { > > void test(Box b) { > Number n = b.map(Box::get).get(); > } > interface Func { T apply(S arg); } > interface Box { > T get(); > Box map(Func f); > } > interface A {} > } > > class Test6 { > interface Consumer { void accept(T arg); } > interface Parent

{ void foo(); } > interface Child extends Parent {} > static void m(T arg, Consumer f) {} > public void test(Child c) { m(new Child() { public void foo() {} > }, Parent::foo); } > } > > I had to write (here under) a method Types.isRaw() using a type > visitor to handle captured type variables, intersection types and > anonymous classes. > > How does this look, did I miss anything? > > Thanks, > Bernard > > diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/code/Types.java > @@ -227,6 +227,52 @@ > }; > // > > + public boolean isRaw(Type t) { > + return t != null && isRaw.visit(t); > + } > + // where > + private final UnaryVisitor isRaw = new > UnaryVisitor() { > + @Override > + public Boolean visitType(Type t, Void ignored) { > + return t.isRaw(); > + } > + > + @Override > + public Boolean visitClassType(ClassType t, Void ignored) { > + if (t.isIntersection()) { > + for (Type u: ((IntersectionClassType) t).getComponents()) > + if (isRaw(u)) > + return true; > + > + return false; > + } > + else if (t.tsym.name.isEmpty()) { > + // Anonymous > + if (t.interfaces_field != null) { > + for (Type i: t.interfaces_field) > + if (isRaw(i)) > + return true; > + } > + else if (t.supertype_field != null && > isRaw(t.supertype_field)) > + return true; > + > + return false; > + } > + > + return t.isRaw(); > + } > + > + @Override > + public Boolean visitTypeVar(TypeVar t, Void ignored) { > + return t.bound != null && isRaw(t.bound); > + } > + > + @Override > + public Boolean visitCapturedType(CapturedType t, Void ignored) { > + return t.bound != null && isRaw(t.bound); > + } > + }; > + > // > /** > * Return the least specific subtype of t that starts with symbol > diff --git a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java > @@ -2963,7 +2963,7 @@ > if (that.getMode() == ReferenceMode.INVOKE && > TreeInfo.isStaticSelector(that.expr, names) && > that.kind.isUnbound() && > - !desc.getParameterTypes().head.isParameterized()) { > + types.isRaw(desc.getParameterTypes().head)) { > chk.checkRaw(that.expr, localEnv); > } > > >> Regarding Daniel's JBS comment, I think the condition should be made >> on isRaw() instead of isParameterized(). >> The following example wouldn't produce any warning: >> >> class Test2 { >> interface Consumer { void accept(T arg); } >> interface Parent

{ void foo(); } >> interface Child extends Parent {} >> static void m(T arg, Consumer f) {} >> public void test(Child c) { m(c, Parent::foo); } >> } >> >> Then, we could add a check on the bound of the captured type variable, >> as below. Liam's example wouldn't produce any warning but the >> following one would: >> >> class Test3 { >> void test(Box b) { >> Object o = b.map(Box::get).get(); >> } >> interface Func { T apply(S arg); } >> interface Box { >> T get(); >> Box map(Func f); >> } >> } >> >> Any comment is welcome. >> Thanks, >> Bernard >> >> diff -r 43a83431f19d >> src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java >> --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java >> Wed Mar 15 15:46:43 2017 +0100 >> +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Attr.java >> Sat Mar 18 19:01:02 2017 +0100 >> @@ -2962,9 +2962,15 @@ >> >> if (that.getMode() == ReferenceMode.INVOKE && >> TreeInfo.isStaticSelector(that.expr, names) && >> - that.kind.isUnbound() && >> - !desc.getParameterTypes().head.isParameterized()) { >> - chk.checkRaw(that.expr, localEnv); >> + that.kind.isUnbound()) { >> + >> + Type t = desc.getParameterTypes().head; >> + if (t.isRaw() || >> + t.getTag() == TYPEVAR && >> + ((TypeVar)t).isCaptured() && >> + ((TypeVar)t).bound.isRaw()) { >> + chk.checkRaw(that.expr, localEnv); >> + } >> } >> >> if (that.sym.isStatic() && >> TreeInfo.isStaticSelector(that.expr, names) && -------------- next part -------------- An HTML attachment was scrubbed... URL: From brian.goetz at oracle.com Thu Mar 23 16:37:24 2017 From: brian.goetz at oracle.com (Brian Goetz) Date: Thu, 23 Mar 2017 12:37:24 -0400 Subject: Proposal for a simplified syntax for invoking @FunctionalInterface methods In-Reply-To: <45c4ab8a-9571-c428-2439-a172ec7ebeed@oracle.com> References: <45c4ab8a-9571-c428-2439-a172ec7ebeed@oracle.com> Message-ID: [ moving to compiler-dev ] This isn't a new suggestion :) It was discussed initially, and comes around with some regularity as people learn about lambdas in Java. As Maurizio suggests, there are technical issues that get in the way (such as the separate namespace for methods and variables). If we were really motivated to do this, we'd probably accept some complex rules akin to shadowing/obscuring, but there's a deeper, philosophical reason why we think this is a bad fit. And that is: functional interfaces are not function types, they're class types. As much as I understand why people wish they were function types, they are not. Functional interfaces are interfaces, and lambdas are just one way to create an instance of a functional interface -- one can implement a functional interface with named classes, anonymous classes, dynamic proxies, etc. A core design principle of the Java language is transparency -- code should do what it looks like it does. How lambdas are implemented in Java represents a delicate compromise; obscuring this compromise may feel good from a code-writing perspective, but ultimately I think it undermines the transparency of code from a code-reading perspective. >> On 02/03/17 15:10, Timothy Fagan wrote: >>> I'm not sure if this is the appropriate forum, or if this idea has been >>> proposed elsewhere, but I'd like to suggest a simplified syntax for >>> invoking @FunctionalInterface methods. >>> >>> The idea is that if: >>> * foo is a object reference (field, local variable or parameter) whose >>> type is a @FunctionalInterface >>> * there is a statement or expression where foo is used as if it were a >>> method name >>> * the formal parameters of the statement or expression match the formal >>> parameters of the abstract method on the @FunctionalInterface >>> * the formal parameters of the statement or expression do NOT match the >>> formal parameters of any other method in scope named foo >>> Then: >>> * the statement or expression is compiled as an invocation of the >>> @FunctionalInterface abstract method on foo's type. >>> >>> E.g. >>> >>> Function doubleString = s -> s + s; >>> >>> // prints "hellohello" >>> System.out.println(*doubleString*("hello")); >>> >>> -Timothy > >> Something like this was present in the very first draft of the lambda language support [1] - syntax aside, the main issue with this avenue, is that Java has separate namespaces for methods and fields. That is, you are able to declare a field AND a method whose type is 'doubleString'. So, if you start treating fields in a more method-y way, the namespace issue might pop up, and ambiguities might ensue. > > But wouldn?t that just be another layer of name shadowing like we already have on fields? I think it?s all about precedence of field over method or method over field. Do I miss something here (I probably do :-))? > -------------- next part -------------- An HTML attachment was scrubbed... URL: From cushon at google.com Thu Mar 23 19:08:38 2017 From: cushon at google.com (Liam Miller-Cushon) Date: Thu, 23 Mar 2017 12:08:38 -0700 Subject: Elements#getTypeElement and completion failures (JDK-8177436) Message-ID: I have a question about Elements#getTypeElement and CompletionFailures related to JDK-8177436. The summary of the bug is that getTypeElement catches completion failures and returns null for symbols that cannot be found, and javac relies on completion failures to detect missing symbols. So if a plugin or annotation processor calls getTypeElement before javac completes the symbol, javac fails to report an error and gets into a bad state. One possible fix would be to avoid relying on completion failures, and always check for errors before using symbols. This seems difficult to do exhaustively, and it requires plugins and annotation processors to also get it right. Another option would be to avoid caching the result of Symbol#complete for missing symbols, and rethrow the original completion failure. Is that worth considering? I attached a patch that illustrates the idea. It avoids the crash in JDK-8177436. -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: 8177436.patch Type: text/x-patch Size: 3374 bytes Desc: not available URL: From cushon at google.com Thu Mar 23 23:35:33 2017 From: cushon at google.com (Liam Miller-Cushon) Date: Thu, 23 Mar 2017 16:35:33 -0700 Subject: RFR 8177486: incorrect handling of mandated parameter names in MethodParameters attributes Message-ID: Hello, Please review this fix for JDK-8177486, which is a class reading bug that affects MethodParameters attributes with mandated parameters. Bug: https://bugs.openjdk.java.net/browse/JDK-8177486 Webrev: http://cr.openjdk.java.net/~cushon/8177486/webrev.00/ -------------- next part -------------- An HTML attachment was scrubbed... URL: From huaming.li at oracle.com Fri Mar 24 09:21:02 2017 From: huaming.li at oracle.com (Hamlin Li) Date: Fri, 24 Mar 2017 17:21:02 +0800 Subject: how to tell 2 methods are override-equivalent In-Reply-To: References: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> <58D1CA44.8000503@oracle.com> <7880d229-f32f-d2e0-34fd-da3b8ab34748@oracle.com> Message-ID: <8b15e258-aa8b-7119-a593-5832aa1bef6c@oracle.com> On 2017/3/22 22:01, Vicente Romero wrote: > Hi Hamlin > > On 03/22/2017 04:57 AM, Hamlin Li wrote: >> >> On 2017/3/22 8:50, Jonathan Gibbons wrote: >>> Hamlin, >>> >>> Note that while it is relative easy to convert a string containing a >>> type name (such as "java.net.URL") to an Element and/or TypeMirror, >>> in general it will not be possible to convert a string like >>> "getContent(java.lang.Class[])" to a Element or TypeMirror, because >>> the string as written does not contain sufficient information. >>> >>> Even if you did provide more info, you would still have to be >>> careful to evaluate the string in the same compilation context as >>> that to which you are comparing it, for the comparison to have any >>> chance of succeeding. >> Hi Jon, >> >> Thank you for explanation. >>> Given your other message mentioning a doclet, you are effectively >>> asking to be able to compile fragments of code (i.e. strings) in the >>> context of your doclet, and that is not possible with the existing >>> public API. >> Although it's bad news to me, it saves my time from continuing work >> in this direction. :-) >> I will try to find some workaround solve the issue. > > If you have access to the method's descriptor, I believe that you > could use it to convert from the method descriptor to the types you > need for your comparison, please let me know if you want to explore > that option, Hi Vicente, I'd like to try your option. But sorry, I'm a little bit confused, do you mean if I have a string representing the method's descriptor then the method descriptor can be converted into a valid ExecutableElement instance which can be used to compare with another one by Elements.overrides(ExecutableElement, ExecutableElement, TypeElement)? Thank you -Hamlin > > Vicente > >> >> Thank you >> -Hamlin >>> -- Jon >>> >>> On 03/21/2017 02:28 PM, Jonathan Gibbons wrote: >>>> >>>> Hamlin, >>>> >>>> Use Element.asType() to move from the Element world to the >>>> TypeMirror world. >>>> http://download.java.net/java/jdk9/docs/api/javax/lang/model/element/Element.html#asType-- >>>> >>>> Use Types.asElement(TypeMirror) to go in the reverse direction, >>>> from a TypeMirror to an Element. >>>> http://download.java.net/java/jdk9/docs/api/javax/lang/model/util/Types.html#asElement-javax.lang.model.type.TypeMirror- >>>> but note the reverse direction is lossy and may throw exceptions: >>>> e.g. for type "int", there is no direct element equivalent; >>>> for type List, the element will be the declaration List >>>> >>>> -- Jon >>>> >>>> On 3/16/17 8:15 PM, Hamlin Li wrote: >>>>> >>>>> Hi, >>>>> >>>>> ( I'm not sure if this is the right alias to ask the question, >>>>> please help forward if necessary. ) >>>>> >>>>> I have a question about telling whether one method is subsignature >>>>> of another one. My situation is, >>>>> >>>>> 1. there is a TypeElement *t1 *which represents java.net.URL, and >>>>> a ExecutableElement *m1* which represents >>>>> getContent(java.lang.Class**[]), >>>>> >>>>> 2. there is a String *t2* which is "java.net.URL", and another >>>>> String *m2 *which is "getContent(java.lang.Class[])". >>>>> >>>>> The difference between m1 and m2 is that, m1 is an instance of >>>>> ExecutableElement, m2 is an instance of String; there is a >>>>> wildcard type argument in m1. >>>>> >>>>> >>>>> Is there a way to tell whether m1 and m2 are override-equivalent, >>>>> m2 is subsignature of m1? >>>>> >>>>> I suppose I should use >>>>> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >>>>> ExecutableType m2), but I don't know how can I convert >>>>> ExecutableElement *m1* and String *m2* to**ExecutableType. >>>>> >>>>> Or I'm in wrong direction? >>>>> >>>>> >>>>> Thank you >>>>> >>>>> -Hamlin >>>>> >>>> >>> >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From vicente.romero at oracle.com Fri Mar 24 13:08:01 2017 From: vicente.romero at oracle.com (Vicente Romero) Date: Fri, 24 Mar 2017 09:08:01 -0400 Subject: how to tell 2 methods are override-equivalent In-Reply-To: <8b15e258-aa8b-7119-a593-5832aa1bef6c@oracle.com> References: <81d8eee0-93ff-2c26-449a-e863ddacbf7c@oracle.com> <58D1CA44.8000503@oracle.com> <7880d229-f32f-d2e0-34fd-da3b8ab34748@oracle.com> <8b15e258-aa8b-7119-a593-5832aa1bef6c@oracle.com> Message-ID: On 03/24/2017 05:21 AM, Hamlin Li wrote: > > > > On 2017/3/22 22:01, Vicente Romero wrote: >> Hi Hamlin >> >> On 03/22/2017 04:57 AM, Hamlin Li wrote: >>> >>> On 2017/3/22 8:50, Jonathan Gibbons wrote: >>>> Hamlin, >>>> >>>> Note that while it is relative easy to convert a string containing >>>> a type name (such as "java.net.URL") to an Element and/or >>>> TypeMirror, in general it will not be possible to convert a string >>>> like "getContent(java.lang.Class[])" to a Element or TypeMirror, >>>> because the string as written does not contain sufficient information. >>>> >>>> Even if you did provide more info, you would still have to be >>>> careful to evaluate the string in the same compilation context as >>>> that to which you are comparing it, for the comparison to have any >>>> chance of succeeding. >>> Hi Jon, >>> >>> Thank you for explanation. >>>> Given your other message mentioning a doclet, you are effectively >>>> asking to be able to compile fragments of code (i.e. strings) in >>>> the context of your doclet, and that is not possible with the >>>> existing public API. >>> Although it's bad news to me, it saves my time from continuing work >>> in this direction. :-) >>> I will try to find some workaround solve the issue. >> >> If you have access to the method's descriptor, I believe that you >> could use it to convert from the method descriptor to the types you >> need for your comparison, please let me know if you want to explore >> that option, > Hi Vicente, > > I'd like to try your option. But sorry, I'm a little bit confused, do > you mean if I have a string representing the method's descriptor then > the method descriptor can be converted into a valid ExecutableElement > instance which can be used to compare with another one by > Elements.overrides(ExecutableElement, ExecutableElement, TypeElement)? correct that's what I meant, > > Thank you > -Hamlin Vicente >> >> Vicente >> >>> >>> Thank you >>> -Hamlin >>>> -- Jon >>>> >>>> On 03/21/2017 02:28 PM, Jonathan Gibbons wrote: >>>>> >>>>> Hamlin, >>>>> >>>>> Use Element.asType() to move from the Element world to the >>>>> TypeMirror world. >>>>> http://download.java.net/java/jdk9/docs/api/javax/lang/model/element/Element.html#asType-- >>>>> >>>>> Use Types.asElement(TypeMirror) to go in the reverse direction, >>>>> from a TypeMirror to an Element. >>>>> http://download.java.net/java/jdk9/docs/api/javax/lang/model/util/Types.html#asElement-javax.lang.model.type.TypeMirror- >>>>> but note the reverse direction is lossy and may throw exceptions: >>>>> e.g. for type "int", there is no direct element equivalent; >>>>> for type List, the element will be the declaration List >>>>> >>>>> -- Jon >>>>> >>>>> On 3/16/17 8:15 PM, Hamlin Li wrote: >>>>>> >>>>>> Hi, >>>>>> >>>>>> ( I'm not sure if this is the right alias to ask the question, >>>>>> please help forward if necessary. ) >>>>>> >>>>>> I have a question about telling whether one method is >>>>>> subsignature of another one. My situation is, >>>>>> >>>>>> 1. there is a TypeElement *t1 *which represents java.net.URL, and >>>>>> a ExecutableElement *m1* which represents >>>>>> getContent(java.lang.Class**[]), >>>>>> >>>>>> 2. there is a String *t2* which is "java.net.URL", and another >>>>>> String *m2 *which is "getContent(java.lang.Class[])". >>>>>> >>>>>> The difference between m1 and m2 is that, m1 is an instance of >>>>>> ExecutableElement, m2 is an instance of String; there is a >>>>>> wildcard type argument in m1. >>>>>> >>>>>> >>>>>> Is there a way to tell whether m1 and m2 are override-equivalent, >>>>>> m2 is subsignature of m1? >>>>>> >>>>>> I suppose I should use >>>>>> javax.lang.model.util.Types.isSubsignature(ExecutableType m1, >>>>>> ExecutableType m2), but I don't know how can I convert >>>>>> ExecutableElement *m1* and String *m2* to**ExecutableType. >>>>>> >>>>>> Or I'm in wrong direction? >>>>>> >>>>>> >>>>>> Thank you >>>>>> >>>>>> -Hamlin >>>>>> >>>>> >>>> >>> >> > -------------- next part -------------- An HTML attachment was scrubbed... URL: From bsrbnd at gmail.com Fri Mar 24 15:56:18 2017 From: bsrbnd at gmail.com (B. Blaser) Date: Fri, 24 Mar 2017 16:56:18 +0100 Subject: question about JDK-8063054 (incorrect raw type warnings for method references) In-Reply-To: <9ad253e7-30bc-f574-8f77-25ca406e5bf6@oracle.com> References: <532edc20-8715-4b17-15a0-36b99f23bed9@oracle.com> <9ad253e7-30bc-f574-8f77-25ca406e5bf6@oracle.com> Message-ID: Hi Maurizio, On 23 March 2017 at 12:58, Maurizio Cimadamore wrote: > Hi Bernard, > > [...] > > I think the lines in bold are the ones we need to pay attention to; in other > words, if the receiver type is raw and the type of the first search is > identical to the type of the second search, then it means no inference > occurred. I think something like this could easily be achieved w/o any > visitors, with something like this: > > if (that.getMode() == ReferenceMode.INVOKE && > TreeInfo.isStaticSelector(that.expr, names) && > that.kind.isUnbound() && > types.isSameTypes(lookupHelper.site, that.expr.type) > { > chk.checkRaw(that.expr, localEnv); > } > > I did some quick tests and this simple patch seems to remove the undesired > warnings in the examples we have seen so far, but retains them where they > are truly deserved. What do you think? > > Maurizio Fine, nice solution... I would simply rewrite it as follows ( lookupHelper.site.isRaw() ): if (that.getMode() == ReferenceMode.INVOKE && TreeInfo.isStaticSelector(that.expr, names) && that.kind.isUnbound() && lookupHelper.site.isRaw()) { chk.checkRaw(that.expr, localEnv); } This would avoid some redundant checks if "ReferenceType" isn't raw (I think), for example: class Test10 { interface Consumer { void accept(T arg); } interface Parent

{ void foo(); } interface Child extends Parent {} static void m(T arg, Consumer f) {} public void test(Child c) { m(c, Parent::foo); } } Here, "types.isSameType(lookupHelper.site, that.expr.type)" would verify if "Parent == Parent" and then "chk.checkRaw()" would check if "Parent" is raw... But, at first sight, this looks good. I'll try to do some more testing... What do you think of this small rewriting? Bernard From maurizio.cimadamore at oracle.com Fri Mar 24 16:26:02 2017 From: maurizio.cimadamore at oracle.com (Maurizio Cimadamore) Date: Fri, 24 Mar 2017 16:26:02 +0000 Subject: question about JDK-8063054 (incorrect raw type warnings for method references) In-Reply-To: References: <532edc20-8715-4b17-15a0-36b99f23bed9@oracle.com> <9ad253e7-30bc-f574-8f77-25ca406e5bf6@oracle.com> Message-ID: On 24/03/17 15:56, B. Blaser wrote: > Hi Maurizio, > > On 23 March 2017 at 12:58, Maurizio Cimadamore > wrote: >> Hi Bernard, >> >> [...] >> >> I think the lines in bold are the ones we need to pay attention to; in other >> words, if the receiver type is raw and the type of the first search is >> identical to the type of the second search, then it means no inference >> occurred. I think something like this could easily be achieved w/o any >> visitors, with something like this: >> >> if (that.getMode() == ReferenceMode.INVOKE && >> TreeInfo.isStaticSelector(that.expr, names) && >> that.kind.isUnbound() && >> types.isSameTypes(lookupHelper.site, that.expr.type) >> { >> chk.checkRaw(that.expr, localEnv); >> } >> >> I did some quick tests and this simple patch seems to remove the undesired >> warnings in the examples we have seen so far, but retains them where they >> are truly deserved. What do you think? >> >> Maurizio > Fine, nice solution... I would simply rewrite it as follows ( > lookupHelper.site.isRaw() ): > > if (that.getMode() == ReferenceMode.INVOKE && > TreeInfo.isStaticSelector(that.expr, names) && > that.kind.isUnbound() && > lookupHelper.site.isRaw()) { > chk.checkRaw(that.expr, localEnv); > } > > This would avoid some redundant checks if "ReferenceType" isn't raw (I > think), for example: > > class Test10 { > interface Consumer { void accept(T arg); } > interface Parent

{ void foo(); } > interface Child extends Parent {} > static void m(T arg, Consumer f) {} > public void test(Child c) { m(c, Parent::foo); } > } > > Here, "types.isSameType(lookupHelper.site, that.expr.type)" would > verify if "Parent == Parent" and then "chk.checkRaw()" > would check if "Parent" is raw... > > But, at first sight, this looks good. I'll try to do some more testing... > > What do you think of this small rewriting? Yeah - I think that could work too (not that I'm too worried about performances here - we're outside overload resolution at this stage). Maurizio > > Bernard From jonathan.gibbons at oracle.com Tue Mar 28 01:00:53 2017 From: jonathan.gibbons at oracle.com (Jonathan Gibbons) Date: Mon, 27 Mar 2017 18:00:53 -0700 Subject: JD 9 RFR: JDK-8177311: Denied access when named module accesses unreferences package from the unnamed module In-Reply-To: <58D0F788.80403@oracle.com> References: <58D0F788.80403@oracle.com> Message-ID: <58D9B5C5.7050306@oracle.com> Looks good to me. -- Jon On 03/21/2017 02:51 AM, Jan Lahoda wrote: > Hi, > > I'd like to ask for a review for: > Bug: https://bugs.openjdk.java.net/browse/JDK-8177311 > http://mail.openjdk.java.net/pipermail/jdk9-dev/2017-March/005672.html > > Webrev: http://cr.openjdk.java.net/~jlahoda/8177311/webrev.00/ > > The problem is this: in Resolve.isAccessible when checks if a module > can access types from other modules does: > currModule.visiblePackages.get(p.fullname) == p > > But if "p" is from an unnamed module, then it may or may not be in the > visiblePackages (depending on whether Symtab.lookupPackage was called > on the given package in the context of currModule), as unnamed module > packages are computed lazily. So this check may fail incorrectly. > > The proposal here is to add one more check for the dependency on the > unnamed module. > > How does this look? > > Thanks, > Jan From stephan.herrmann at berlin.de Sat Mar 4 13:12:23 2017 From: stephan.herrmann at berlin.de (Stephan Herrmann) Date: Sat, 04 Mar 2017 13:12:23 -0000 Subject: spec clarification: wildcard array element signature Message-ID: <3b7b4c3b-24fa-653c-bee2-e59b257ccf0a@berlin.de> If I understand correctly, the situation discussed here should be avoided by future changes in JLS, right? Until then, compilers are free to generate anything they want when they encounter such situations? Let me add that the original discussion [1] regarding ecj started with a slightly different example, where inference computes the type of a lambda parameter to a capture, and then creating an LVTT was creating trouble: javac would simply not generate such an entry, although it seems to be recommended to generate one, whereas ecj generates an LVTT with inevitably unspec'ed encoding. Will that situation, too, be avoided by future JLS changes? I imagine that not only "captures" are concerned, but likely also those "fresh type variables" that are introduced in JSL 18.4. What happens when Java gets type inference for local variables? Can we be sure that none of this will have to show up in class files? Will there, e.g., be rules about when generating LVTT entries should be avoided? Or is there perhaps more to it? thanks, Stephan [1] http://stackoverflow.com/questions/37268391/strange-entry-in-localvariabletypetable-when-compiling-with-eclipse-compile > On 2/7/2017 10:54 AM, Dan Smith wrote: >> Yes, I object! "?[]" is not a type. It's meaningless. >> >> It is always wrong to perform substitutions that replace type >> variables with wildcards. javac has a history of doing so, and those >> cases need to be fixed. The compiler's internal representation of >> wildcards should not even allow such an attempt at substitution to >> compile (e.g., a class Wildcard should not extend a class Type), but >> alas, we have a lot of legacy violating this rule. > > Am I right to say that this is what javac is doing in the recent snipper > from Stephan Herrmann? :- > > --- > public class Bug494198 { class Inner {...} } > > Bug494198 outer = ... > ... outer.new Inner() {...} > > final class Bug494198$1 > extends ***Bug494198<>***.Inner > --- > >> Liam's program raises issues related to two existing spec bugs: >> JDK-8030746: 4.10: Define subtyping for inner classes of >> parameterized types JDK-8016196: Inference: define supertype >> parameterization for wildcard-parameterized types >> >> These are part of our type system cleanup effort; when addressed, >> we'll have a clear answer for how to interpret "B.I" and, thus, >> how to record it in bytecode. (Preview: the answer is probably "A> extends Object[]>.I".) >> >> Suggest closing JDK-8172742 as "Not an Issue"?the JVMS grammar is >> fine. > > OK -- please close it with an explanation for Liam and Stephan's benefit. > > Alex From li.jiang at oracle.com Tue Mar 14 03:58:52 2017 From: li.jiang at oracle.com (Leo Jiang) Date: Tue, 14 Mar 2017 03:58:52 -0000 Subject: RFR 9 (xs): 8171395 (jdeprscan) add comments to L10N message file In-Reply-To: <402f0b3e-32bf-bfba-34d4-5f4b0e2a75ae@oracle.com> References: <402f0b3e-32bf-bfba-34d4-5f4b0e2a75ae@oracle.com> Message-ID: <6b0b46f4-0ad4-45ae-a6bd-e78c2d160d29@oracle.com> Looks very good, definitely help translators to do their works better. Thank you! -Leo On 03/14/2017 11:35 AM, Stuart Marks wrote: > Hi Leo, all, > > Please review this small changeset to the jdeprscan resource properties file. It simply adds some comments to explain > the various format elements, to help out with translation. Patch appended below. > > Thanks, > > s'marks > > > # HG changeset patch > # User smarks > # Date 1489457980 25200 > # Mon Mar 13 19:19:40 2017 -0700 > # Node ID 9a523636445575e5b174ed78e8f0779b4cae8fd2 > # Parent 6b51827c339c267f484248c9bd10e6bc9fe00703 > 8171395: (jdeprscan) add comments to L10N message file > Reviewed-by: XXX > > diff -r 6b51827c339c -r 9a5236364455 src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/resources/jdeprscan.properties > --- a/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/resources/jdeprscan.properties Fri Mar 10 09:52:49 2017 -0800 > +++ b/src/jdk.jdeps/share/classes/com/sun/tools/jdeprscan/resources/jdeprscan.properties Mon Mar 13 19:19:40 2017 -0700 > @@ -75,24 +75,52 @@ > > scan.process.class=Processing class {0}... > > +# The "removal tag": empty for normal deprecations, > +# nonempty for removal deprecations; do not translate. > scan.dep.normal= > scan.dep.removal=(forRemoval=true) > > scan.err.exception=error: unexpected exception {0} > scan.err.noclass=error: cannot find class {0} > scan.err.nofile=error: cannot find file {0} > + > +# 0: class name, 1: method name, 2: parameter and return types > scan.err.nomethod=error: cannot resolve Methodref {0}.{1}:{2} > > scan.head.jar=Jar file {0}: > scan.head.dir=Directory {0}: > > +# In all of the messages below, 0 and 1 are as follows: > +# 0: type kind (class, interface, enum, or annotation type) > +# 1: type name > +# The last element is generally a "removal tag"; see above. > + > +# 2: class name, 3: removal tag > scan.out.extends={0} {1} extends deprecated class {2} {3} > + > +# 2: interface name, 3: removal tag > scan.out.implements={0} {1} implements deprecated interface {2} {3} > + > +# 2: class name, 3: removal tag > scan.out.usesclass={0} {1} uses deprecated class {2} {3} > + > +# 2: class name, 3: method name, 4: method parameter and return types, 5: removal tag > scan.out.usesmethod={0} {1} uses deprecated method {2}::{3}{4} {5} > + > +# 2: class name, 3: method name, 4: method parameter and return types, 5: removal tag > scan.out.usesintfmethod={0} {1} uses deprecated method {2}::{3}{4} {5} > + > +# 2: class name, 3: field name, 4: removal tag > scan.out.usesfield={0} {1} uses deprecated field {2}::{3} {4} > + > +# 2: field name, 3: type name, 4: removal tag > scan.out.hasfield={0} {1} has field named {2} of deprecated type {3} {4} > + > +# 2: method name, 3: parameter type, 4: removal tag > scan.out.methodparmtype={0} {1} has method named {2} having deprecated parameter type {3} {4} > + > +# 2: method name, 3: return type, 4: removal tag > scan.out.methodrettype={0} {1} has method named {2} having deprecated return type {3} {4} > + > +# 2: class name, 3: method name, 4: method parameter and return types, 5: removal tag > scan.out.methodoverride={0} {1} overrides deprecated method {2}::{3}{4} {5} > From postolowicz at gmail.com Sat Mar 25 17:53:46 2017 From: postolowicz at gmail.com (_) Date: Sat, 25 Mar 2017 17:53:46 -0000 Subject: javac "cannot find symbol" bug (?) Message-ID: Hello, I discovered strange behavior of javac in my project: depending on order of source files passed it compiles successfully or fail. Could you take a look at sample reproducible case at https://bitbucket.org/postolowicz/javac-error ? Steps to reproduce: 1. Run `./gradlew build` This depending on your luck may success or fail at buildling system-test module. 2. Run `./compile-successful.sh` It should succeed. 3. Run `./compile-failing.sh` It should fail with message: system-test/src/main/java/postolowicz/systemtest/AbstractSystemTestWithoutDB.java:18: error: cannot find symbol protected class RunnerImpl extends ValidationRunner { ^ symbol: class ValidationRunner location: class AbstractSystemTestWithoutDB system-test/src/main/java/postolowicz/systemtest/AbstractSystemTestWithoutDB.java:13: error: cannot find symbol @Configuration ^ symbol: class Configuration location: class AbstractSystemTestWithoutDB system-test/src/main/java/postolowicz/systemtest/AbstractSystemTestWithoutDB.java:14: error: cannot find symbol @PropertySource(value = "", ignoreResourceNotFound = true) ^ symbol: class PropertySource location: class AbstractSystemTestWithoutDB system-test/src/main/java/postolowicz/systemtest/AbstractSystemTestWithoutDB.java:23: error: method does not override or implement a method from a supertype @Override ^ system-test/src/main/java/postolowicz/systemtest/AbstractSystemTestWithoutDB.java:28: error: method does not override or implement a method from a supertype @Override ^ 5 errors The only difference between these two scripts is order of source files. Is it a bug or I miss something? Occurs for javac -version javac 1.8.0_121 TIA, Radek Posto?owicz