Extend profile rewriting to additional initializer argument classes

Bug: b/265729283
Bug: b/267592755
Change-Id: I6b0a6e1935fbab4f9650de2496d22b267020cf14
diff --git a/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorProgramOptimizer.java b/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorProgramOptimizer.java
index bf1afad..16edb6a 100644
--- a/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorProgramOptimizer.java
+++ b/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorProgramOptimizer.java
@@ -36,6 +36,7 @@
 import com.android.tools.r8.ir.optimize.info.ConcreteCallSiteOptimizationInfo;
 import com.android.tools.r8.optimize.argumentpropagation.ArgumentPropagatorGraphLens.Builder;
 import com.android.tools.r8.optimize.argumentpropagation.utils.ParameterRemovalUtils;
+import com.android.tools.r8.profile.art.rewriting.ArtProfileCollectionAdditions;
 import com.android.tools.r8.shaking.AppInfoWithLiveness;
 import com.android.tools.r8.shaking.KeepFieldInfo;
 import com.android.tools.r8.shaking.KeepMethodInfo;
@@ -193,18 +194,23 @@
       Timing timing)
       throws ExecutionException {
     timing.begin("Optimize components");
+    ArtProfileCollectionAdditions artProfileCollectionAdditions =
+        ArtProfileCollectionAdditions.create(appView);
+    ArgumentPropagatorSyntheticEventConsumer eventConsumer =
+        ArgumentPropagatorSyntheticEventConsumer.create(artProfileCollectionAdditions);
     ProcessorContext processorContext = appView.createProcessorContext();
     Collection<Builder> partialGraphLensBuilders =
         ThreadUtils.processItemsWithResults(
             stronglyConnectedProgramComponents,
             classes ->
-                new StronglyConnectedComponentOptimizer(processorContext)
+                new StronglyConnectedComponentOptimizer(eventConsumer, processorContext)
                     .optimize(
                         classes,
                         interfaceDispatchOutsideProgram.getOrDefault(
                             classes, DexMethodSignatureSet.empty()),
                         affectedClassConsumer),
             executorService);
+    artProfileCollectionAdditions.commit(appView);
     timing.end();
 
     // Merge all the partial, disjoint graph lens builders into a single graph lens.
@@ -267,9 +273,12 @@
     private final Map<DexMethodSignature, Pair<AllowedPrototypeChanges, DexMethodSignature>>
         occupiedMethodSignatures = new HashMap<>();
 
+    private final ArgumentPropagatorSyntheticEventConsumer eventConsumer;
     private final ProcessorContext processorContext;
 
-    public StronglyConnectedComponentOptimizer(ProcessorContext processorContext) {
+    public StronglyConnectedComponentOptimizer(
+        ArgumentPropagatorSyntheticEventConsumer eventConsumer, ProcessorContext processorContext) {
+      this.eventConsumer = eventConsumer;
       this.processorContext = processorContext;
     }
 
@@ -876,16 +885,17 @@
           }
         }
       }
-      DexType extraArgumentType =
+      DexProgramClass extraArgumentClass =
           appView
               .getSyntheticItems()
               .createClass(
                   kinds -> kinds.NON_FIXED_INIT_TYPE_ARGUMENT,
                   processorContext.createMethodProcessingContext(method).createUniqueContext(),
-                  appView)
-              .getType();
+                  appView);
+      eventConsumer.acceptInitializerArgumentClass(extraArgumentClass, method);
       RewrittenPrototypeDescription finalPrototypeChanges =
-          prototypeChanges.withExtraParameters(new ExtraUnusedNullParameter(extraArgumentType));
+          prototypeChanges.withExtraParameters(
+              new ExtraUnusedNullParameter(extraArgumentClass.getType()));
       boolean added =
           instanceInitializerSignatures.add(
               finalPrototypeChanges.rewriteMethod(method, dexItemFactory));
diff --git a/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorSyntheticEventConsumer.java b/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorSyntheticEventConsumer.java
new file mode 100644
index 0000000..aae0602
--- /dev/null
+++ b/src/main/java/com/android/tools/r8/optimize/argumentpropagation/ArgumentPropagatorSyntheticEventConsumer.java
@@ -0,0 +1,52 @@
+// Copyright (c) 2023, 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.optimize.argumentpropagation;
+
+import com.android.tools.r8.graph.DexProgramClass;
+import com.android.tools.r8.graph.ProgramMethod;
+import com.android.tools.r8.profile.art.rewriting.ArtProfileCollectionAdditions;
+import com.android.tools.r8.profile.art.rewriting.ConcreteArtProfileCollectionAdditions;
+
+public interface ArgumentPropagatorSyntheticEventConsumer {
+
+  void acceptInitializerArgumentClass(DexProgramClass clazz, ProgramMethod context);
+
+  static ArgumentPropagatorSyntheticEventConsumer create(
+      ArtProfileCollectionAdditions collectionAdditions) {
+    if (collectionAdditions.isNop()) {
+      return empty();
+    }
+    return create(collectionAdditions.asConcrete());
+  }
+
+  static ArgumentPropagatorSyntheticEventConsumer create(
+      ConcreteArtProfileCollectionAdditions collectionAdditions) {
+    return (clazz, context) ->
+        collectionAdditions.applyIfContextIsInProfile(
+            context, additionsBuilder -> additionsBuilder.addRule(clazz));
+  }
+
+  static ArgumentPropagatorSyntheticEventConsumer empty() {
+    return EmptyArgumentPropagatorSyntheticEventConsumer.getInstance();
+  }
+
+  class EmptyArgumentPropagatorSyntheticEventConsumer
+      implements ArgumentPropagatorSyntheticEventConsumer {
+
+    private static EmptyArgumentPropagatorSyntheticEventConsumer INSTANCE =
+        new EmptyArgumentPropagatorSyntheticEventConsumer();
+
+    private EmptyArgumentPropagatorSyntheticEventConsumer() {}
+
+    static EmptyArgumentPropagatorSyntheticEventConsumer getInstance() {
+      return INSTANCE;
+    }
+
+    @Override
+    public void acceptInitializerArgumentClass(DexProgramClass clazz, ProgramMethod context) {
+      // Intentionally empty.
+    }
+  }
+}
diff --git a/src/main/java/com/android/tools/r8/profile/art/rewriting/ArtProfileCollectionAdditions.java b/src/main/java/com/android/tools/r8/profile/art/rewriting/ArtProfileCollectionAdditions.java
index 858de9d..36d235f 100644
--- a/src/main/java/com/android/tools/r8/profile/art/rewriting/ArtProfileCollectionAdditions.java
+++ b/src/main/java/com/android/tools/r8/profile/art/rewriting/ArtProfileCollectionAdditions.java
@@ -43,7 +43,7 @@
     return false;
   }
 
-  ConcreteArtProfileCollectionAdditions asConcrete() {
+  public ConcreteArtProfileCollectionAdditions asConcrete() {
     return null;
   }
 
diff --git a/src/main/java/com/android/tools/r8/profile/art/rewriting/ConcreteArtProfileCollectionAdditions.java b/src/main/java/com/android/tools/r8/profile/art/rewriting/ConcreteArtProfileCollectionAdditions.java
index 24d6911..85c54e1 100644
--- a/src/main/java/com/android/tools/r8/profile/art/rewriting/ConcreteArtProfileCollectionAdditions.java
+++ b/src/main/java/com/android/tools/r8/profile/art/rewriting/ConcreteArtProfileCollectionAdditions.java
@@ -47,7 +47,7 @@
     }
   }
 
-  void applyIfContextIsInProfile(
+  public void applyIfContextIsInProfile(
       DexClassAndMethod context, Consumer<ArtProfileAdditionsBuilder> builderConsumer) {
     applyIfContextIsInProfile(context.getReference(), builderConsumer);
   }
@@ -61,7 +61,7 @@
   }
 
   @Override
-  ConcreteArtProfileCollectionAdditions asConcrete() {
+  public ConcreteArtProfileCollectionAdditions asConcrete() {
     return this;
   }
 
diff --git a/src/test/java/com/android/tools/r8/internal/opensourceapps/TiviTest.java b/src/test/java/com/android/tools/r8/internal/opensourceapps/TiviTest.java
index 8d8aed0..ac5d3b5 100644
--- a/src/test/java/com/android/tools/r8/internal/opensourceapps/TiviTest.java
+++ b/src/test/java/com/android/tools/r8/internal/opensourceapps/TiviTest.java
@@ -52,7 +52,6 @@
         .addOptionsModification(options -> options.outline.enabled = false)
         .addOptionsModification(
             options -> options.apiModelingOptions().enableStubbingOfClasses = false)
-        .addOptionsModification(options -> options.callSiteOptimizationOptions().setEnabled(false))
         .addOptionsModification(
             options -> options.getArtProfileOptions().setEnableCompletenessCheckForTesting(true))
         .apply(this::configure)