Google ref b/8153611 Looks very similar to PR53816. Test: class A { virtual int String (); }; class F: public A { }; template < typename V > class G { V value; }; class D { template < int N > void Verify(const int (&p1)[N]) const { for (int iter; G < A > *x = 0;) { F& name = x->value; name.String (); } } }; ICE with g++ (GCC) 4.8.0 20130205 (experimental). g++ -c t.ii # ok g++ -c -std=c++11 t.ii t.ii: In member function ‘void D::Verify(const int (&)[N]) const’: t.ii:19:22: internal compiler error: tree check: expected field_decl, have identifier_node in fixed_type_or_null, at cp/class.c:6645 name.String (); ^ 0xc6159a tree_check_failed(tree_node const*, char const*, int, char const*, ...) ../../gcc/tree.c:8946 0x5cd853 tree_check ../../gcc/tree.h:3669 ...
Started with http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=193504
Any news on this bug? It's one of only a few P1 regressions left.
(In reply to comment #2) > Any news on this bug? It's one of only a few P1 regressions left. This bug triggers with --enable-checking on the constexpr stuff. I was looking at it yesterday, and tried to fix it in the same way than you fixed PR53816. It did work, but it caused a regression on constexpr-static10.C which I didn't manage to resolve yet. If I fail to find out what goes wrong this week-end, I will probably have to defer to someone more involved than me on the constexpr stuff. I didn't check if it was a regression wrt 4.7 with --enable-checking
I think the testcase is invalid Shouldn't the below line be diagnosed, even if it is in a template ? F& name = x->value; We fail to return early, and the compiler is confused because of this error.
reduced testcase: class A { virtual int String (); }; class F: public A { }; template < typename V > class G { V value; }; class D { template < int N > void Verify() { G<A>* x = 0; F& name = x->value; name.String(); } };
(In reply to comment #4) > I think the testcase is invalid Looks like you are right, and it's been over-reduced. > Shouldn't the below line be diagnosed, even if it is in a template ? > F& name = x->value; The error being that typeof(x->value) is A, not F, right? If so, this corrected test case still triggers ICE: class A { virtual int String (); }; class F: public A { }; template < typename V > class G { V value; }; class D { template < int N > void Verify() { G<F>* x = 0; F& name = x->value; name.String(); } };
(In reply to comment #6) > (In reply to comment #4) [...] > If so, this corrected test case still triggers ICE: Good point. Further reduced: struct A { virtual int String (); }; class F: public A { }; struct G { F value; }; class D { template <int> void Verify() { G x; F& name = x.value; name.String(); } }; I restarted the analysis from the beginning. My fix for c++/11750 was basically to restrict the cases where the unsafe front-end de-virtualization was done. It wouldn't help to refine that change because anyway, it would still be possible to find a testcase that shows the same ICE. My attempts to fix the problem on the constexpr side failed probably because it is correct. The problem is more related to the COMPONENT_REF 'G'. Probably because D::Verify is not instantiated yet, the field 'value' of G is still an IDENTIFIER_NODE instead of being a FIELD_DECL, which leads to a crash while calling DECL_FIELD_IS_BASE. Hence, I can only see two solutions: 1) make 'value' a FIELD_DECL before or during the fold_non_dependent_expr_sfinae call. Not sure it is simple. 2) check that the first operand of a COMPONENT_REF is actually a FIELD_DECL before calling DECL_FIELD_IS_BASE on it. Upcoming patch for the solution 2 on gcc-patch...
(In reply to comment #6) [...] > 2) check that the first operand of a COMPONENT_REF is actually a FIELD_DECL > before calling DECL_FIELD_IS_BASE on it. As a consequency, while processing fold_non_dependent_expr_sfinae, fixed_type_or_null returns NULL_TREE on 'x.value' the and build_vtbl_ref_1 has not chance to call unshare_expr. Jason, is that a big deal ?
Author: jason Date: Thu Feb 28 16:01:09 2013 New Revision: 196343 URL: http://gcc.gnu.org/viewcvs?root=gcc&view=rev&rev=196343 Log: PR c++/56243 * call.c (build_over_call): Avoid virtual lookup in a template. Added: trunk/gcc/testsuite/g++.dg/template/virtual4.C Modified: trunk/gcc/cp/ChangeLog trunk/gcc/cp/call.c
Fixed.