L8 Shrinking for Jdk11TimeTests

- ArrayTypes need to be handled correctly
  when R8 generates keep rules for L8.

Bug: 142377475
Change-Id: I055f538b742626e7d1e48840c8ad39b3adbe4b32
diff --git a/src/main/java/com/android/tools/r8/dex/CodeToKeep.java b/src/main/java/com/android/tools/r8/dex/CodeToKeep.java
index 6e44735..2e87405 100644
--- a/src/main/java/com/android/tools/r8/dex/CodeToKeep.java
+++ b/src/main/java/com/android/tools/r8/dex/CodeToKeep.java
@@ -45,11 +45,13 @@
     private final Set<DexType> emulatedInterfaces = Sets.newIdentityHashSet();
     private final Map<DexType, Pair<Set<DexField>, Set<DexMethod>>> toKeep =
         new ConcurrentHashMap<>();
+    private final InternalOptions options;
 
     public DesugaredLibraryCodeToKeep(NamingLens namingLens, InternalOptions options) {
       emulatedInterfaces.addAll(
           options.desugaredLibraryConfiguration.getEmulateLibraryInterface().values());
       this.namingLens = namingLens;
+      this.options = options;
     }
 
     private boolean shouldKeep(DexType type) {
@@ -91,8 +93,9 @@
     }
 
     private void keepClass(DexType type) {
+      DexType baseType = type.lookupBaseType(options.itemFactory);
       toKeep.putIfAbsent(
-          type, new Pair<>(Sets.newConcurrentHashSet(), Sets.newConcurrentHashSet()));
+          baseType, new Pair<>(Sets.newConcurrentHashSet(), Sets.newConcurrentHashSet()));
     }
 
     @Override
diff --git a/src/main/java/com/android/tools/r8/graph/DexItemFactory.java b/src/main/java/com/android/tools/r8/graph/DexItemFactory.java
index 7ba3f89..ad03301 100644
--- a/src/main/java/com/android/tools/r8/graph/DexItemFactory.java
+++ b/src/main/java/com/android/tools/r8/graph/DexItemFactory.java
@@ -1187,6 +1187,10 @@
     return canonicalize(strings, new DexString(source));
   }
 
+  public DexString lookupString(int size, byte[] content) {
+    return strings.get(new DexString(size, content));
+  }
+
   public DexString lookupString(String source) {
     return strings.get(new DexString(source));
   }
diff --git a/src/main/java/com/android/tools/r8/graph/DexType.java b/src/main/java/com/android/tools/r8/graph/DexType.java
index 264c6f8..d1652ca 100644
--- a/src/main/java/com/android/tools/r8/graph/DexType.java
+++ b/src/main/java/com/android/tools/r8/graph/DexType.java
@@ -315,6 +315,21 @@
     return dexItemFactory.createType(newDesc);
   }
 
+  // Similar to the method above, but performs a lookup only, allowing to use
+  // this method also after strings are sorted in the ApplicationWriter.
+  public DexType lookupBaseType(DexItemFactory dexItemFactory) {
+    int leadingSquareBrackets = getNumberOfLeadingSquareBrackets();
+    if (leadingSquareBrackets == 0) {
+      return this;
+    }
+    DexString newDesc =
+        dexItemFactory.lookupString(
+            descriptor.size - leadingSquareBrackets,
+            Arrays.copyOfRange(
+                descriptor.content, leadingSquareBrackets, descriptor.content.length));
+    return dexItemFactory.lookupType(newDesc);
+  }
+
   public DexType replaceBaseType(DexType newBase, DexItemFactory dexItemFactory) {
     assert this.isArrayType();
     assert !newBase.isArrayType();
diff --git a/src/test/java/com/android/tools/r8/desugar/corelib/corelibjdktests/Jdk11TimeTests.java b/src/test/java/com/android/tools/r8/desugar/corelib/corelibjdktests/Jdk11TimeTests.java
index 052094a..01b3c9d 100644
--- a/src/test/java/com/android/tools/r8/desugar/corelib/corelibjdktests/Jdk11TimeTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/corelib/corelibjdktests/Jdk11TimeTests.java
@@ -10,33 +10,36 @@
 import com.android.tools.r8.D8TestCompileResult;
 import com.android.tools.r8.D8TestRunResult;
 import com.android.tools.r8.TestParameters;
-import com.android.tools.r8.TestParametersCollection;
 import com.android.tools.r8.ToolHelper.DexVm.Version;
-import com.android.tools.r8.ir.code.And;
-import com.android.tools.r8.utils.AndroidApiLevel;
+import com.android.tools.r8.utils.BooleanUtils;
 import com.android.tools.r8.utils.StringUtils;
 import java.nio.file.Paths;
-import org.junit.Assume;
+import java.util.List;
 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 Jdk11TimeTests extends Jdk11CoreLibTestBase {
 
   private final TestParameters parameters;
+  private final boolean shrinkDesugaredLibrary;
 
-  @Parameterized.Parameters(name = "{0}")
-  public static TestParametersCollection data() {
+  @Parameters(name = "{1}, shrinkDesugaredLibrary: {0}")
+  public static List<Object[]> data() {
     // TODO(134732760): Support Dalvik VMs, currently fails because libjavacrypto is required and
     // present only in ART runtimes.
-    return getTestParameters()
-        .withDexRuntimesStartingFromIncluding(Version.V5_1_1)
-        .withAllApiLevels()
-        .build();
+    return buildParameters(
+        BooleanUtils.values(),
+        getTestParameters()
+            .withDexRuntimesStartingFromIncluding(Version.V5_1_1)
+            .withAllApiLevels()
+            .build());
   }
 
-  public Jdk11TimeTests(TestParameters parameters) {
+  public Jdk11TimeTests(boolean shrinkDesugaredLibrary, TestParameters parameters) {
+    this.shrinkDesugaredLibrary = shrinkDesugaredLibrary;
     this.parameters = parameters;
   }
 
@@ -131,6 +134,7 @@
 
   @Test
   public void testTime() throws Exception {
+    KeepRuleConsumer keepRuleConsumer = createKeepRuleConsumer(parameters);
     String verbosity = "2";
     D8TestCompileResult compileResult =
         testForD8()
@@ -139,11 +143,14 @@
             .addProgramFiles(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar"))
             .addProgramFiles(Paths.get(JDK_TESTS_BUILD_DIR + "jcommander-1.48.jar"))
             .setMinApi(parameters.getApiLevel())
-            .enableCoreLibraryDesugaring(parameters.getApiLevel())
+            .enableCoreLibraryDesugaring(parameters.getApiLevel(), keepRuleConsumer)
             .compile()
             .withArt6Plus64BitsLib()
             .addDesugaredCoreLibraryRunClassPath(
-                this::buildDesugaredLibrary, parameters.getApiLevel());
+                this::buildDesugaredLibrary,
+                parameters.getApiLevel(),
+                keepRuleConsumer.get(),
+                shrinkDesugaredLibrary);
     for (String success : successes) {
       D8TestRunResult result =
           compileResult.run(parameters.getRuntime(), "TestNGMainRunner", verbosity, success);