Hi All,
This patch fixes an ICE that occurs when attempting to fold nested INDIRECT_REF
trees that have conversions in between the indirect references. For example:
constexpr unsigned long b = *((ul_ptr)(*((ul_ptr)0x0)));
What happens is that 'cxx_fold_indirect_ref' gets the top indirect reference,
strips out all the conversions ending up with the nested indirect reference,
and then asserts that the type is a pointer type, which (obviously) it isn't.
This patch fixes the problem by exiting the fold for non-pointer sub-trees
instead of doing the assert. 'fold_indirect_ref_1' already does things this
way.
Tested on x86_64 GNU/Linux. OK?
Also, This fixes the problem on trunk, but I have reproduced the issue back to
the 4.6 branch as well. On the 4.6 branch I think it is OK to just remove the
'gcc_assert (POINTER_TYPE_P (subtype))' assert. I tested this and saw no
regressions.
P.S. If it is OK can some please commit for me? I don't have write access.
--
Meador Inge
CodeSourcery / Mentor Embedded
http://www.mentor.com/embedded-software
cp/
2012-03-26 Meador Inge <mead...@codesourcery.com>
PR c++/52672
* gcc/cp/semantics.c (cxx_fold_indirect_ref): Don't attempt to fold
stripped child trees that are not pointer types.
testsuite/
2012-03-26 Meador Inge <mead...@codesourcery.com>
PR c++/52672
* g++.dg/cpp0x/constexpr-52672.C: New testcase.
Index: gcc/testsuite/g++.dg/cpp0x/constexpr-52672.C
===================================================================
--- gcc/testsuite/g++.dg/cpp0x/constexpr-52672.C (revision 0)
+++ gcc/testsuite/g++.dg/cpp0x/constexpr-52672.C (revision 0)
@@ -0,0 +1,8 @@
+// PR c++/52672
+// { dg-do compile }
+// { dg-options "-std=c++11" }
+
+typedef unsigned long * ul_ptr;
+constexpr unsigned long a = *((ul_ptr)0x0); // { dg-error "" }
+constexpr unsigned long b = *((ul_ptr)(*((ul_ptr)0x0))); // { dg-error "" }
+constexpr unsigned long c = *((ul_ptr)*((ul_ptr)(*((ul_ptr)0x0)))); // { dg-error "" }
Index: gcc/cp/semantics.c
===================================================================
--- gcc/cp/semantics.c (revision 185750)
+++ gcc/cp/semantics.c (working copy)
@@ -7202,7 +7202,8 @@ cxx_fold_indirect_ref (location_t loc, tree type,
sub = op0;
STRIP_NOPS (sub);
subtype = TREE_TYPE (sub);
- gcc_assert (POINTER_TYPE_P (subtype));
+ if (!POINTER_TYPE_P (subtype))
+ return NULL_TREE;
if (TREE_CODE (sub) == ADDR_EXPR)
{