Fix dominator check in ValueUtils.computeInitialArrayValues()
It was not correctly identifying linear edges.
Bug: 391417819
Change-Id: Ibfea470210b2af338129c306f349e87a0e47af6e
diff --git a/src/main/java/com/android/tools/r8/ir/code/BasicBlock.java b/src/main/java/com/android/tools/r8/ir/code/BasicBlock.java
index ad61781..7250c3a 100644
--- a/src/main/java/com/android/tools/r8/ir/code/BasicBlock.java
+++ b/src/main/java/com/android/tools/r8/ir/code/BasicBlock.java
@@ -380,6 +380,10 @@
return predecessors.size() == 1;
}
+ public boolean hasUniquePredecessorWithUniqueSuccessor() {
+ return hasUniquePredecessor() && getUniquePredecessor().getSuccessors().size() == 1;
+ }
+
public BasicBlock getUniquePredecessor() {
assert hasUniquePredecessor();
return predecessors.get(0);
diff --git a/src/main/java/com/android/tools/r8/ir/conversion/passes/ArrayConstructionSimplifier.java b/src/main/java/com/android/tools/r8/ir/conversion/passes/ArrayConstructionSimplifier.java
index e934e3e..a674ff5 100644
--- a/src/main/java/com/android/tools/r8/ir/conversion/passes/ArrayConstructionSimplifier.java
+++ b/src/main/java/com/android/tools/r8/ir/conversion/passes/ArrayConstructionSimplifier.java
@@ -229,19 +229,6 @@
ArrayPut lastArrayPut = ArrayUtils.last(arrayValues.getArrayPutsByIndex());
BasicBlock lastArrayPutBlock = lastArrayPut.getBlock();
BasicBlock subgraphEntryBlock = arrayValue.definition.getBlock();
- for (ArrayPut arrayPut : arrayValues.getArrayPutsByIndex()) {
- if (arrayPut.getBlock() != lastArrayPut.getBlock()
- && !DominatorChecker.check(subgraphEntryBlock, lastArrayPutBlock, arrayPut.getBlock())) {
- return false;
- }
- }
- for (Instruction instruction = lastArrayPut.getBlock().getLastInstruction();
- instruction != lastArrayPut;
- instruction = instruction.getPrev()) {
- if (instruction.isArrayPut() && instruction.asArrayPut().array() == arrayValue) {
- return false;
- }
- }
// Ensure all blocks for users of the array are dominated by the last array-put's block.
for (BasicBlock usageBlock : usageBlocks) {
diff --git a/src/main/java/com/android/tools/r8/utils/DominatorChecker.java b/src/main/java/com/android/tools/r8/utils/DominatorChecker.java
index d1dc853..94bdd97 100644
--- a/src/main/java/com/android/tools/r8/utils/DominatorChecker.java
+++ b/src/main/java/com/android/tools/r8/utils/DominatorChecker.java
@@ -56,12 +56,12 @@
}
// See if a block on the same linear path has already been checked.
BasicBlock firstSplittingBlock = targetBlock;
- if (firstSplittingBlock.hasUniqueSuccessor()) {
+ if (firstSplittingBlock.hasUniqueSuccessorWithUniquePredecessor()) {
do {
// knownDominators prevents firstSplittingBlock from being destBlock.
assert firstSplittingBlock != subgraphExitBlock;
firstSplittingBlock = firstSplittingBlock.getUniqueSuccessor();
- } while (firstSplittingBlock.hasUniqueSuccessor());
+ } while (firstSplittingBlock.hasUniqueSuccessorWithUniquePredecessor());
if (knownDominators.contains(firstSplittingBlock)) {
knownDominators.add(targetBlock);
@@ -130,7 +130,7 @@
// successors.
Set<BasicBlock> headAndTailDominators = Sets.newIdentityHashSet();
headAndTailDominators.add(subgraphEntryBlock);
- while (subgraphEntryBlock.hasUniqueSuccessor()) {
+ while (subgraphEntryBlock.hasUniqueSuccessorWithUniquePredecessor()) {
subgraphEntryBlock = subgraphEntryBlock.getUniqueSuccessor();
if (!headAndTailDominators.add(subgraphEntryBlock)) {
// Hit an infinite loop. Code would not verify in this case.
@@ -150,7 +150,7 @@
// Shrink the subgraph by moving subgraphExitBlock back to the first block with multiple
// predecessors.
headAndTailDominators.add(subgraphExitBlock);
- while (subgraphExitBlock.hasUniquePredecessor()) {
+ while (subgraphExitBlock.hasUniquePredecessorWithUniqueSuccessor()) {
subgraphExitBlock = subgraphExitBlock.getUniquePredecessor();
if (!headAndTailDominators.add(subgraphExitBlock)) {
if (subgraphEntryBlock == subgraphExitBlock) {
diff --git a/src/main/java/com/android/tools/r8/utils/ValueUtils.java b/src/main/java/com/android/tools/r8/utils/ValueUtils.java
index 9082be5..178b51f 100644
--- a/src/main/java/com/android/tools/r8/utils/ValueUtils.java
+++ b/src/main/java/com/android/tools/r8/utils/ValueUtils.java
@@ -167,6 +167,7 @@
* * An array-put is found after the last-index array-put.
* * An array-put is found where the array and value are the same: arr[index] = arr;
* * There are multiple array-put instructions for the same index.
+ * * An array-put exists that does not dominate the array-put of the highest index.
* </pre>
*/
public static ArrayValues computeInitialArrayValues(NewArrayEmpty newArrayEmpty) {