RFC/discussion: https://lists.llvm.org/pipermail/llvm-dev/2021-September/152665.html
This patch implements simple hoisting of instructions from two
single-predecessor blocks to their common predecessor, as a subroutine
in the GVN pass.
The patch pairs two instructions (A and B) with the same value number,
moves A to the predecessor block, replaces all uses of B with A, and
deletes B.
Outline of the algorithm follows:
First we scan the then-block to collect hoist candidates ("then-" and "else-"
prefixes are purely naming and have no connection to the condition in the
predecessor block)
Then we scan the else-block for hoist candidates, that match some already
selected instruction from the then-block.
During both scans, instructions, which are not guaranteed to transfer control to
the following instruction act as "hoist barriers" - after we encounter such an
instruction, we select for potential hoisting/merge only instructions, which are
safe to execute speculatively.
Next we try hoist to hoist each candidate pair. We begin by trying to hoist
operands of the then-instruction. Every such operand must already be in a
dominating block or in itself paired with an instruction from the else-block. If
we cannot hoist an operand for whatever reason, the we stop trying to hoist the
pair.
Now that all the operands of the then-instruction are in a dominating block, we
check the operands of the else-instruction. They all must already be in a
dominating block, either initially or as a result of hoisting operands of the
then-instruction. If any of the operands is still in the else-block, we stop
trying to hoist the pair.
As a last step, we move the then-instruction to the predecessor block and delete
the else-instruction.
Not entirely clear from description which pairs does this store. What if we have N equivalent instructions in different paths, none dominating other? How many (and which) pairs is it going to store?