This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[3.4 PATCH] Fix ICE in store_field
- From: Ulrich Weigand <uweigand at de dot ibm dot com>
- To: gcc-patches at gcc dot gnu dot org
- Date: Thu, 27 Oct 2005 16:49:42 +0200 (CEST)
- Subject: [3.4 PATCH] Fix ICE in store_field
Hello,
we've noticed a problem in the old 3.x increment queue handling.
The following code ICEs on s390 (and presumably all platforms
where CONST_INTs are not accepted by CONSTANT_ADDRESS_P):
struct test { unsigned int x; };
return ++((struct test *) 0)->x;
This function, while obviously invoking undefined behaviour when
executed, is still valid C code as far as I can see, and shouldn't
cause an ICE. (This is extracted from real-world source code,
resulting from debug assertion-checking macros -- in the actual
scenario, it is guaranteed that the code can never be executed ...)
The reason for the ICE is that store_field thinks it needs to copy
the pre-increment address (i.e. const_int 0) to a register, and
tries to do so with copy_to_reg. This ICEs because the mode is
VOIDmode. The following patch fixes this by using the function
copy_to_addr_reg instead.
Note that on GCC 4.x this problem no longer exists as the whole
increment queue handling was removed.
Bootstrapped/regtested on s390-ibm-linux and s390x-ibm-linux
on the 3.4 branch. OK for the branch?
Bye,
Ulrich
ChangeLog:
* expr.c (store_field): Use copy_to_addr_reg to copy addresses.
testsuite/ChangeLog:
* gcc.dg/20051027-1.c: New test.
Index: gcc/expr.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/expr.c,v
retrieving revision 1.615.4.21
diff -c -p -r1.615.4.21 expr.c
*** gcc/expr.c 11 May 2005 21:19:48 -0000 1.615.4.21
--- gcc/expr.c 27 Oct 2005 12:46:20 -0000
*************** store_field (rtx target, HOST_WIDE_INT b
*** 5416,5422 ****
&& GET_CODE (XEXP (addr, 1)) == CONST_INT
&& (XEXP (addr, 0) == virtual_incoming_args_rtx
|| XEXP (addr, 0) == virtual_stack_vars_rtx)))
! to_rtx = replace_equiv_address (to_rtx, copy_to_reg (addr));
/* Now build a reference to just the desired component. */
--- 5416,5422 ----
&& GET_CODE (XEXP (addr, 1)) == CONST_INT
&& (XEXP (addr, 0) == virtual_incoming_args_rtx
|| XEXP (addr, 0) == virtual_stack_vars_rtx)))
! to_rtx = replace_equiv_address (to_rtx, copy_addr_to_reg (addr));
/* Now build a reference to just the desired component. */
*** /dev/null Tue Oct 26 21:09:21 2004
--- gcc/testsuite/gcc.dg/20051027-1.c Thu Oct 27 14:42:58 2005
***************
*** 0 ****
--- 1,11 ----
+ /* This used to ICE due to a bug in store_field. */
+
+ /* { dg-do compile } */
+
+
+ int test (void)
+ {
+ struct test { unsigned int x; };
+ return ++((struct test *) 0)->x;
+ }
+
--
Dr. Ulrich Weigand
Linux on zSeries Development
Ulrich.Weigand@de.ibm.com