[PATCH] Use gen_lowpart_or_truncate in simplify_shift_const_1
Adam Nemet
anemet@caviumnetworks.com
Tue Mar 7 21:50:00 GMT 2006
This was uncovered by a MIPS64 patch that I am working on to let
backends turn explicit truncates into implicit ones. With the patch I
got an UNPREDICTABLE exception in gcc.c-torture/execute/simd-2.c on
the simulator. This exception occurs if a 32-bit mode operation is
performed on a register that has not been properly truncated.
The problem is in simplify_shift_const_1. It does this
transformation:
(ashift:SI (subreg:SI (lshiftrt:DI (reg:DI 436) 48)) 16)
-> (subreg:SI (ashift:DI (lshiftrt:DI (reg:DI 436) 48) 16)))
If truncation from DI to SI requires explicit truncation we cannot
just lift the subreg unconditionally here.
I am changing the call to gen_lowpart to gen_lowpart_or_truncate which
will only generate a SUBREG if the value is known have already been
truncated.
There are lot of other places where we use gen_lowpart which might not
be correct. Changing them to use gen_lowpart_or_truncate would hurt
performance at this point. I hope that after the above mentioned
patch this will not be as intrusive.
This patch was bootstrapped and tested on i686-pc-linux-gnu and tested
on mipsisa64-elf with and without the patch triggering the bug.
OK to install?
Adam
* combine.c (simplify_shift_const_1): Use gen_lowpart_or_truncate
instead of gen_lowpart.
Index: combine.c
===================================================================
--- combine.c (revision 111703)
+++ combine.c (working copy)
@@ -9199,7 +9199,7 @@ simplify_shift_const_1 (enum rtx_code co
GET_MODE_MASK (result_mode) >> orig_count);
/* Do the remainder of the processing in RESULT_MODE. */
- x = gen_lowpart (result_mode, x);
+ x = gen_lowpart_or_truncate (result_mode, x);
/* If COMPLEMENT_P is set, we have to complement X before doing the outer
operation. */
More information about the Gcc-patches
mailing list