On 10/12/25 10:25 pm, Andrew Pinski wrote:
> The only question I have is why reject INTEGER_CST and not VECTOR_CST?
>  Really why reject integer cst in general?
>
> Thanks,
> Andrew
Hi Andrew,

The reason for rejecting |INTEGER_CST| is to avoid regressing rs6000 single 
rotate-and-insert/mask
instructions generation.

When @2 is a constant (a mask), the existing RTL infrastructure(simplify-rtx) 
handles the canonical XOR-form well.
Specifically, the combiner can match the sequence (rotate -> xor -> and -> xor) 
and merge it into a  rotate + (rotate-and-insert/mask) instruction.

If we force the IOR form |(A & C) | (B & ~C)| in GIMPLE for constants, the RTL 
combiner fails to match
the single rotate-and-insert pattern.
It often greedily simplifies the (ROTATE + AND ) part into a simple logical 
shift (|lshiftrt|), breaking the sequence.

Example Trace (IOR Form - Regressed):

When we have a sequence of ROTATE(A) + AND(A, C) + ANDN(B, C) + IOR (A,B)
1) combine sees: (rotate %a) & c
2) Simplifies to: lshiftrt %a (loss of IOR form semantics)
3) Result: We end up with 3 instructions: lshiftrt, andn, ior.


Example Trace (XOR Form - Current/Optimal):

When we have a sequence of ROTATE(A) +XOR + AND + XOR
1) Ignore the ROTATE
2) simplify-rtx sees the canonical XOR pattern.
3) Matches it directly to a rlwimi kind of operation.
4) Result: 2 instruction rotate + (rotate-and-insert/mask)

Attempting to match this new sequence in the combiner is difficult because the 
middle-end attempts to
simplify the shift/mask operation into a ZERO_EXTRACT. Since the RS6000 backend 
does not generally accept ZERO_EXTRACT
for these integer operations, the match fails, and we lose the rlwimi kind of 
instructions (regressing to 3 separate instructions).

Since simplify-rtx already detects and optimizes the constant case correctly
(transforming the XOR form where appropriate without breaking), i thought it is 
safer to restrict this GIMPLE patch to variables only.

Thanks,
Kishan

Reply via email to