GCC reload problem
David S. Miller
davem@redhat.com
Fri Apr 11 00:30:00 GMT 2003
From: Eric Botcazou <ebotcazou@libertysurf.fr>
Date: Thu, 10 Apr 2003 23:31:32 +0200
Now the machinery used to trigger for these invalid subregs, independently of
the constraints of the insn. But it appears that you have disabled it: from
reload.c:find_reloads()
/* This following hunk of code should no longer be
needed at all with SUBREG_BYTE. If you need this
code back, please explain to me why so I can
fix the real problem. -DaveM */
#if 0
/* Subreg of a hard reg which can't handle the subreg's mode
or which would handle that mode in the wrong number of
registers for subregging to work. */
|| (GET_CODE (operand) == REG
&& REGNO (operand) < FIRST_PSEUDO_REGISTER
&& ((GET_MODE_SIZE (operand_mode[i]) <= UNITS_PER_WORD
&& (GET_MODE_SIZE (GET_MODE (operand))
> UNITS_PER_WORD)
&& ((GET_MODE_SIZE (GET_MODE (operand))
/ UNITS_PER_WORD)
!= HARD_REGNO_NREGS (REGNO (operand),
GET_MODE (operand))))
|| ! HARD_REGNO_MODE_OK (REGNO (operand) + offset,
operand_mode[i])))
#endif
Re-enabling it fix PR target/10286.
Hence the question: what is the replacement machinery that is supposed to be
doing the work?
The problem here is that with SUBREG_BYTE, the word-based tests in
this if statement are no longer valid. Which parts of the comparison
are actually passing?
We need to weed out the invalid parts of the test, and only retain the
valid portions necessary to make this code trigger when it should.
My initial guess is that the part that's valid is the
HARD_REGNO_MODE_OK check. And thus we'd end up with something like:
|| (GET_CODE (operand) == REG
&& REGNO (operand) < FIRST_PSEUDO_REGISTER
&& ! HARD_REGNO_MODE_OK (REGNO (operand) + offset,
operand_mode[i]))
More information about the Gcc
mailing list