pt.c (tsubst_pack_expansion): Re-use ARGUMENT_PACK_SELECTs.
authorJason Merrill <jason@redhat.com>
Mon, 3 Oct 2011 04:32:35 +0000 (00:32 -0400)
committerJason Merrill <jason@gcc.gnu.org>
Mon, 3 Oct 2011 04:32:35 +0000 (00:32 -0400)
* pt.c (tsubst_pack_expansion): Re-use ARGUMENT_PACK_SELECTs.
Change unsubstituted_packs to bool.

From-SVN: r179444

gcc/cp/ChangeLog
gcc/cp/pt.c

index c34954984af75de4f4c5717381df5b0acd554829..c8ca7c5f85a57831118d4df3b5e5e034842a7b58 100644 (file)
@@ -1,5 +1,8 @@
 2011-10-02  Jason Merrill  <jason@redhat.com>
 
+       * pt.c (tsubst_pack_expansion): Re-use ARGUMENT_PACK_SELECTs.
+       Change unsubstituted_packs to bool.
+
        * parser.c (cp_parser_range_for): Don't try to deduce from {}
        in a template.
 
index 015ee3777070cb6b65f3a7e07c59bbc44a4fd0a2..051c89a7eff64b608ea0f805ed7d50f2349cf770 100644 (file)
@@ -9102,7 +9102,8 @@ tsubst_pack_expansion (tree t, tree args, tsubst_flags_t complain,
                       tree in_decl)
 {
   tree pattern;
-  tree pack, packs = NULL_TREE, unsubstituted_packs = NULL_TREE;
+  tree pack, packs = NULL_TREE;
+  bool unsubstituted_packs = false;
   int i, len = -1;
   tree result;
   htab_t saved_local_specializations = NULL;
@@ -9203,10 +9204,11 @@ tsubst_pack_expansion (tree t, tree args, tsubst_flags_t complain,
           TREE_TYPE (packs) = orig_arg;
         }
       else
-        /* We can't substitute for this parameter pack.  */
-        unsubstituted_packs = tree_cons (TREE_PURPOSE (pack),
-                                         TREE_VALUE (pack),
-                                         unsubstituted_packs);
+       {
+         /* We can't substitute for this parameter pack.  */
+         unsubstituted_packs = true;
+         break;
+       }
     }
 
   /* We cannot expand this expansion expression, because we don't have
@@ -9252,33 +9254,38 @@ tsubst_pack_expansion (tree t, tree args, tsubst_flags_t complain,
       for (pack = packs; pack; pack = TREE_CHAIN (pack))
         {
           tree parm = TREE_PURPOSE (pack);
+         tree arg;
 
+         /* Select the Ith argument from the pack.  */
           if (TREE_CODE (parm) == PARM_DECL)
             {
-             /* Select the Ith argument from the pack.  */
-             tree arg = make_node (ARGUMENT_PACK_SELECT);
-             ARGUMENT_PACK_SELECT_FROM_PACK (arg) = TREE_VALUE (pack);
-             ARGUMENT_PACK_SELECT_INDEX (arg) = i;
-              mark_used (parm);
-              register_local_specialization (arg, parm);
+             if (i == 0)
+               {
+                 arg = make_node (ARGUMENT_PACK_SELECT);
+                 ARGUMENT_PACK_SELECT_FROM_PACK (arg) = TREE_VALUE (pack);
+                 mark_used (parm);
+                 register_local_specialization (arg, parm);
+               }
+             else
+               arg = retrieve_local_specialization (parm);
             }
           else
             {
-              tree value = parm;
               int idx, level;
               template_parm_level_and_index (parm, &level, &idx);
-              
-             if (i < len) 
+
+             if (i == 0)
                {
-                 /* Select the Ith argument from the pack. */
-                 value = make_node (ARGUMENT_PACK_SELECT);
-                 ARGUMENT_PACK_SELECT_FROM_PACK (value) = TREE_VALUE (pack);
-                 ARGUMENT_PACK_SELECT_INDEX (value) = i;
+                 arg = make_node (ARGUMENT_PACK_SELECT);
+                 ARGUMENT_PACK_SELECT_FROM_PACK (arg) = TREE_VALUE (pack);
+                 /* Update the corresponding argument.  */
+                 TMPL_ARG (args, level, idx) = arg;
                }
-
-              /* Update the corresponding argument.  */
-              TMPL_ARG (args, level, idx) = value;
+             else
+               /* Re-use the ARGUMENT_PACK_SELECT.  */
+               arg = TMPL_ARG (args, level, idx);
             }
+         ARGUMENT_PACK_SELECT_INDEX (arg) = i;
         }
 
       /* Substitute into the PATTERN with the altered arguments.  */