Trace keep xml as R8 root set when using optimized shrinking
Bug: b/326564914
Change-Id: Ieb844d34507603932d04ace6e4ad5fe3d525c2fd
diff --git a/src/main/java/com/android/tools/r8/shaking/Enqueuer.java b/src/main/java/com/android/tools/r8/shaking/Enqueuer.java
index 682b2df..8102003 100644
--- a/src/main/java/com/android/tools/r8/shaking/Enqueuer.java
+++ b/src/main/java/com/android/tools/r8/shaking/Enqueuer.java
@@ -3884,7 +3884,7 @@
private void traceManifests(Timing timing) {
if (options.isOptimizedResourceShrinking()) {
timing.begin("Trace AndroidManifest.xml files");
- appView.getResourceShrinkerState().traceManifests();
+ appView.getResourceShrinkerState().traceKeepXmlAndManifest();
timing.end();
}
}
diff --git a/src/resourceshrinker/java/com/android/build/shrinker/r8integration/R8ResourceShrinkerState.java b/src/resourceshrinker/java/com/android/build/shrinker/r8integration/R8ResourceShrinkerState.java
index 29a3399..e43c68e 100644
--- a/src/resourceshrinker/java/com/android/build/shrinker/r8integration/R8ResourceShrinkerState.java
+++ b/src/resourceshrinker/java/com/android/build/shrinker/r8integration/R8ResourceShrinkerState.java
@@ -93,12 +93,32 @@
}
}
- public void traceManifests() {
+ public void traceKeepXmlAndManifest() {
+ // We start by building the root set of all keep/discard rules to find those pinned resources
+ // before marking additional resources in the trace.
+ // We then explicitly trace those resources to transitively get the full set of reachable
+ // resources and code.
+ try {
+ updateModelWithKeepXmlReferences();
+ } catch (IOException e) {
+ throw errorHandler.apply(e);
+ }
+ // TODO(b/329584653): Update processToolsAttributes in AGP to return the kept resources and
+ // trace directly using this instead of iterating the full resource store below.
+ r8ResourceShrinkerModel.getResourceStore().processToolsAttributes();
+ traceLiveResources();
for (Supplier<InputStream> manifestProvider : manifestProviders) {
traceXml("AndroidManifest.xml", manifestProvider.get());
}
}
+ private void traceLiveResources() {
+ r8ResourceShrinkerModel.getResourceStore().getResources().stream()
+ .filter(Resource::isReachable)
+ .map(r -> r.value)
+ .forEach(this::trace);
+ }
+
public void setEnqueuerCallback(ClassReferenceCallback enqueuerCallback) {
assert this.enqueuerCallback == null;
this.enqueuerCallback = enqueuerCallback;
diff --git a/src/test/java/com/android/tools/r8/androidresources/KeepXmlTransitiveCodeReachabilityTest.java b/src/test/java/com/android/tools/r8/androidresources/KeepXmlTransitiveCodeReachabilityTest.java
index ee97c1c..da9fa3c 100644
--- a/src/test/java/com/android/tools/r8/androidresources/KeepXmlTransitiveCodeReachabilityTest.java
+++ b/src/test/java/com/android/tools/r8/androidresources/KeepXmlTransitiveCodeReachabilityTest.java
@@ -3,7 +3,7 @@
// BSD-style license that can be found in the LICENSE file.
package com.android.tools.r8.androidresources;
-import static com.android.tools.r8.utils.codeinspector.Matchers.isAbsent;
+import static com.android.tools.r8.utils.codeinspector.Matchers.isPresentAndNotRenamed;
import static org.hamcrest.MatcherAssert.assertThat;
import com.android.tools.r8.TestBase;
@@ -59,10 +59,10 @@
})
.inspect(
codeInspector -> {
- // TODO(b/326564914): Ensure that we handle code references from resources that are
- // kept with xml keep rules (i.e., Bar is present).
- assertThat(codeInspector.clazz(Bar.class), isAbsent());
- });
+ assertThat(codeInspector.clazz(Bar.class), isPresentAndNotRenamed());
+ })
+ .run(parameters.getRuntime(), TestClass.class)
+ .assertSuccessWithOutputLines("init");
}
public static class TestClass {