[Linux-ia64] Re: optimization/3783
Jim Wilson
wilson@cygnus.com
Thu Sep 6 15:09:00 GMT 2001
You have identified the right piece of code to look at, but the suggested
fix is not right.
POST_MODIFY is an addressing mode. It is valid only as part of a MEM, it
isn't valid as a SET_SRC. What your patch does by accident is disable the
recursion in canon_rtx because it recurs on PLUS, but not on POST_MODIFY.
The real problem here is that we have some shared RTL being destructively
modified.
We have two instructions:
...*fp...
reg350 = fp + 1
When the alias analysis code sees the second instruction, it determines
that the SET_SRC does not vary (!rtx_varies), and stores it in reg_known_value.
Later, the AUTO_INC_DEC code modifies the sequence to this
reg350 = fp
...*reg350...
reg350 = reg350 + 1
We do this so that we can now combine the two insns to use a POST_MODIFY
addressing mode. We change the assignment by destructively modifying it in
place. We when do this, we accidentally also change reg_known_value which
is shared RTL. We now have
reg_known_value[350] = r350 + 1
which is nonsense, because reg_known_value is supposed to be a function
invariant value. This causes canon_rtx to go into the infinite loop.
We could fix this by unsharing RTL, but I think there is a deeper problem
here. When flow modifies the instruction sequence, it is invalidating
the alias info. reg350 is no longer set only once, and hence it is wrong
to have any reg_known_values value for it. Thus I think the right fix is
to add an interface to the alias code so that we can invalidate a
reg_known_values entry. Then the AUTO_INC_DEC code that does this
transformation would call into alias.c to invalidate reg_known_values for
r350. The aliasing code previously did not need any invalidate support
because it was originally only used in the scheduler, and the scheduler
does not do any code transformations like this, it only reorders code.
Jim
More information about the Gcc-bugs
mailing list