Add support for iget/iput in virtual method hoister
Bug: b/241190995
Change-Id: I58f4fe00f8a768ab9d139dd78487aa54c7a0a992
diff --git a/src/main/java/com/android/tools/r8/ir/code/InstanceFieldInstruction.java b/src/main/java/com/android/tools/r8/ir/code/InstanceFieldInstruction.java
index faebe44..a9b3668 100644
--- a/src/main/java/com/android/tools/r8/ir/code/InstanceFieldInstruction.java
+++ b/src/main/java/com/android/tools/r8/ir/code/InstanceFieldInstruction.java
@@ -4,12 +4,17 @@
package com.android.tools.r8.ir.code;
+import com.android.tools.r8.graph.AppInfoWithClassHierarchy;
import com.android.tools.r8.graph.AppView;
+import com.android.tools.r8.graph.DexField;
+import com.android.tools.r8.graph.FieldResolutionResult;
import com.android.tools.r8.graph.ProgramMethod;
import com.android.tools.r8.ir.code.Instruction.SideEffectAssumption;
public interface InstanceFieldInstruction {
+ DexField getField();
+
boolean hasOutValue();
Value outValue();
@@ -33,4 +38,7 @@
boolean isInstancePut();
InstancePut asInstancePut();
+
+ FieldResolutionResult resolveField(
+ AppView<? extends AppInfoWithClassHierarchy> appView, ProgramMethod context);
}
diff --git a/src/main/java/com/android/tools/r8/optimize/virtualmethodhoisting/VirtualMethodHoister.java b/src/main/java/com/android/tools/r8/optimize/virtualmethodhoisting/VirtualMethodHoister.java
index 93b2570..0f7160e 100644
--- a/src/main/java/com/android/tools/r8/optimize/virtualmethodhoisting/VirtualMethodHoister.java
+++ b/src/main/java/com/android/tools/r8/optimize/virtualmethodhoisting/VirtualMethodHoister.java
@@ -18,7 +18,9 @@
import static com.android.tools.r8.ir.code.Opcodes.IF;
import static com.android.tools.r8.ir.code.Opcodes.INC;
import static com.android.tools.r8.ir.code.Opcodes.INIT_CLASS;
+import static com.android.tools.r8.ir.code.Opcodes.INSTANCE_GET;
import static com.android.tools.r8.ir.code.Opcodes.INSTANCE_OF;
+import static com.android.tools.r8.ir.code.Opcodes.INSTANCE_PUT;
import static com.android.tools.r8.ir.code.Opcodes.INT_SWITCH;
import static com.android.tools.r8.ir.code.Opcodes.MONITOR;
import static com.android.tools.r8.ir.code.Opcodes.MUL;
@@ -47,6 +49,7 @@
import com.android.tools.r8.graph.AppView;
import com.android.tools.r8.graph.DexClass;
import com.android.tools.r8.graph.DexEncodedMethod;
+import com.android.tools.r8.graph.DexField;
import com.android.tools.r8.graph.DexItemFactory;
import com.android.tools.r8.graph.DexMethod;
import com.android.tools.r8.graph.DexProgramClass;
@@ -349,6 +352,8 @@
break;
}
+ case INSTANCE_GET:
+ case INSTANCE_PUT:
case STATIC_GET:
case STATIC_PUT:
{
@@ -360,10 +365,17 @@
return false;
}
- if (fieldInstruction.isStaticPut()) {
- Value value = fieldInstruction.asStaticPut().value();
- DexType fieldType = fieldInstruction.getField().getType();
- if (isInvalidUseOfThis(value, fieldType, targetMethod)) {
+ DexField field = fieldInstruction.getField();
+ if (fieldInstruction.isInstanceFieldInstruction()) {
+ Value object = fieldInstruction.asInstanceFieldInstruction().object();
+ if (isInvalidUseOfThis(object, field.getHolderType(), targetMethod)) {
+ return false;
+ }
+ }
+
+ if (fieldInstruction.isFieldPut()) {
+ Value value = fieldInstruction.asFieldPut().value();
+ if (isInvalidUseOfThis(value, field.getType(), targetMethod)) {
return false;
}
}