This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: tweak in push_template_decl_real
- To: brendan at cygnus dot com
- Subject: Re: tweak in push_template_decl_real
- From: Mark Mitchell <mark at markmitchell dot com>
- Date: Thu, 11 Jun 1998 23:21:30 -0700
- Cc: jason at cygnus dot com, egcs-patches at cygnus dot com
- References: <20963.897442383@lisa.cygnus.com>
- Reply-to: mark at markmitchell dot com
Here's a patch for the crash you found on:
struct outer {
template <class T> struct inner;
} o;
template <class T> struct outer::inner {};
Jason, OK?
--
Mark Mitchell mark@markmitchell.com
Mark Mitchell Consulting http://www.markmitchell.com
1998-06-11 Mark Mitchell <mark@markmitchell.com>
* pt.c (is_member_template_class): New function.
(push_template_decl_real): Use it.
Index: testsuite/g++.old-deja/g++.pt/memclass12.C
===================================================================
RCS file: memclass12.C
diff -N memclass12.C
*** /dev/null Mon Dec 31 20:00:00 1979
--- memclass12.C Thu Jun 11 23:15:54 1998
***************
*** 0 ****
--- 1,6 ----
+ // Build don't link:
+
+ struct outer {
+ template <class T> struct inner;
+ } o;
+ template <class T> struct outer::inner {};
Index: cp/pt.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/cp/pt.c,v
retrieving revision 1.153
diff -c -p -r1.153 pt.c
*** pt.c 1998/06/09 23:39:34 1.153
--- pt.c 1998/06/12 06:16:15
*************** static tree maybe_get_template_decl_from
*** 115,120 ****
--- 115,121 ----
static int check_cv_quals_for_unify PROTO((int, tree, tree));
static tree tsubst_template_arg_vector PROTO((tree, tree));
static void regenerate_decl_from_template PROTO((tree, tree));
+ static int is_member_template_class PROTO((tree));
/* Nonzero if ARGVEC contains multiple levels of template arguments. */
#define TMPL_ARGS_HAVE_MULTIPLE_LEVELS(NODE) \
*************** is_member_template (t)
*** 378,383 ****
--- 379,410 ----
return 0;
}
+ /* Returns non-zero iff T is a member template class. See
+ is_member_template for a description of what precisely constitutes
+ a member template. */
+
+ int
+ is_member_template_class (t)
+ tree t;
+ {
+ if (!DECL_CLASS_TEMPLATE_P (t))
+ /* Anything that isn't a class template, is certainly not a member
+ template. */
+ return 0;
+
+ if (!DECL_CONTEXT (t)
+ || !IS_AGGR_TYPE_CODE (TREE_CODE (DECL_CONTEXT (t))))
+ /* Anything whose context isn't a class type is surely not a
+ member template. */
+ return 0;
+
+ /* If there are more levels of template parameters than there are
+ template classes surrounding the declaration, then we have a
+ member template. */
+ return (list_length (DECL_TEMPLATE_PARMS (t)) >
+ template_class_depth (DECL_CONTEXT (t)));
+ }
+
/* Return a new template argument vector which contains all of ARGS
for all outer templates TMPL is contained in, but has as its
innermost set of arguments the EXTRA_ARGS. If UNBOUND_ONLY, we
*************** push_template_decl_real (decl, is_friend
*** 1784,1792 ****
else
tmpl = DECL_TI_TEMPLATE (decl);
! if (is_member_template (tmpl))
{
! if (DECL_TEMPLATE_INFO (decl) && DECL_TI_ARGS (decl)
&& DECL_TEMPLATE_SPECIALIZATION (decl))
{
tree new_tmpl;
--- 1811,1820 ----
else
tmpl = DECL_TI_TEMPLATE (decl);
! if (is_member_template (tmpl) || is_member_template_class (tmpl))
{
! if (DECL_FUNCTION_TEMPLATE_P (tmpl)
! && DECL_TEMPLATE_INFO (decl) && DECL_TI_ARGS (decl)
&& DECL_TEMPLATE_SPECIALIZATION (decl))
{
tree new_tmpl;
*************** push_template_decl_real (decl, is_friend
*** 1812,1818 ****
}
a = TREE_VEC_ELT (args, TREE_VEC_LENGTH (args) - 1);
! t = DECL_INNERMOST_TEMPLATE_PARMS (DECL_TI_TEMPLATE (decl));
if (TREE_VEC_LENGTH (t) != TREE_VEC_LENGTH (a))
{
cp_error ("got %d template parameters for `%#D'",
--- 1840,1846 ----
}
a = TREE_VEC_ELT (args, TREE_VEC_LENGTH (args) - 1);
! t = DECL_INNERMOST_TEMPLATE_PARMS (tmpl);
if (TREE_VEC_LENGTH (t) != TREE_VEC_LENGTH (a))
{
cp_error ("got %d template parameters for `%#D'",