# HG changeset patch # User chegar # Date 1512587827 0 # Node ID 1826a0130c591937263e7b3d6e947f88515b1af6 # Parent b1c1b4ef4be22516707191d5a7e647388320cbb4# Parent d8c634b016c628622c9abbdc6bf50509e5dedbec Merge diff -r b1c1b4ef4be2 -r 1826a0130c59 src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Lower.java --- a/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Lower.java Wed Dec 06 11:11:59 2017 -0800 +++ b/src/jdk.compiler/share/classes/com/sun/tools/javac/comp/Lower.java Wed Dec 06 19:17:07 2017 +0000 @@ -3236,12 +3236,10 @@ make.Ident(index)).setType(elemtype); JCVariableDecl loopvardef = (JCVariableDecl)make.VarDef(tree.var.mods, tree.var.name, - tree.var.vartype, null).setType(tree.var.type); + tree.var.vartype, loopvarinit).setType(tree.var.type); loopvardef.sym = tree.var.sym; - JCStatement loopVarAssign = make.Assignment(tree.var.sym, loopvarinit); - JCBlock body = make. - Block(0, List.of(loopVarAssign, tree.body)); + JCBlock body = make.Block(0, List.of(loopvardef, tree.body)); arraycachedef = translate(arraycachedef); result = translate(make. @@ -3251,12 +3249,7 @@ body)); patchTargets(body, tree, result); JCStatement nullAssignToArr = make.Assignment(arraycache, make.Literal(BOT, null).setType(syms.botType)); - JCStatement nullAssignToLoopVar = tree.var.type.isPrimitive() ? - null : - make.Assignment(tree.var.sym, make.Literal(BOT, null).setType(syms.botType)); - result = nullAssignToLoopVar == null ? - make.Block(0, List.of(arraycachedef, loopvardef, (JCStatement)result, nullAssignToArr)): - make.Block(0, List.of(arraycachedef, loopvardef, (JCStatement)result, nullAssignToArr, nullAssignToLoopVar)); + result = make.Block(0, List.of(arraycachedef, (JCStatement)result, nullAssignToArr)); } /** Patch up break and continue targets. */ private void patchTargets(JCTree body, final JCTree src, final JCTree dest) { @@ -3310,7 +3303,7 @@ types.erasure(types.asSuper(iterator.type.getReturnType(), syms.iteratorType.tsym)), currentMethodSym); - JCStatement init = make. + JCStatement init = make. VarDef(itvar, make.App(make.Select(tree.expr, iterator) .setType(types.erasure(iterator.type)))); @@ -3331,10 +3324,9 @@ JCVariableDecl indexDef = (JCVariableDecl)make.VarDef(tree.var.mods, tree.var.name, tree.var.vartype, - null).setType(tree.var.type); + vardefinit).setType(tree.var.type); indexDef.sym = tree.var.sym; - JCStatement loopVarAssign = make.Assignment(tree.var.sym, vardefinit); - JCBlock body = make.Block(0, List.of(loopVarAssign, tree.body)); + JCBlock body = make.Block(0, List.of(indexDef, tree.body)); body.endpos = TreeInfo.endPos(tree.body); init = translate(init); result = translate(make. @@ -3344,12 +3336,7 @@ body)); patchTargets(body, tree, result); JCStatement nullAssignToIterator = make.Assignment(itvar, make.Literal(BOT, null).setType(syms.botType)); - JCStatement nullAssignToLoopVar = tree.var.type.isPrimitive() ? - null : - make.Assignment(tree.var.sym, make.Literal(BOT, null).setType(syms.botType)); - result = nullAssignToLoopVar == null ? - make.Block(0, List.of(init, indexDef, (JCStatement)result, nullAssignToIterator)): - make.Block(0, List.of(init, indexDef, (JCStatement)result, nullAssignToIterator, nullAssignToLoopVar)); + result = make.Block(0, List.of(init, (JCStatement)result, nullAssignToIterator)); } public void visitVarDef(JCVariableDecl tree) { diff -r b1c1b4ef4be2 -r 1826a0130c59 test/langtools/tools/javac/T8192885/AddGotoAfterForLoopToLNTTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/test/langtools/tools/javac/T8192885/AddGotoAfterForLoopToLNTTest.java Wed Dec 06 19:17:07 2017 +0000 @@ -0,0 +1,116 @@ +/* + * Copyright (c) 2017, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ + +/* + * @test + * @bug 8192885 + * @summary Compiler in JDK 10-ea+33 misses to include entry in LineNumberTable for goto instruction of foreach loop + * @library /tools/lib + * @modules jdk.jdeps/com.sun.tools.classfile + * jdk.compiler/com.sun.tools.javac.api + * jdk.compiler/com.sun.tools.javac.main + * jdk.compiler/com.sun.tools.javac.util + * jdk.jdeps/com.sun.tools.javap + * @build toolbox.ToolBox toolbox.JavacTask + * @run main AddGotoAfterForLoopToLNTTest + */ + +import java.io.File; +import java.nio.file.Paths; + +import com.sun.tools.classfile.ClassFile; +import com.sun.tools.classfile.Code_attribute; +import com.sun.tools.classfile.LineNumberTable_attribute; +import com.sun.tools.classfile.Method; +import com.sun.tools.javac.util.Assert; + +import toolbox.JavacTask; +import toolbox.ToolBox; + +public class AddGotoAfterForLoopToLNTTest { + + static final String testSource = + /* 01 */ "class GotoAtEnhancedForTest {\n" + + /* 02 */ " void lookForThisMethod() {\n" + + /* 03 */ " for (Object o : java.util.Collections.emptyList()) {\n" + + /* 04 */ " }\n" + + /* 05 */ " }\n" + + /* 06 */ "}"; + + static final int[][] expectedLNT = { + // {line-number, start-pc}, + {3, 0}, + {4, 25}, + {3, 28}, + {5, 30}, + }; + + static final String methodToLookFor = "lookForThisMethod"; + + public static void main(String[] args) throws Exception { + new AddGotoAfterForLoopToLNTTest().run(); + } + + ToolBox tb = new ToolBox(); + + void run() throws Exception { + compileTestClass(); + checkClassFile(new File(Paths.get(System.getProperty("user.dir"), + "GotoAtEnhancedForTest.class").toUri()), methodToLookFor); + } + + void compileTestClass() throws Exception { + new JavacTask(tb) + .sources(testSource) + .run(); + } + + void checkClassFile(final File cfile, String methodToFind) throws Exception { + ClassFile classFile = ClassFile.read(cfile); + boolean methodFound = false; + for (Method method : classFile.methods) { + if (method.getName(classFile.constant_pool).equals(methodToFind)) { + methodFound = true; + Code_attribute code = (Code_attribute) method.attributes.get("Code"); + LineNumberTable_attribute lnt = + (LineNumberTable_attribute) code.attributes.get("LineNumberTable"); + Assert.check(lnt.line_number_table_length == expectedLNT.length, + "The LineNumberTable found has a length different to the expected one"); + int i = 0; + for (LineNumberTable_attribute.Entry entry: lnt.line_number_table) { + Assert.check(entry.line_number == expectedLNT[i][0] && + entry.start_pc == expectedLNT[i][1], + "LNT entry at pos " + i + " differ from expected." + + "Found " + entry.line_number + ":" + entry.start_pc + + ". Expected " + expectedLNT[i][0] + ":" + expectedLNT[i][1]); + i++; + } + } + } + Assert.check(methodFound, "The seek method was not found"); + } + + void error(String msg) { + throw new AssertionError(msg); + } +} diff -r b1c1b4ef4be2 -r 1826a0130c59 test/langtools/tools/javac/flow/tests/TestCaseForEach.java --- a/test/langtools/tools/javac/flow/tests/TestCaseForEach.java Wed Dec 06 11:11:59 2017 -0800 +++ b/test/langtools/tools/javac/flow/tests/TestCaseForEach.java Wed Dec 06 19:17:07 2017 +0000 @@ -3,7 +3,7 @@ public class TestCaseForEach { @AliveRange(varName="o", bytecodeStart=25, bytecodeLength=11) - @AliveRange(varName="o", bytecodeStart=44, bytecodeLength=1) + @AliveRange(varName="o", bytecodeStart=41, bytecodeLength=1) void m(String[] args) { Object o; for (String s : args) {