On 29.07.2016 09:47, Segher Boessenkool wrote:
Hi Johann,
I tested a variant of your patch, building Linux for 32 different
(sub-)architectures; surprisingly (to me) there are no regressions
at all.
I am not so surprised because most backends don't make such an intense use of
hard-regs like the avr BE does.
Do you want to send it to gcc-patches?
https://gcc.gnu.org/ml/gcc-patches/2016-07/msg01921.html
There might still problems linger around if hard-regs are used:
Suppose we set the reg in DImode and then get_last_value is called for the same
reg in SImode. Using the DI value might be wrong, e.g. if it is used to
compute the sign (on little endian) or the number of sign bit copies.
Anyway, for now I am happy with the current solution. Many thanks for your
patient help.
Johann
Segher
diff --git a/gcc/combine.c b/gcc/combine.c
index 77e0d2b..750bf83 100644
--- a/gcc/combine.c
+++ b/gcc/combine.c
@@ -13240,6 +13240,12 @@ get_last_value (const_rtx x)
&& DF_INSN_LUID (rsp->last_set) >= subst_low_luid)
return 0;
+ /* If fewer bits were set than what we are asked for now, we cannot use
+ the value. */
+ if (GET_MODE_PRECISION (rsp->last_set_mode)
+ < GET_MODE_PRECISION (GET_MODE (x)))
+ return 0;
+
/* If the value has all its registers valid, return it. */
if (get_last_value_validate (&value, rsp->last_set, rsp->last_set_label, 0))
return value;