----------------------------------------
define i4 @src(i4 %a, i4 %b, i4 %c) {
%or1 = or i4 %b, %a
%not1 = xor i4 %or1, -1
%or2 = or i4 %a, %c
%not2 = xor i4 %or2, -1
%and = and i4 %not2, %b
%or3 = or i4 %and, %not1
ret i4 %or3
}
define i4 @tgt(i4 %a, i4 %b, i4 %c) {
%and = and i4 %c, %b
%or = or i4 %and, %a
%or3 = xor i4 %or, -1
ret i4 %or3
}
Transformation seems to be correct!Details
Diff Detail
- Repository
- rG LLVM Github Monorepo
Event Timeline
Similar feedback as D112276 - more tests needed (8 commutes, extra uses of intermediate values).
| llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp | ||
|---|---|---|
| 2800–2801 | This one's a little smaller/easier than the other patch. If we have one-use checks on Op0 (the 'and') and Op1 (the 'not' of RHS), then this transform should be fine. So we don't need the m_OneUse on the inner 'not' here. | |
| llvm/test/Transforms/InstCombine/and-xor-or.ll | ||
| 1105 | Add an instruction to prevent this from commuting. | |
| 1110 | This is identical to the first test? | |
| 1167 | Flipped the wrong set of operands? This is effectively the same as "commute2". The final 'or' doesn't really matter (but it's fine to commute that just to be sure). | |
| 1202 | Add an instruction to prevent this from commuting. | |
LGTM.
The commute tests are not complete, but they should be enough to ensure the pattern-matching won't silently break.
| llvm/lib/Transforms/InstCombine/InstCombineAndOrXor.cpp | ||
|---|---|---|
| 2822 | The use checks aren't what I suggested, but either way, it is overly conservative (and we would see improvements on some of the tests that are currently left unchanged), so please put a TODO comment on this block to suggest we can loosen the use checks. | |
This one's a little smaller/easier than the other patch. If we have one-use checks on Op0 (the 'and') and Op1 (the 'not' of RHS), then this transform should be fine. So we don't need the m_OneUse on the inner 'not' here.