https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67260

--- Comment #7 from Alexander Monakov <amonakov at gcc dot gnu.org> ---
Oleg, Rich, there's some confusion in comments 4-6.  Please unwind all the way
back to comment #1, and let me explain the issue once again.  I now see that my
phrasing back then was insufficiently detailed.

Look at the RTL template I quote there, and note how it picks a register to
hold relative callee address:

10484    (clobber (match_scratch:SI 3 "=&k"))

It then proceeds to specify how to emit a sequence of insns, first to load the
address into operands[3] (the scratch reg above), and then to make a call using
operands[3]. The split takes part after reload, so at the time of register
allocation the instruction is not split and is represented by the RTL template
as quoted.

Note that there's no way to specify that the match_scratch reg is not going to
be live simultaneously with operands[0], the return value. In fact, you can
imagine that splitting emits some third instruction after the call that tries
to use operands[3] and operands[0], and then there's no way to pick a scratch
reg.

So it's not like GCC is not doing something it should. It's sh.md that demands
the impossible.

This is why I suggested using a hard register in place of a scratch (because
r0-r3 are free to use for that purpose anyway), but of course it has to be
properly encoded in the RTL template: you'd clobber a specific hardreg instead
of clobbering a scratch. Perhaps Rich misremembered something when saying that
the chosen hardreg would not be explicit in the RTL.

Does that clarify?

Reply via email to