Commit 65f914e7 by Richard Sandiford Committed by Richard Sandiford

poly_int: reloading complex subregs

This patch splits out a condition that is common to both push_reload
and reload_inner_reg_of_subreg.

2018-01-03  Richard Sandiford  <richard.sandiford@linaro.org>
	    Alan Hayward  <alan.hayward@arm.com>
	    David Sherwood  <david.sherwood@arm.com>

gcc/
	* reload.c (complex_word_subreg_p): New function.
	(reload_inner_reg_of_subreg, push_reload): Use it.

Co-Authored-By: Alan Hayward <alan.hayward@arm.com>
Co-Authored-By: David Sherwood <david.sherwood@arm.com>

From-SVN: r256159
parent 00224b1a
...@@ -2,6 +2,13 @@ ...@@ -2,6 +2,13 @@
Alan Hayward <alan.hayward@arm.com> Alan Hayward <alan.hayward@arm.com>
David Sherwood <david.sherwood@arm.com> David Sherwood <david.sherwood@arm.com>
* reload.c (complex_word_subreg_p): New function.
(reload_inner_reg_of_subreg, push_reload): Use it.
2018-01-03 Richard Sandiford <richard.sandiford@linaro.org>
Alan Hayward <alan.hayward@arm.com>
David Sherwood <david.sherwood@arm.com>
* lra-constraints.c (process_alt_operands): Reject matched * lra-constraints.c (process_alt_operands): Reject matched
operands whose sizes aren't ordered. operands whose sizes aren't ordered.
(match_reload): Refer to this check here. (match_reload): Refer to this check here.
...@@ -811,6 +811,23 @@ find_reusable_reload (rtx *p_in, rtx out, enum reg_class rclass, ...@@ -811,6 +811,23 @@ find_reusable_reload (rtx *p_in, rtx out, enum reg_class rclass,
return n_reloads; return n_reloads;
} }
/* Return true if:
(a) (subreg:OUTER_MODE REG ...) represents a word or subword subreg
of a multiword value; and
(b) the number of *words* in REG does not match the number of *registers*
in REG. */
static bool
complex_word_subreg_p (machine_mode outer_mode, rtx reg)
{
machine_mode inner_mode = GET_MODE (reg);
return (GET_MODE_SIZE (outer_mode) <= UNITS_PER_WORD
&& GET_MODE_SIZE (inner_mode) > UNITS_PER_WORD
&& GET_MODE_SIZE (inner_mode) / UNITS_PER_WORD != REG_NREGS (reg));
}
/* Return true if X is a SUBREG that will need reloading of its SUBREG_REG /* Return true if X is a SUBREG that will need reloading of its SUBREG_REG
expression. MODE is the mode that X will be used in. OUTPUT is true if expression. MODE is the mode that X will be used in. OUTPUT is true if
the function is invoked for the output part of an enclosing reload. */ the function is invoked for the output part of an enclosing reload. */
...@@ -842,11 +859,7 @@ reload_inner_reg_of_subreg (rtx x, machine_mode mode, bool output) ...@@ -842,11 +859,7 @@ reload_inner_reg_of_subreg (rtx x, machine_mode mode, bool output)
INNER is larger than a word and the number of registers in INNER is INNER is larger than a word and the number of registers in INNER is
not the same as the number of words in INNER, then INNER will need not the same as the number of words in INNER, then INNER will need
reloading (with an in-out reload). */ reloading (with an in-out reload). */
return (output return output && complex_word_subreg_p (mode, inner);
&& GET_MODE_SIZE (mode) <= UNITS_PER_WORD
&& GET_MODE_SIZE (GET_MODE (inner)) > UNITS_PER_WORD
&& ((GET_MODE_SIZE (GET_MODE (inner)) / UNITS_PER_WORD)
!= REG_NREGS (inner)));
} }
/* Return nonzero if IN can be reloaded into REGNO with mode MODE without /* Return nonzero if IN can be reloaded into REGNO with mode MODE without
...@@ -1064,12 +1077,7 @@ push_reload (rtx in, rtx out, rtx *inloc, rtx *outloc, ...@@ -1064,12 +1077,7 @@ push_reload (rtx in, rtx out, rtx *inloc, rtx *outloc,
/* The case where out is nonzero /* The case where out is nonzero
is handled differently in the following statement. */ is handled differently in the following statement. */
&& (out == 0 || subreg_lowpart_p (in)) && (out == 0 || subreg_lowpart_p (in))
&& ((GET_MODE_SIZE (inmode) <= UNITS_PER_WORD && (complex_word_subreg_p (inmode, SUBREG_REG (in))
&& (GET_MODE_SIZE (GET_MODE (SUBREG_REG (in)))
> UNITS_PER_WORD)
&& ((GET_MODE_SIZE (GET_MODE (SUBREG_REG (in)))
/ UNITS_PER_WORD)
!= REG_NREGS (SUBREG_REG (in))))
|| !targetm.hard_regno_mode_ok (subreg_regno (in), inmode))) || !targetm.hard_regno_mode_ok (subreg_regno (in), inmode)))
|| (secondary_reload_class (1, rclass, inmode, in) != NO_REGS || (secondary_reload_class (1, rclass, inmode, in) != NO_REGS
&& (secondary_reload_class (1, rclass, GET_MODE (SUBREG_REG (in)), && (secondary_reload_class (1, rclass, GET_MODE (SUBREG_REG (in)),
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment