OSDN Git Service

* pt.c (is_member_template_class): New function.
authormmitchel <mmitchel@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 11 Jun 1998 23:53:24 +0000 (23:53 +0000)
committermmitchel <mmitchel@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 11 Jun 1998 23:53:24 +0000 (23:53 +0000)
(push_template_decl_real): Use it.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@20435 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/cp/ChangeLog
gcc/cp/pt.c
gcc/testsuite/g++.old-deja/g++.pt/memclass12.C [new file with mode: 0644]

index d02ae09..5539b4c 100644 (file)
@@ -1,3 +1,8 @@
+1998-06-11  Mark Mitchell  <mark@markmitchell.com>
+
+       * pt.c (is_member_template_class): New function.
+       (push_template_decl_real): Use it.
+
 1998-06-11  Benjamin Kosnik  <bkoz@elmo.cygnus.com>
 
        * friend.c (do_friend): Add support for nested classes using
index 2a06dab..537361e 100644 (file)
@@ -115,6 +115,7 @@ static tree maybe_get_template_decl_from_type_decl PROTO((tree));
 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)           \
@@ -378,6 +379,31 @@ is_member_template (t)
   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_CLASS_SCOPE_P (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
@@ -1784,9 +1810,10 @@ push_template_decl_real (decl, is_friend)
       else
        tmpl = DECL_TI_TEMPLATE (decl);
       
-      if (is_member_template (tmpl))
+      if (is_member_template (tmpl) || is_member_template_class (tmpl))
        {
-         if (DECL_TEMPLATE_INFO (decl) && DECL_TI_ARGS (decl) 
+         if (DECL_FUNCTION_TEMPLATE_P (tmpl)
+             && DECL_TEMPLATE_INFO (decl) && DECL_TI_ARGS (decl) 
              && DECL_TEMPLATE_SPECIALIZATION (decl))
            {
              tree new_tmpl;
@@ -1812,7 +1839,7 @@ push_template_decl_real (decl, is_friend)
            }
          
          a = TREE_VEC_ELT (args, TREE_VEC_LENGTH (args) - 1);
-         t = DECL_INNERMOST_TEMPLATE_PARMS (DECL_TI_TEMPLATE (decl));
+         t = DECL_INNERMOST_TEMPLATE_PARMS (tmpl);
          if (TREE_VEC_LENGTH (t) != TREE_VEC_LENGTH (a))
            {
              cp_error ("got %d template parameters for `%#D'",
diff --git a/gcc/testsuite/g++.old-deja/g++.pt/memclass12.C b/gcc/testsuite/g++.old-deja/g++.pt/memclass12.C
new file mode 100644 (file)
index 0000000..f4d0354
--- /dev/null
@@ -0,0 +1,6 @@
+// Build don't link:
+
+struct outer {
+  template <class T> struct inner;
+} o;
+template <class T> struct outer::inner {};