This is a Machine Function version of D116058, also a conservative version of D37467 without critical edge splitting.
This pass does the transformation
bb.0: ... %3:gr32 = MOV32ri 7 JCC_1 %bb.2, 5, implicit $eflags bb.1: %5:gr32 = MOV32ri 11 bb.2: %0:gr32 = PHI %3:gr32, %bb.0, %5:gr32, %bb.1 // At most one non-const operand %6:gr32 = ADD32rr %2:gr32(tied-def 0), %0:gr32, implicit-def dead $eflags ... => bb.0: ... %7:gr32 = ADD32ri8 %2:gr32(tied-def 0), 7, implicit-def dead $eflags JCC_1 %bb.2, 5, implicit $eflags bb.1: %8:gr32 = ADD32ri8 %2:gr32(tied-def 0), 11, implicit-def dead $eflags bb.2: %6:gr32 = PHI %7:gr32, %bb.0, %8:gr32, %bb.1 ...
So we can reduce both static and dynamic instructions. If there is one non-const operand, we can still do the transformation without code size improvement, but still have performance improvement.
Test case dup-phi-users1.ll is from D116058 and dup-phi-users2.ll is from D37467.
Could you add a comment explaining the relationship between UseReg and the other arguments?
I'm guessing UseReg is what defines ImmVal.
In other words, putting all the arguments together, we're looking at a pattern like this:
While at it, would be worth adding a \pre UseReg is used in UseMI.