Version 1.4.81
Cherry pick: Consider trivial loops in workaround code.
CL: https://r8-review.googlesource.com/c/r8/+/36805
Bug: 129901036
Change-Id: I632846b91789f01b2d0c0d3ad10b40f8d28d9b96
diff --git a/src/main/java/com/android/tools/r8/Version.java b/src/main/java/com/android/tools/r8/Version.java
index 7d55141..eff22da 100644
--- a/src/main/java/com/android/tools/r8/Version.java
+++ b/src/main/java/com/android/tools/r8/Version.java
@@ -11,7 +11,7 @@
// This field is accessed from release scripts using simple pattern matching.
// Therefore, changing this field could break our release scripts.
- public static final String LABEL = "1.4.80";
+ public static final String LABEL = "1.4.81";
private Version() {
}
diff --git a/src/main/java/com/android/tools/r8/ir/optimize/CodeRewriter.java b/src/main/java/com/android/tools/r8/ir/optimize/CodeRewriter.java
index 3861c66..5075b99 100644
--- a/src/main/java/com/android/tools/r8/ir/optimize/CodeRewriter.java
+++ b/src/main/java/com/android/tools/r8/ir/optimize/CodeRewriter.java
@@ -3836,7 +3836,8 @@
// header. If we ever end up computing exact loop headers, use that here instead.
// The loop is conditional if it has at least two normal successors.
BasicBlock target = handler.endOfGotoChain();
- if (target.getPredecessors().size() > 2
+ if (target != null
+ && target.getPredecessors().size() > 2
&& target.getNormalPredecessors().size() > 1
&& target.getNormalSuccessors().size() > 1) {
Instruction fixit = new AlwaysMaterializingNop();
diff --git a/src/test/java/com/android/tools/r8/debuginfo/Regress129901036Test.java b/src/test/java/com/android/tools/r8/debuginfo/Regress129901036Test.java
new file mode 100644
index 0000000..294662c
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/debuginfo/Regress129901036Test.java
@@ -0,0 +1,35 @@
+// Copyright (c) 2019, the R8 project authors. Please see the AUTHORS file
+// for details. All rights reserved. Use of this source code is governed by a
+// BSD-style license that can be found in the LICENSE file.
+package com.android.tools.r8.debuginfo;
+
+import java.util.Arrays;
+import java.util.Iterator;
+
+// Copy of Regress111337896Test.java modified to hit the trivial loop issue.
+public class Regress129901036Test {
+
+ public static void regress129901036() {
+ Iterator it = Arrays.asList(new Object()).iterator();
+ while (it.hasNext()) { // Loop must be a conditional to hit the issue.
+ it.next();
+ try {
+ noThrow();
+ noThrow();
+ noThrow();
+ // Workaround failed to handle a trivial loop when searching for a possible loop header.
+ } catch (Exception e) { while (true); }
+ // The normal successor may differ from the exceptional one and still cause the issue.
+ it.hasNext();
+ }
+ }
+
+ public static void noThrow() throws Exception {
+ // Intentionally empty.
+ }
+
+ public static void main(String[] args) {
+ regress129901036();
+ System.out.print("aok");
+ }
+}
diff --git a/src/test/java/com/android/tools/r8/debuginfo/Regress129901036TestRunner.java b/src/test/java/com/android/tools/r8/debuginfo/Regress129901036TestRunner.java
new file mode 100644
index 0000000..a3eb9f8
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/debuginfo/Regress129901036TestRunner.java
@@ -0,0 +1,23 @@
+// Copyright (c) 2019, the R8 project authors. Please see the AUTHORS file
+// for details. All rights reserved. Use of this source code is governed by a
+// BSD-style license that can be found in the LICENSE file.
+package com.android.tools.r8.debuginfo;
+
+import com.android.tools.r8.CompilationMode;
+import com.android.tools.r8.TestBase;
+import com.android.tools.r8.ToolHelper;
+import com.android.tools.r8.utils.AndroidApiLevel;
+import org.junit.Test;
+
+public class Regress129901036TestRunner extends TestBase {
+
+ @Test
+ public void test() throws Exception {
+ testForD8()
+ .addProgramClasses(Regress129901036Test.class)
+ .setMode(CompilationMode.RELEASE)
+ .setMinApi(ToolHelper.getMinApiLevelForDexVmNoHigherThan(AndroidApiLevel.L_MR1))
+ .run(Regress129901036Test.class)
+ .assertSuccessWithOutput("aok");
+ }
+}