Retrieve single call target without liveness if possible.
Bug: 128421006
Change-Id: Ifb1cbd6c0eaa3ff34b67b0469f12f61f90ede657
diff --git a/src/main/java/com/android/tools/r8/ir/conversion/IRConverter.java b/src/main/java/com/android/tools/r8/ir/conversion/IRConverter.java
index a66e958..37102ef 100644
--- a/src/main/java/com/android/tools/r8/ir/conversion/IRConverter.java
+++ b/src/main/java/com/android/tools/r8/ir/conversion/IRConverter.java
@@ -915,7 +915,7 @@
previous = printMethod(code, "IR after disable assertions (SSA)", previous);
- if (options.enableNonNullTracking && nonNullTracker != null) {
+ if (nonNullTracker != null) {
nonNullTracker.addNonNull(code);
assert code.isConsistentSSA();
}
@@ -974,7 +974,7 @@
invertConditionalsForTesting(code);
}
- if (options.enableNonNullTracking && nonNullTracker != null) {
+ if (nonNullTracker != null) {
// Computation of non-null parameters on normal exits rely on the existence of non-null IRs.
nonNullTracker.computeNonNullParamOnNormalExits(feedback, code);
nonNullTracker.cleanupNonNull(code);
diff --git a/src/main/java/com/android/tools/r8/ir/optimize/NonNullTracker.java b/src/main/java/com/android/tools/r8/ir/optimize/NonNullTracker.java
index ec338ca..489891a 100644
--- a/src/main/java/com/android/tools/r8/ir/optimize/NonNullTracker.java
+++ b/src/main/java/com/android/tools/r8/ir/optimize/NonNullTracker.java
@@ -120,14 +120,28 @@
knownToBeNonNullValues.add(knownToBeNonNullValue);
}
}
- if (current.isInvokeMethod()
- && !current.isInvokePolymorphic()
- && appView.appInfo().hasLiveness()) {
- DexEncodedMethod singleTarget =
- current
- .asInvokeMethod()
- .lookupSingleTarget(
- appView.appInfo().withLiveness(), code.method.method.holder);
+ if (current.isInvokeMethod() && !current.isInvokePolymorphic()) {
+ DexEncodedMethod singleTarget = null;
+ if (appView.enableWholeProgramOptimizations()) {
+ assert appView.appInfo().hasLiveness();
+ singleTarget =
+ current
+ .asInvokeMethod()
+ .lookupSingleTarget(
+ appView.appInfo().withLiveness(), code.method.method.holder);
+ } else {
+ // Even in D8, invoke-{direct|static} can be resolved without liveness.
+ // Due to the incremental compilation, though, it is allowed only if the holder of the
+ // invoked method is same as that of the method we are processing now.
+ DexMethod invokedMethod = current.asInvokeMethod().getInvokedMethod();
+ if (invokedMethod.holder == code.method.method.holder) {
+ if (current.isInvokeDirect()) {
+ singleTarget = appView.appInfo().lookupDirectTarget(invokedMethod);
+ } else if (current.isInvokeStatic()) {
+ singleTarget = appView.appInfo().lookupStaticTarget(invokedMethod);
+ }
+ }
+ }
if (singleTarget != null
&& singleTarget.getOptimizationInfo().getNonNullParamOnNormalExits() != null) {
BitSet facts = singleTarget.getOptimizationInfo().getNonNullParamOnNormalExits();