Version 1.5.55
Cherry-pick: Test for incorrect removal of abstract visibility bridge
CL: https://r8-review.googlesource.com/c/r8/+/40152
Cherry-pick: Consider package name when comparing protected
accessflags
CL: https://r8-review.googlesource.com/c/r8/+/40154
Bug: 136195382
Change-Id: I1f365864387c3da1ba323c07c4991a5289d66594
diff --git a/src/main/java/com/android/tools/r8/Version.java b/src/main/java/com/android/tools/r8/Version.java
index 8038d4e..872f8cd 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.5.54";
+ public static final String LABEL = "1.5.55";
private Version() {
}
diff --git a/src/main/java/com/android/tools/r8/graph/AccessFlags.java b/src/main/java/com/android/tools/r8/graph/AccessFlags.java
index 9716eea..a0322a1 100644
--- a/src/main/java/com/android/tools/r8/graph/AccessFlags.java
+++ b/src/main/java/com/android/tools/r8/graph/AccessFlags.java
@@ -83,8 +83,18 @@
return originalFlags | modifiedFlags;
}
- public boolean isMoreVisibleThan(AccessFlags other) {
- return visibilityOrdinal() > other.visibilityOrdinal();
+ public boolean isMoreVisibleThan(
+ AccessFlags other, String packageNameThis, String packageNameOther) {
+ int visibilityOrdinal = visibilityOrdinal();
+ if (visibilityOrdinal > other.visibilityOrdinal()) {
+ return true;
+ }
+ if (visibilityOrdinal == other.visibilityOrdinal()
+ && isVisibilityDependingOnPackage()
+ && !packageNameThis.equals(packageNameOther)) {
+ return true;
+ }
+ return false;
}
public boolean isAtLeastAsVisibleAs(AccessFlags other) {
@@ -106,6 +116,10 @@
return 1;
}
+ public boolean isVisibilityDependingOnPackage() {
+ return visibilityOrdinal() == 1 || visibilityOrdinal() == 2;
+ }
+
public boolean isPublic() {
return isSet(Constants.ACC_PUBLIC);
}
diff --git a/src/main/java/com/android/tools/r8/shaking/ScopedDexMethodSet.java b/src/main/java/com/android/tools/r8/shaking/ScopedDexMethodSet.java
index 3587cf4..6d76acd 100644
--- a/src/main/java/com/android/tools/r8/shaking/ScopedDexMethodSet.java
+++ b/src/main/java/com/android/tools/r8/shaking/ScopedDexMethodSet.java
@@ -51,7 +51,11 @@
public boolean addMethodIfMoreVisible(DexEncodedMethod method) {
Wrapper<DexMethod> wrapped = METHOD_EQUIVALENCE.wrap(method.method);
DexEncodedMethod existing = lookup(wrapped);
- if (existing == null || method.accessFlags.isMoreVisibleThan(existing.accessFlags)) {
+ if (existing == null
+ || method.accessFlags.isMoreVisibleThan(
+ existing.accessFlags,
+ method.method.holder.getPackageName(),
+ existing.method.holder.getPackageName())) {
items.put(wrapped, method);
return true;
}
diff --git a/src/main/java/com/android/tools/r8/shaking/StaticClassMerger.java b/src/main/java/com/android/tools/r8/shaking/StaticClassMerger.java
index 8b4bedb..cbe3961 100644
--- a/src/main/java/com/android/tools/r8/shaking/StaticClassMerger.java
+++ b/src/main/java/com/android/tools/r8/shaking/StaticClassMerger.java
@@ -360,7 +360,10 @@
Representative packageRepresentative = representatives.get(key);
if (packageRepresentative != null) {
if (isValidRepresentative(clazz)
- && clazz.accessFlags.isMoreVisibleThan(packageRepresentative.clazz.accessFlags)) {
+ && clazz.accessFlags.isMoreVisibleThan(
+ packageRepresentative.clazz.accessFlags,
+ clazz.type.getPackageName(),
+ packageRepresentative.clazz.type.getPackageName())) {
// Use `clazz` as a representative for this package instead.
Representative newRepresentative = getOrCreateRepresentative(key, clazz);
newRepresentative.include(packageRepresentative.clazz);
@@ -482,6 +485,7 @@
targetClass.type.toSourceString());
}
+ // TODO(b/136457753) This check is a bit weird for protected, since it is moving access.
assert targetClass.accessFlags.isAtLeastAsVisibleAs(sourceClass.accessFlags);
assert sourceClass.instanceFields().size() == 0;
assert targetClass.instanceFields().size() == 0;
diff --git a/src/test/java/com/android/tools/r8/shaking/b136195382/AbstractBridgeInheritTest.java b/src/test/java/com/android/tools/r8/shaking/b136195382/AbstractBridgeInheritTest.java
new file mode 100644
index 0000000..2514381
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/shaking/b136195382/AbstractBridgeInheritTest.java
@@ -0,0 +1,49 @@
+// 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.shaking.b136195382;
+
+import com.android.tools.r8.CompilationFailedException;
+import com.android.tools.r8.TestBase;
+import com.android.tools.r8.TestParameters;
+import com.android.tools.r8.TestParametersCollection;
+import com.android.tools.r8.shaking.b136195382.package1.Factory;
+import com.android.tools.r8.shaking.b136195382.package1.Service;
+import com.android.tools.r8.shaking.b136195382.package2.Main;
+import com.android.tools.r8.shaking.b136195382.package2.SubFactory;
+import com.android.tools.r8.shaking.b136195382.package2.SubService;
+import java.io.IOException;
+import java.util.concurrent.ExecutionException;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.Parameterized;
+import org.junit.runners.Parameterized.Parameters;
+
+@RunWith(Parameterized.class)
+public class AbstractBridgeInheritTest extends TestBase {
+
+ private final TestParameters parameters;
+
+ @Parameters(name = "{0}")
+ public static TestParametersCollection data() {
+ return getTestParameters().withAllRuntimes().build();
+ }
+
+ public AbstractBridgeInheritTest(TestParameters parameters) {
+ this.parameters = parameters;
+ }
+
+ @Test
+ public void testRemovingBridge()
+ throws ExecutionException, CompilationFailedException, IOException {
+ testForR8(parameters.getBackend())
+ .addProgramClasses(
+ Service.class, Factory.class, SubService.class, SubFactory.class, Main.class)
+ .addKeepMainRule(Main.class)
+ .enableInliningAnnotations()
+ .run(parameters.getRuntime(), Main.class)
+ .assertSuccessWithOutputLines("Hello World!")
+ .inspector();
+ }
+}
diff --git a/src/test/java/com/android/tools/r8/shaking/b136195382/package1/Factory.java b/src/test/java/com/android/tools/r8/shaking/b136195382/package1/Factory.java
new file mode 100644
index 0000000..90c9753
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/shaking/b136195382/package1/Factory.java
@@ -0,0 +1,15 @@
+// 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.shaking.b136195382.package1;
+
+import com.android.tools.r8.NeverInline;
+
+public class Factory {
+
+ @NeverInline
+ public static String create(Service service) {
+ return service.baseUrl();
+ }
+}
diff --git a/src/test/java/com/android/tools/r8/shaking/b136195382/package1/Service.java b/src/test/java/com/android/tools/r8/shaking/b136195382/package1/Service.java
new file mode 100644
index 0000000..3099321
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/shaking/b136195382/package1/Service.java
@@ -0,0 +1,10 @@
+// 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.shaking.b136195382.package1;
+
+public abstract class Service {
+
+ protected abstract String baseUrl();
+}
diff --git a/src/test/java/com/android/tools/r8/shaking/b136195382/package2/Main.java b/src/test/java/com/android/tools/r8/shaking/b136195382/package2/Main.java
new file mode 100644
index 0000000..be585a4
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/shaking/b136195382/package2/Main.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.shaking.b136195382.package2;
+
+import com.android.tools.r8.shaking.b136195382.package1.Factory;
+
+public class Main extends SubService {
+
+ @Override
+ protected String baseUrl() {
+ return "Hello World!";
+ }
+
+ public static void main(String[] args) {
+ if (args.length == 0) {
+ System.out.println(SubFactory.create(new Main()));
+ } else {
+ System.out.println(Factory.create(new Main()));
+ }
+ }
+}
diff --git a/src/test/java/com/android/tools/r8/shaking/b136195382/package2/SubFactory.java b/src/test/java/com/android/tools/r8/shaking/b136195382/package2/SubFactory.java
new file mode 100644
index 0000000..fbdeaa2
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/shaking/b136195382/package2/SubFactory.java
@@ -0,0 +1,15 @@
+// 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.shaking.b136195382.package2;
+
+import com.android.tools.r8.NeverInline;
+
+public class SubFactory {
+
+ @NeverInline
+ public static String create(SubService subService) {
+ return subService.baseUrl();
+ }
+}
diff --git a/src/test/java/com/android/tools/r8/shaking/b136195382/package2/SubService.java b/src/test/java/com/android/tools/r8/shaking/b136195382/package2/SubService.java
new file mode 100644
index 0000000..c6891ef
--- /dev/null
+++ b/src/test/java/com/android/tools/r8/shaking/b136195382/package2/SubService.java
@@ -0,0 +1,13 @@
+// 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.shaking.b136195382.package2;
+
+import com.android.tools.r8.shaking.b136195382.package1.Service;
+
+public abstract class SubService extends Service {
+
+ @Override
+ protected abstract String baseUrl();
+}