Hi Segher,
>>>> This patch fixes a combiner bug in simplify_set which calls
>>>> CANNOT_CHANGE_MODE_CLASS with wrong mode params.
>>>> It occurs when trying to simplify paradoxical subregs of hw regs (whose
>>>> natural mode is lower than a word).
>>>>
>>>> In fact, changing from (set x:m1 (subreg:m1 (op:m2))) to (set (subreg:m2
>>>> x)  op2) is valid if REG_CANNOT_CHANGE_MODE_P (x, m1, m2) is false
>>>> and REG_CANNOT_CHANGE_MODE_P (x, GET_MODE (src), GET_MODE (SUBREG_REG
>>>> (src))
>>> r62212 (in 2003) changed it to what we have now, it used to be what you
>>> want to change it back to.
>>>
>>> You say m1 > m2, which means you have WORD_REGISTER_OPERATIONS defined.
>> No, just some hard regs whose natural mode size is 2 and UNIT_PER_WORD
>> is 4...
> You said it is a paradoxical subreg?  Or do you mean the result is
> a paradoxical subreg?
I mean that the result is a paradoxical subreg: (subreg:SI (reg:HI r0)
0) = (reg:SI r0) whith r0 is a HI reg.
>>> Where does this transformation go wrong?  Why is the resulting insn
>>> recognised at all?  For example, general_operand should refuse it.
>>> Maybe you have custom *_operand that do not handle subreg correctly?
>>>
>>> The existing code looks correct: what we want to know is if an m2
>>> interpreted as an m1 yields the correct value.  We might *also* want
>>> your condition, but I'm not sure about that.
>> OK, looks like both m1->m2 & m2 -> m1 checks would be needed, but the m1
>> -> m2 should be filtererd by valid predicates (general_operand).
>> Sorry about that.
> Hrm, maybe you can show the RTL before and after this transform?
RTL before combine:
(set (reg:SI 31 (lshiftt:SI (reg:SI 29) (const_int 16))))
(set (reg:HI 1 "r1") (reg:HI 25))
(set (reg:HI 0 "r0") (subreg:HI (reg:SI 31) 0))    ; LE target

r0 and r1 are HI regs

RTL after combining 1 --> 3:
(set (reg:HI 1 "r1") (reg:HI 25))
(set (reg:SI 0 "r0") (lshift:SI (reg:SI 29) (const_int 16)))
 and r1 is clobbered by last insn.

Thanks,
Aurélien




Reply via email to