Richard Sandiford <[EMAIL PROTECTED]> writes:
> "Omar Torres" <[EMAIL PROTECTED]> writes:
>> Richard Sandiford wrote:
>>> Also, you need to beware of cases in which operands[1] overlaps
>>> operands[0].  The splitter says:
>>>
>>>  [(set (match_dup 2) (match_dup 4))
>>>   (set (match_dup 3) (match_dup 5))]
>>>
>>> and operands[2] is always the highpart:
>>>
>>>    operands[2] = gen_highpart(QImode, operands[0]);
>>>
>>> but consider the case in which operands[1] (and thus operands[4])
>>> is a memory reference that uses the high part of operands[0] as
>>> a base register.  In that case, the base register will be modified
>>> by the first split instruction and have the wrong value in the
>>> second split instruction.  See other ports for the canonical way
>>> of handling this.
>>>
>>> Richard
>>
>> By looking at other ports, I learned that I can detect when this happens
>> by using the reg_overlap_mentioned_p(). Here is one case:
>> (insn 43 115 74 (set (reg:HI 7 %i0h)
>>          (mem/s/j:HI (plus:HI (reg/f:HI 7 %i0h [orig:39 source ] [39])
>>                  (const_int 2 [0x2])) [0 <variable>.r+0 S2 A8])) 3
>> {*movhi} (nil)
>>      (nil))
>>
>>    I need to tell the compiler not to use as destination the same base
>> register when doing index operations. Any suggestions on how do I that?
>
> Hmm.  If one destination register is the base and the other is the
> index, you're probably best off adding them together and freeing up
> a register that way.  Hopefully it'll be a rare case.
>
> Because you're doing this in a splitter, some of the later
> rtl optimisers _might_ be able to get rid of the addition,
> but I wouldn't bet on it.

Sorry, this was the same thing Paul suggested.  Doesn't seem
as hacky to me as it did to him ;)

Richard

Reply via email to