On 2014-12-17 7:57 PM, Kaz Kojima wrote:
This patch is discussed in PR55212
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=55212#c47
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=55212#c48
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=55212#c49
and is to avoid segfault in remove_pseudos.
In the problematic case in #c47, a call_insn has a note for an argument
via memory:
(expr_list:DF (use (mem:DF (reg/f:SI 699) [0 S8 A32]))
and this usage of pseudo 699 was missed by LRA. spill_hard_reg[699]
doesn't have correct value and causes a segfault in remove_pseudos.
--
* lra.c (lra_update_insn_regno_info): Take account of arguments
via memory which could be implicit usage of pseudo regs.
It could be a solution but I believe the problem should be solved in
some other way. The patch will generate a correct code but it might
also generate worse code. The regs mentioned in insn data are always
processed for liveness and adding the pseudo can make live range longer
potentially worsening allocation of other pseudos.
So I guess we need to find another solution for the problem. I
suspect spill_hard_reg is undefined as the pseudo 699 is present only in
CALL_INSN_USAGE. Otherwise, spill_hard_reg would be NULL. A solution
would be to figure out why there is only one reference, what does it
mean, and what we expect at the end of RA instead of pseudo (e.g.
anything, const or some register). And add code correspondingly in
remove_pseudos for case nrefs==0 or scratch pseudo (cases when
spill_hard_reg is not initialized). May be such code is the result of
wrong transformations (e.g. incomplete reg equiv substitution chain),
then it should be fixed somewhere else.
It would be nice to have a small test case for this problem with
compiler options to reproduce it.