Extend the VarHandle desugaring with instance fields of type long
Bug: b/247076137
Change-Id: I11a9bbde938d6fd54f333f519758e0c40c759547
diff --git a/src/main/java/com/android/tools/r8/ir/desugar/varhandle/VarHandleDesugaringMethods.java b/src/main/java/com/android/tools/r8/ir/desugar/varhandle/VarHandleDesugaringMethods.java
index 78f3611..e32fa57 100644
--- a/src/main/java/com/android/tools/r8/ir/desugar/varhandle/VarHandleDesugaringMethods.java
+++ b/src/main/java/com/android/tools/r8/ir/desugar/varhandle/VarHandleDesugaringMethods.java
@@ -1296,10 +1296,32 @@
CfLabel label1 = new CfLabel();
return new CfCode(
method.holder,
- 2,
+ 4,
2,
ImmutableList.of(
- label0, new CfConstNumber(-1, ValueType.LONG), new CfReturn(ValueType.LONG), label1),
+ label0,
+ new CfLoad(ValueType.OBJECT, 0),
+ new CfInstanceFieldRead(
+ factory.createField(
+ factory.createType("Lcom/android/tools/r8/DesugarVarHandle;"),
+ factory.createType("Lsun/misc/Unsafe;"),
+ factory.createString("U"))),
+ new CfLoad(ValueType.OBJECT, 1),
+ new CfLoad(ValueType.OBJECT, 0),
+ new CfInstanceFieldRead(
+ factory.createField(
+ factory.createType("Lcom/android/tools/r8/DesugarVarHandle;"),
+ factory.longType,
+ factory.createString("offset"))),
+ new CfInvoke(
+ 182,
+ factory.createMethod(
+ factory.createType("Lsun/misc/Unsafe;"),
+ factory.createProto(factory.longType, factory.objectType, factory.longType),
+ factory.createString("getLong")),
+ false),
+ new CfReturn(ValueType.LONG),
+ label1),
ImmutableList.of(),
ImmutableList.of());
}
@@ -1310,6 +1332,8 @@
CfLabel label2 = new CfLabel();
CfLabel label3 = new CfLabel();
CfLabel label4 = new CfLabel();
+ CfLabel label5 = new CfLabel();
+ CfLabel label6 = new CfLabel();
return new CfCode(
method.holder,
5,
@@ -1347,7 +1371,7 @@
factory.createProto(factory.voidType, factory.objectType, factory.intType),
factory.createString("set")),
false),
- new CfGoto(label3),
+ new CfGoto(label5),
label2,
new CfFrame(
new Int2ObjectAVLTreeMap<>(
@@ -1362,6 +1386,48 @@
new CfInstanceFieldRead(
factory.createField(
factory.createType("Lcom/android/tools/r8/DesugarVarHandle;"),
+ factory.classType,
+ factory.createString("type"))),
+ new CfStaticFieldRead(
+ factory.createField(
+ factory.createType("Ljava/lang/Long;"),
+ factory.classType,
+ factory.createString("TYPE"))),
+ new CfIfCmp(If.Type.NE, ValueType.OBJECT, label4),
+ label3,
+ new CfLoad(ValueType.OBJECT, 0),
+ new CfLoad(ValueType.OBJECT, 1),
+ new CfLoad(ValueType.OBJECT, 0),
+ new CfLoad(ValueType.OBJECT, 2),
+ new CfInvoke(
+ 182,
+ factory.createMethod(
+ factory.createType("Lcom/android/tools/r8/DesugarVarHandle;"),
+ factory.createProto(factory.longType, factory.objectType),
+ factory.createString("toLongIfPossible")),
+ false),
+ new CfInvoke(
+ 182,
+ factory.createMethod(
+ factory.createType("Lcom/android/tools/r8/DesugarVarHandle;"),
+ factory.createProto(factory.voidType, factory.objectType, factory.longType),
+ factory.createString("set")),
+ false),
+ new CfGoto(label5),
+ label4,
+ new CfFrame(
+ new Int2ObjectAVLTreeMap<>(
+ new int[] {0, 1, 2},
+ new FrameType[] {
+ FrameType.initializedNonNullReference(
+ factory.createType("Lcom/android/tools/r8/DesugarVarHandle;")),
+ FrameType.initializedNonNullReference(factory.objectType),
+ FrameType.initializedNonNullReference(factory.objectType)
+ })),
+ new CfLoad(ValueType.OBJECT, 0),
+ new CfInstanceFieldRead(
+ factory.createField(
+ factory.createType("Lcom/android/tools/r8/DesugarVarHandle;"),
factory.createType("Lsun/misc/Unsafe;"),
factory.createString("U"))),
new CfLoad(ValueType.OBJECT, 1),
@@ -1380,7 +1446,7 @@
factory.voidType, factory.objectType, factory.longType, factory.objectType),
factory.createString("putObject")),
false),
- label3,
+ label5,
new CfFrame(
new Int2ObjectAVLTreeMap<>(
new int[] {0, 1, 2},
@@ -1391,7 +1457,7 @@
FrameType.initializedNonNullReference(factory.objectType)
})),
new CfReturnVoid(),
- label4),
+ label6),
ImmutableList.of(),
ImmutableList.of());
}
diff --git a/src/test/java/com/android/tools/r8/cf/varhandle/VarHandleDesugaringInstanceLongFieldTest.java b/src/test/java/com/android/tools/r8/cf/varhandle/VarHandleDesugaringInstanceLongFieldTest.java
index 8e91f72..c50db54 100644
--- a/src/test/java/com/android/tools/r8/cf/varhandle/VarHandleDesugaringInstanceLongFieldTest.java
+++ b/src/test/java/com/android/tools/r8/cf/varhandle/VarHandleDesugaringInstanceLongFieldTest.java
@@ -83,4 +83,9 @@
protected String getExpectedOutput() {
return EXPECTED_OUTPUT;
}
+
+ @Override
+ protected boolean getTestWithDesugaring() {
+ return true;
+ }
}
diff --git a/src/test/java/com/android/tools/r8/ir/desugar/varhandle/DesugarVarHandle.java b/src/test/java/com/android/tools/r8/ir/desugar/varhandle/DesugarVarHandle.java
index 57c13dd..af2bb5b 100644
--- a/src/test/java/com/android/tools/r8/ir/desugar/varhandle/DesugarVarHandle.java
+++ b/src/test/java/com/android/tools/r8/ir/desugar/varhandle/DesugarVarHandle.java
@@ -135,14 +135,15 @@
}
long getLong(Object ct1) {
- // TODO(b/247076137): Implement.
- return -1L;
+ return U.getLong(ct1, offset);
}
// set variants.
void set(Object ct1, Object newValue) {
if (type == int.class) {
setInt(ct1, toIntIfPossible(newValue));
+ } else if (type == long.class) {
+ setLong(ct1, toLongIfPossible(newValue));
} else {
U.putObject(ct1, offset, newValue);
}