I am trying to understand the checkin by Jeff Law from about 11 years ago: r19204 | law | 1998-04-14 01:04:21 -0700 (Tue, 14 Apr 1998) | 4 lines * combine.c (simplify_rtx, case TRUNCATE): Respect value of TRULY_NOOP_TRUNCATION. Index: combine.c =================================================================== --- combine.c (revision 19018) +++ combine.c (revision 19204) @@ -3736,7 +3736,9 @@ simplify_rtx (x, op0_mode, last, in_dest if (GET_MODE_CLASS (mode) == MODE_PARTIAL_INT) break; - if (GET_MODE_BITSIZE (mode) <= HOST_BITS_PER_WIDE_INT) + if (GET_MODE_BITSIZE (mode) <= HOST_BITS_PER_WIDE_INT + && TRULY_NOOP_TRUNCATION (GET_MODE_BITSIZE (mode), + GET_MODE_BITSIZE (GET_MODE (XEXP (x, 0))))) SUBST (XEXP (x, 0), force_to_mode (XEXP (x, 0), GET_MODE (XEXP (x, 0)), GET_MODE_MASK (mode), NULL_RTX, 0));
This optimization simplifies the input to a truncate by only computing bits that won't be eliminated by the truncation. Normally these are the bits in the output mode mask. Note that the optimization does not change the truncate into a low-part subreg, which would pretty automatically warrant the TRULY_NOOP_TRUNCATION check. Specifically I am curious if this was prompted by MIPS (or SH) or maybe some other target that have a notion of truncate different from MIPS. force_to_mode was broken WRT truncate before my patch in 2006: http://gcc.gnu.org/ml/gcc-patches/2006-01/msg00553.html so maybe the Jeff's patch was just trying to avoid the call to force_to_mode. Anyhow, I don't think that the above transformation is illegal for MIPS64. When truncating to SI mode the bits outside the resulting SI mode will all be copies of the SI mode sign bit so their input values are obviously irrelevant. For QI and HI modes the representation requires the upper 32 bits in the 64-bit word to be copies of the 31st bit. The transformation might change the 31 bits so it can affect the the resulting bits in the 64-bit word. This however should have no visible effect. Operations on QI- and HI-mode values are performed in SI mode with proper extensions before the operation if bits outside the mode would affect the result. I also tried a few things after removing the above check. Boostrapping and regtesting on mips64octeon-linux was successful so was regtesting on mipsisa64r2-elf. The assembly output of gcc.c-torture/execute/*.c improved as: 13 files changed, 73 insertions(+), 99 deletions(-) The changes typically remove zero and sign-extensions before a subsequent truncation. Any further information on this subject would be very much appreciated. Adam