re PR debug/66653 (ice in gen_type_die_with_usage, at dwarf2out.c:20876)
[gcc.git] / gcc / cp / pt.c
index 14b5bfb190a498292ac9015e1e74ba20dca5256a..6b73d49ce29c3d69db6485a6c6064ca9e6a1c9c5 100644 (file)
@@ -1,5 +1,5 @@
 /* Handle parameterized types (templates) for GNU -*- C++ -*-.
 /* Handle parameterized types (templates) for GNU -*- C++ -*-.
-   Copyright (C) 1992-2014 Free Software Foundation, Inc.
+   Copyright (C) 1992-2015 Free Software Foundation, Inc.
    Written by Ken Raeburn (raeburn@cygnus.com) while at Watchmaker Computing.
    Rewritten by Jason Merrill (jason@cygnus.com).
 
    Written by Ken Raeburn (raeburn@cygnus.com) while at Watchmaker Computing.
    Rewritten by Jason Merrill (jason@cygnus.com).
 
@@ -28,6 +28,8 @@ along with GCC; see the file COPYING3.  If not see
 #include "system.h"
 #include "coretypes.h"
 #include "tm.h"
 #include "system.h"
 #include "coretypes.h"
 #include "tm.h"
+#include "alias.h"
+#include "symtab.h"
 #include "tree.h"
 #include "stringpool.h"
 #include "varasm.h"
 #include "tree.h"
 #include "stringpool.h"
 #include "varasm.h"
@@ -80,18 +82,22 @@ static tree cur_stmt_expr;
 /* True if we've recursed into fn_type_unification too many times.  */
 static bool excessive_deduction_depth;
 
 /* True if we've recursed into fn_type_unification too many times.  */
 static bool excessive_deduction_depth;
 
-typedef struct GTY(()) spec_entry
+struct GTY((for_user)) spec_entry
 {
   tree tmpl;
   tree args;
   tree spec;
 {
   tree tmpl;
   tree args;
   tree spec;
-} spec_entry;
+};
+
+struct spec_hasher : ggc_ptr_hash<spec_entry>
+{
+  static hashval_t hash (spec_entry *);
+  static bool equal (spec_entry *, spec_entry *);
+};
 
 
-static GTY ((param_is (spec_entry)))
-  htab_t decl_specializations;
+static GTY (()) hash_table<spec_hasher> *decl_specializations;
 
 
-static GTY ((param_is (spec_entry)))
-  htab_t type_specializations;
+static GTY (()) hash_table<spec_hasher> *type_specializations;
 
 /* Contains canonical template parameter types. The vector is indexed by
    the TEMPLATE_TYPE_IDX of the template parameter. Each element is a
 
 /* Contains canonical template parameter types. The vector is indexed by
    the TEMPLATE_TYPE_IDX of the template parameter. Each element is a
@@ -125,7 +131,7 @@ static int unify (tree, tree, tree, tree, int, bool);
 static void add_pending_template (tree);
 static tree reopen_tinst_level (struct tinst_level *);
 static tree tsubst_initializer_list (tree, tree);
 static void add_pending_template (tree);
 static tree reopen_tinst_level (struct tinst_level *);
 static tree tsubst_initializer_list (tree, tree);
-static tree get_class_bindings (tree, tree, tree, tree);
+static tree get_partial_spec_bindings (tree, tree, tree, tree);
 static tree coerce_template_parms (tree, tree, tree, tsubst_flags_t,
                                   bool, bool);
 static tree coerce_innermost_template_parms (tree, tree, tree, tsubst_flags_t,
 static tree coerce_template_parms (tree, tree, tree, tsubst_flags_t,
                                   bool, bool);
 static tree coerce_innermost_template_parms (tree, tree, tree, tsubst_flags_t,
@@ -153,7 +159,6 @@ static bool inline_needs_template_parms (tree, bool);
 static void push_inline_template_parms_recursive (tree, int);
 static tree retrieve_local_specialization (tree);
 static void register_local_specialization (tree, tree);
 static void push_inline_template_parms_recursive (tree, int);
 static tree retrieve_local_specialization (tree);
 static void register_local_specialization (tree, tree);
-static hashval_t hash_specialization (const void *p);
 static tree reduce_template_parm_level (tree, tree, int, tree, tsubst_flags_t);
 static int mark_template_parm (tree, void *);
 static int template_parm_this_level_p (tree, void *);
 static tree reduce_template_parm_level (tree, tree, int, tree, tsubst_flags_t);
 static int mark_template_parm (tree, void *);
 static int template_parm_this_level_p (tree, void *);
@@ -170,7 +175,7 @@ static tree tsubst_template_arg (tree, tree, tsubst_flags_t, tree);
 static tree tsubst_template_args (tree, tree, tsubst_flags_t, tree);
 static tree tsubst_template_parms (tree, tree, tsubst_flags_t);
 static void regenerate_decl_from_template (tree, tree);
 static tree tsubst_template_args (tree, tree, tsubst_flags_t, tree);
 static tree tsubst_template_parms (tree, tree, tsubst_flags_t);
 static void regenerate_decl_from_template (tree, tree);
-static tree most_specialized_class (tree, tsubst_flags_t);
+static tree most_specialized_partial_spec (tree, tsubst_flags_t);
 static tree tsubst_aggr_type (tree, tree, tsubst_flags_t, tree, int);
 static tree tsubst_arg_types (tree, tree, tree, tsubst_flags_t, tree);
 static tree tsubst_function_type (tree, tree, tsubst_flags_t, tree);
 static tree tsubst_aggr_type (tree, tree, tsubst_flags_t, tree, int);
 static tree tsubst_arg_types (tree, tree, tree, tsubst_flags_t, tree);
 static tree tsubst_function_type (tree, tree, tsubst_flags_t, tree);
@@ -205,6 +210,7 @@ static tree template_parm_to_arg (tree t);
 static tree current_template_args (void);
 static tree tsubst_template_parm (tree, tree, tsubst_flags_t);
 static tree instantiate_alias_template (tree, tree, tsubst_flags_t);
 static tree current_template_args (void);
 static tree tsubst_template_parm (tree, tree, tsubst_flags_t);
 static tree instantiate_alias_template (tree, tree, tsubst_flags_t);
+static bool complex_alias_template_p (const_tree tmpl);
 
 /* Make the current scope suitable for access checking when we are
    processing T.  T can be FUNCTION_DECL for instantiated function
 
 /* Make the current scope suitable for access checking when we are
    processing T.  T can be FUNCTION_DECL for instantiated function
@@ -931,18 +937,18 @@ maybe_process_partial_specialization (tree type)
                     new member specialization template.  */
                  spec_entry elt;
                  spec_entry *entry;
                     new member specialization template.  */
                  spec_entry elt;
                  spec_entry *entry;
-                 void **slot;
 
                  elt.tmpl = most_general_template (tmpl);
                  elt.args = CLASSTYPE_TI_ARGS (inst);
                  elt.spec = inst;
 
 
                  elt.tmpl = most_general_template (tmpl);
                  elt.args = CLASSTYPE_TI_ARGS (inst);
                  elt.spec = inst;
 
-                 htab_remove_elt (type_specializations, &elt);
+                 type_specializations->remove_elt (&elt);
 
                  elt.tmpl = tmpl;
                  elt.args = INNERMOST_TEMPLATE_ARGS (elt.args);
 
 
                  elt.tmpl = tmpl;
                  elt.args = INNERMOST_TEMPLATE_ARGS (elt.args);
 
-                 slot = htab_find_slot (type_specializations, &elt, INSERT);
+                 spec_entry **slot
+                   = type_specializations->find_slot (&elt, INSERT);
                  entry = ggc_alloc<spec_entry> ();
                  *entry = elt;
                  *slot = entry;
                  entry = ggc_alloc<spec_entry> ();
                  *entry = elt;
                  *slot = entry;
@@ -1013,6 +1019,35 @@ optimize_specialization_lookup_p (tree tmpl)
          && !DECL_FRIEND_P (DECL_TEMPLATE_RESULT (tmpl)));
 }
 
          && !DECL_FRIEND_P (DECL_TEMPLATE_RESULT (tmpl)));
 }
 
+/* Make sure ARGS doesn't use any inappropriate typedefs; we should have
+   gone through coerce_template_parms by now.  */
+
+static void
+check_unstripped_args (tree args ATTRIBUTE_UNUSED)
+{
+#ifdef ENABLE_CHECKING
+  ++processing_template_decl;
+  if (!any_dependent_template_arguments_p (args))
+    {
+      tree inner = INNERMOST_TEMPLATE_ARGS (args);
+      for (int i = 0; i < TREE_VEC_LENGTH (inner); ++i)
+       {
+         tree arg = TREE_VEC_ELT (inner, i);
+         if (TREE_CODE (arg) == TEMPLATE_DECL)
+           /* OK */;
+         else if (TYPE_P (arg))
+           gcc_assert (strip_typedefs (arg, NULL) == arg);
+         else if (strip_typedefs (TREE_TYPE (arg), NULL) != TREE_TYPE (arg))
+           /* Allow typedefs on the type of a non-type argument, since a
+              parameter can have them.  */;
+         else
+           gcc_assert (strip_typedefs_expr (arg, NULL) == arg);
+       }
+    }
+  --processing_template_decl;
+#endif
+}
+
 /* Retrieve the specialization (in the sense of [temp.spec] - a
    specialization is either an instantiation or an explicit
    specialization) of TMPL for the given template ARGS.  If there is
 /* Retrieve the specialization (in the sense of [temp.spec] - a
    specialization is either an instantiation or an explicit
    specialization) of TMPL for the given template ARGS.  If there is
@@ -1046,6 +1081,8 @@ retrieve_specialization (tree tmpl, tree args, hashval_t hash)
                  ? TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl))
                  : template_class_depth (DECL_CONTEXT (tmpl))));
 
                  ? TMPL_PARMS_DEPTH (DECL_TEMPLATE_PARMS (tmpl))
                  : template_class_depth (DECL_CONTEXT (tmpl))));
 
+  check_unstripped_args (args);
+
   if (optimize_specialization_lookup_p (tmpl))
     {
       tree class_template;
   if (optimize_specialization_lookup_p (tmpl))
     {
       tree class_template;
@@ -1085,7 +1122,7 @@ retrieve_specialization (tree tmpl, tree args, hashval_t hash)
     {
       spec_entry *found;
       spec_entry elt;
     {
       spec_entry *found;
       spec_entry elt;
-      htab_t specializations;
+      hash_table<spec_hasher> *specializations;
 
       elt.tmpl = tmpl;
       elt.args = args;
 
       elt.tmpl = tmpl;
       elt.args = args;
@@ -1097,8 +1134,8 @@ retrieve_specialization (tree tmpl, tree args, hashval_t hash)
        specializations = decl_specializations;
 
       if (hash == 0)
        specializations = decl_specializations;
 
       if (hash == 0)
-       hash = hash_specialization (&elt);
-      found = (spec_entry *) htab_find_with_hash (specializations, &elt, hash);
+       hash = spec_hasher::hash (&elt);
+      found = specializations->find_with_hash (&elt, hash);
       if (found)
        return found->spec;
     }
       if (found)
        return found->spec;
     }
@@ -1343,7 +1380,7 @@ register_specialization (tree spec, tree tmpl, tree args, bool is_friend,
                         hashval_t hash)
 {
   tree fn;
                         hashval_t hash)
 {
   tree fn;
-  void **slot = NULL;
+  spec_entry **slot = NULL;
   spec_entry elt;
 
   gcc_assert ((TREE_CODE (tmpl) == TEMPLATE_DECL && DECL_P (spec))
   spec_entry elt;
 
   gcc_assert ((TREE_CODE (tmpl) == TEMPLATE_DECL && DECL_P (spec))
@@ -1376,10 +1413,10 @@ register_specialization (tree spec, tree tmpl, tree args, bool is_friend,
       elt.spec = spec;
 
       if (hash == 0)
       elt.spec = spec;
 
       if (hash == 0)
-       hash = hash_specialization (&elt);
+       hash = spec_hasher::hash (&elt);
 
       slot =
 
       slot =
-       htab_find_slot_with_hash (decl_specializations, &elt, hash, INSERT);
+       decl_specializations->find_slot_with_hash (&elt, hash, INSERT);
       if (*slot)
        fn = ((spec_entry *) *slot)->spec;
       else
       if (*slot)
        fn = ((spec_entry *) *slot)->spec;
       else
@@ -1482,12 +1519,17 @@ register_specialization (tree spec, tree tmpl, tree args, bool is_friend,
       gcc_assert (tmpl && args && spec);
       *entry = elt;
       *slot = entry;
       gcc_assert (tmpl && args && spec);
       *entry = elt;
       *slot = entry;
-      if (TREE_CODE (spec) == FUNCTION_DECL && DECL_NAMESPACE_SCOPE_P (spec)
-         && PRIMARY_TEMPLATE_P (tmpl)
-         && DECL_SAVED_TREE (DECL_TEMPLATE_RESULT (tmpl)) == NULL_TREE)
-       /* TMPL is a forward declaration of a template function; keep a list
+      if ((TREE_CODE (spec) == FUNCTION_DECL && DECL_NAMESPACE_SCOPE_P (spec)
+          && PRIMARY_TEMPLATE_P (tmpl)
+          && DECL_SAVED_TREE (DECL_TEMPLATE_RESULT (tmpl)) == NULL_TREE)
+         || variable_template_p (tmpl))
+       /* If TMPL is a forward declaration of a template function, keep a list
           of all specializations in case we need to reassign them to a friend
           of all specializations in case we need to reassign them to a friend
-          template later in tsubst_friend_function.  */
+          template later in tsubst_friend_function.
+
+          Also keep a list of all variable template instantiations so that
+          process_partial_specialization can check whether a later partial
+          specialization would have used it.  */
        DECL_TEMPLATE_INSTANTIATIONS (tmpl)
          = tree_cons (args, spec, DECL_TEMPLATE_INSTANTIATIONS (tmpl));
     }
        DECL_TEMPLATE_INSTANTIATIONS (tmpl)
          = tree_cons (args, spec, DECL_TEMPLATE_INSTANTIATIONS (tmpl));
     }
@@ -1500,11 +1542,9 @@ register_specialization (tree spec, tree tmpl, tree args, bool is_friend,
 
 int comparing_specializations;
 
 
 int comparing_specializations;
 
-static int
-eq_specializations (const void *p1, const void *p2)
+bool
+spec_hasher::equal (spec_entry *e1, spec_entry *e2)
 {
 {
-  const spec_entry *e1 = (const spec_entry *)p1;
-  const spec_entry *e2 = (const spec_entry *)p2;
   int equal;
 
   ++comparing_specializations;
   int equal;
 
   ++comparing_specializations;
@@ -1527,10 +1567,9 @@ hash_tmpl_and_args (tree tmpl, tree args)
 /* Returns a hash for a spec_entry node based on the TMPL and ARGS members,
    ignoring SPEC.  */
 
 /* Returns a hash for a spec_entry node based on the TMPL and ARGS members,
    ignoring SPEC.  */
 
-static hashval_t
-hash_specialization (const void *p)
+hashval_t
+spec_hasher::hash (spec_entry *e)
 {
 {
-  const spec_entry *e = (const spec_entry *)p;
   return hash_tmpl_and_args (e->tmpl, e->args);
 }
 
   return hash_tmpl_and_args (e->tmpl, e->args);
 }
 
@@ -1598,6 +1637,7 @@ iterative_hash_template_arg (tree arg, hashval_t val)
     case CONSTRUCTOR:
       {
        tree field, value;
     case CONSTRUCTOR:
       {
        tree field, value;
+       iterative_hash_template_arg (TREE_TYPE (arg), val);
        FOR_EACH_CONSTRUCTOR_ELT (CONSTRUCTOR_ELTS (arg), i, field, value)
          {
            val = iterative_hash_template_arg (field, val);
        FOR_EACH_CONSTRUCTOR_ELT (CONSTRUCTOR_ELTS (arg), i, field, value)
          {
            val = iterative_hash_template_arg (field, val);
@@ -1668,6 +1708,18 @@ iterative_hash_template_arg (tree arg, hashval_t val)
   switch (tclass)
     {
     case tcc_type:
   switch (tclass)
     {
     case tcc_type:
+      if (alias_template_specialization_p (arg))
+       {
+         // We want an alias specialization that survived strip_typedefs
+         // to hash differently from its TYPE_CANONICAL, to avoid hash
+         // collisions that compare as different in template_args_equal.
+         // These could be dependent specializations that strip_typedefs
+         // left alone, or untouched specializations because
+         // coerce_template_parms returns the unconverted template
+         // arguments if it sees incomplete argument packs.
+         tree ti = TYPE_TEMPLATE_INFO (arg);
+         return hash_tmpl_and_args (TI_TEMPLATE (ti), TI_ARGS (ti));
+       }
       if (TYPE_CANONICAL (arg))
        return iterative_hash_object (TYPE_HASH (TYPE_CANONICAL (arg)),
                                      val);
       if (TYPE_CANONICAL (arg))
        return iterative_hash_object (TYPE_HASH (TYPE_CANONICAL (arg)),
                                      val);
@@ -1709,7 +1761,7 @@ reregister_specialization (tree spec, tree tinfo, tree new_spec)
   elt.args = TI_ARGS (tinfo);
   elt.spec = NULL_TREE;
 
   elt.args = TI_ARGS (tinfo);
   elt.spec = NULL_TREE;
 
-  entry = (spec_entry *) htab_find (decl_specializations, &elt);
+  entry = decl_specializations->find (&elt);
   if (entry != NULL)
     {
       gcc_assert (entry->spec == spec || entry->spec == new_spec);
   if (entry != NULL)
     {
       gcc_assert (entry->spec == spec || entry->spec == new_spec);
@@ -1892,7 +1944,13 @@ determine_specialization (tree template_id,
     ++header_count;
 
   if (variable_template_p (fns))
     ++header_count;
 
   if (variable_template_p (fns))
-    templates = tree_cons (explicit_targs, fns, templates);
+    {
+      tree parms = INNERMOST_TEMPLATE_PARMS (DECL_TEMPLATE_PARMS (fns));
+      targs = coerce_template_parms (parms, explicit_targs, fns,
+                                    tf_warning_or_error,
+                                    /*req_all*/true, /*use_defarg*/true);
+      templates = tree_cons (targs, fns, templates);
+    }
   else for (; fns; fns = OVL_NEXT (fns))
     {
       tree fn = OVL_CURRENT (fns);
   else for (; fns; fns = OVL_NEXT (fns))
     {
       tree fn = OVL_CURRENT (fns);
@@ -2308,12 +2366,13 @@ check_template_variable (tree decl)
 {
   tree ctx = CP_DECL_CONTEXT (decl);
   int wanted = num_template_headers_for_class (ctx);
 {
   tree ctx = CP_DECL_CONTEXT (decl);
   int wanted = num_template_headers_for_class (ctx);
-  if (!TYPE_P (ctx) || !CLASSTYPE_TEMPLATE_INFO (ctx))
+  if (DECL_LANG_SPECIFIC (decl) && DECL_TEMPLATE_INFO (decl)
+      && PRIMARY_TEMPLATE_P (DECL_TI_TEMPLATE (decl)))
     {
     {
-      if (cxx_dialect < cxx1y)
+      if (cxx_dialect < cxx14)
         pedwarn (DECL_SOURCE_LOCATION (decl), 0,
                  "variable templates only available with "
         pedwarn (DECL_SOURCE_LOCATION (decl), 0,
                  "variable templates only available with "
-                 "-std=c++1y or -std=gnu++1y");
+                 "-std=c++14 or -std=gnu++14");
 
       // Namespace-scope variable templates should have a template header.
       ++wanted;
 
       // Namespace-scope variable templates should have a template header.
       ++wanted;
@@ -2323,7 +2382,8 @@ check_template_variable (tree decl)
       bool warned = pedwarn (DECL_SOURCE_LOCATION (decl), 0,
                             "too many template headers for %D (should be %d)",
                             decl, wanted);
       bool warned = pedwarn (DECL_SOURCE_LOCATION (decl), 0,
                             "too many template headers for %D (should be %d)",
                             decl, wanted);
-      if (warned && CLASSTYPE_TEMPLATE_SPECIALIZATION (ctx))
+      if (warned && CLASS_TYPE_P (ctx)
+         && CLASSTYPE_TEMPLATE_SPECIALIZATION (ctx))
        inform (DECL_SOURCE_LOCATION (decl),
                "members of an explicitly specialized class are defined "
                "without a template header");
        inform (DECL_SOURCE_LOCATION (decl),
                "members of an explicitly specialized class are defined "
                "without a template header");
@@ -2395,7 +2455,7 @@ check_explicit_specialization (tree declarator,
   switch (tsk)
     {
     case tsk_none:
   switch (tsk)
     {
     case tsk_none:
-      if (processing_specialization)
+      if (processing_specialization && !VAR_P (decl))
        {
          specialization = 1;
          SET_DECL_TEMPLATE_SPECIALIZATION (decl);
        {
          specialization = 1;
          SET_DECL_TEMPLATE_SPECIALIZATION (decl);
@@ -2451,11 +2511,9 @@ check_explicit_specialization (tree declarator,
       /* Fall through.  */
     case tsk_expl_spec:
       if (VAR_P (decl) && TREE_CODE (declarator) != TEMPLATE_ID_EXPR)
       /* Fall through.  */
     case tsk_expl_spec:
       if (VAR_P (decl) && TREE_CODE (declarator) != TEMPLATE_ID_EXPR)
-        {
-           // In cases like template<> constexpr bool v = true;
-           error ("%qD is not a template variable", dname);
-           break;
-        }
+       /* In cases like template<> constexpr bool v = true;
+          We'll give an error in check_template_variable.  */
+       break;
 
       SET_DECL_TEMPLATE_SPECIALIZATION (decl);
       if (ctype)
 
       SET_DECL_TEMPLATE_SPECIALIZATION (decl);
       if (ctype)
@@ -2470,13 +2528,24 @@ check_explicit_specialization (tree declarator,
          /* This case handles bogus declarations like template <>
             template <class T> void f<int>(); */
 
          /* This case handles bogus declarations like template <>
             template <class T> void f<int>(); */
 
-         if (uses_template_parms (declarator))
-           error ("function template partial specialization %qD "
-                  "is not allowed", declarator);
-         else
+         if (!uses_template_parms (declarator))
            error ("template-id %qD in declaration of primary template",
                   declarator);
            error ("template-id %qD in declaration of primary template",
                   declarator);
+         else if (variable_template_p (TREE_OPERAND (declarator, 0)))
+           {
+             /* Partial specialization of variable template.  */
+             SET_DECL_TEMPLATE_SPECIALIZATION (decl);
+             specialization = 1;
+             goto ok;
+           }
+         else if (cxx_dialect < cxx14)
+           error ("non-type partial specialization %qD "
+                  "is not allowed", declarator);
+         else
+           error ("non-class, non-variable partial specialization %qD "
+                  "is not allowed", declarator);
          return decl;
          return decl;
+       ok:;
        }
 
       if (ctype && CLASSTYPE_TEMPLATE_INSTANTIATION (ctype))
        }
 
       if (ctype && CLASSTYPE_TEMPLATE_INSTANTIATION (ctype))
@@ -2515,9 +2584,10 @@ check_explicit_specialization (tree declarator,
     {
       tree tmpl = NULL_TREE;
       tree targs = NULL_TREE;
     {
       tree tmpl = NULL_TREE;
       tree targs = NULL_TREE;
+      bool was_template_id = (TREE_CODE (declarator) == TEMPLATE_ID_EXPR);
 
       /* Make sure that the declarator is a TEMPLATE_ID_EXPR.  */
 
       /* Make sure that the declarator is a TEMPLATE_ID_EXPR.  */
-      if (TREE_CODE (declarator) != TEMPLATE_ID_EXPR)
+      if (!was_template_id)
        {
          tree fns;
 
        {
          tree fns;
 
@@ -2584,7 +2654,7 @@ check_explicit_specialization (tree declarator,
       else if (ctype != NULL_TREE
               && (identifier_p (TREE_OPERAND (declarator, 0))))
        {
       else if (ctype != NULL_TREE
               && (identifier_p (TREE_OPERAND (declarator, 0))))
        {
-         // Ignore variable templates.
+         // We'll match variable templates in start_decl.
          if (VAR_P (decl))
            return decl;
 
          if (VAR_P (decl))
            return decl;
 
@@ -2721,7 +2791,7 @@ check_explicit_specialization (tree declarator,
          /* If this is a specialization of a member template of a
             template class, we want to return the TEMPLATE_DECL, not
             the specialization of it.  */
          /* If this is a specialization of a member template of a
             template class, we want to return the TEMPLATE_DECL, not
             the specialization of it.  */
-         if (tsk == tsk_template)
+         if (tsk == tsk_template && !was_template_id)
            {
              tree result = DECL_TEMPLATE_RESULT (tmpl);
              SET_DECL_TEMPLATE_SPECIALIZATION (tmpl);
            {
              tree result = DECL_TEMPLATE_RESULT (tmpl);
              SET_DECL_TEMPLATE_SPECIALIZATION (tmpl);
@@ -2746,6 +2816,9 @@ check_explicit_specialization (tree declarator,
          /* Set up the DECL_TEMPLATE_INFO for DECL.  */
          DECL_TEMPLATE_INFO (decl) = build_template_info (tmpl, targs);
 
          /* Set up the DECL_TEMPLATE_INFO for DECL.  */
          DECL_TEMPLATE_INFO (decl) = build_template_info (tmpl, targs);
 
+         if (was_template_id)
+           TINFO_USED_TEMPLATE_ID (DECL_TEMPLATE_INFO (decl)) = true;
+
          /* Inherit default function arguments from the template
             DECL is specializing.  */
          if (DECL_FUNCTION_TEMPLATE_P (tmpl))
          /* Inherit default function arguments from the template
             DECL is specializing.  */
          if (DECL_FUNCTION_TEMPLATE_P (tmpl))
@@ -2813,8 +2886,9 @@ check_explicit_specialization (tree declarator,
            SET_DECL_IMPLICIT_INSTANTIATION (decl);
          else if (TREE_CODE (decl) == FUNCTION_DECL)
            /* A specialization is not necessarily COMDAT.  */
            SET_DECL_IMPLICIT_INSTANTIATION (decl);
          else if (TREE_CODE (decl) == FUNCTION_DECL)
            /* A specialization is not necessarily COMDAT.  */
-           DECL_COMDAT (decl) = DECL_DECLARED_INLINE_P (decl);
-         else if (TREE_CODE (decl) == VAR_DECL)
+           DECL_COMDAT (decl) = (TREE_PUBLIC (decl)
+                                 && DECL_DECLARED_INLINE_P (decl));
+         else if (VAR_P (decl))
            DECL_COMDAT (decl) = false;
 
          /* Register this specialization so that we can find it
            DECL_COMDAT (decl) = false;
 
          /* Register this specialization so that we can find it
@@ -3295,9 +3369,9 @@ make_pack_expansion (tree arg)
   if (!arg || arg == error_mark_node)
     return arg;
 
   if (!arg || arg == error_mark_node)
     return arg;
 
-  if (TREE_CODE (arg) == TREE_LIST)
+  if (TREE_CODE (arg) == TREE_LIST && TREE_PURPOSE (arg))
     {
     {
-      /* The only time we will see a TREE_LIST here is for a base
+      /* A TREE_LIST with a non-null TREE_PURPOSE is for a base
          class initializer.  In this case, the TREE_PURPOSE will be a
          _TYPE node (representing the base class expansion we're
          initializing) and the TREE_VALUE will be a TREE_LIST
          class initializer.  In this case, the TREE_PURPOSE will be a
          _TYPE node (representing the base class expansion we're
          initializing) and the TREE_VALUE will be a TREE_LIST
@@ -4085,8 +4159,9 @@ static tree
 process_partial_specialization (tree decl)
 {
   tree type = TREE_TYPE (decl);
 process_partial_specialization (tree decl)
 {
   tree type = TREE_TYPE (decl);
-  tree maintmpl = CLASSTYPE_TI_TEMPLATE (type);
-  tree specargs = CLASSTYPE_TI_ARGS (type);
+  tree tinfo = get_template_info (decl);
+  tree maintmpl = TI_TEMPLATE (tinfo);
+  tree specargs = TI_ARGS (tinfo);
   tree inner_args = INNERMOST_TEMPLATE_ARGS (specargs);
   tree main_inner_parms = DECL_INNERMOST_TEMPLATE_PARMS (maintmpl);
   tree inner_parms;
   tree inner_args = INNERMOST_TEMPLATE_ARGS (specargs);
   tree main_inner_parms = DECL_INNERMOST_TEMPLATE_PARMS (maintmpl);
   tree inner_parms;
@@ -4171,11 +4246,11 @@ process_partial_specialization (tree decl)
 
      The argument list of the specialization shall not be identical to
      the implicit argument list of the primary template.  */
 
      The argument list of the specialization shall not be identical to
      the implicit argument list of the primary template.  */
-  if (comp_template_args
-      (inner_args,
-       INNERMOST_TEMPLATE_ARGS (CLASSTYPE_TI_ARGS (TREE_TYPE
-                                                  (maintmpl)))))
-    error ("partial specialization %qT does not specialize any template arguments", type);
+  tree main_args
+    = TI_ARGS (get_template_info (DECL_TEMPLATE_RESULT (maintmpl)));
+  if (comp_template_args (inner_args, INNERMOST_TEMPLATE_ARGS (main_args)))
+    error ("partial specialization %qD does not specialize "
+          "any template arguments", decl);
 
   /* A partial specialization that replaces multiple parameters of the
      primary template with a pack expansion is less specialized for those
 
   /* A partial specialization that replaces multiple parameters of the
      primary template with a pack expansion is less specialized for those
@@ -4315,7 +4390,8 @@ process_partial_specialization (tree decl)
     }
 
   /* We should only get here once.  */
     }
 
   /* We should only get here once.  */
-  gcc_assert (!COMPLETE_TYPE_P (type));
+  if (TREE_CODE (decl) == TYPE_DECL)
+    gcc_assert (!COMPLETE_TYPE_P (type));
 
   tree tmpl = build_template_decl (decl, current_template_parms,
                                   DECL_MEMBER_TEMPLATE_P (maintmpl));
 
   tree tmpl = build_template_decl (decl, current_template_parms,
                                   DECL_MEMBER_TEMPLATE_P (maintmpl));
@@ -4333,15 +4409,21 @@ process_partial_specialization (tree decl)
   for (inst = DECL_TEMPLATE_INSTANTIATIONS (maintmpl); inst;
        inst = TREE_CHAIN (inst))
     {
   for (inst = DECL_TEMPLATE_INSTANTIATIONS (maintmpl); inst;
        inst = TREE_CHAIN (inst))
     {
-      tree inst_type = TREE_VALUE (inst);
-      if (COMPLETE_TYPE_P (inst_type)
-         && CLASSTYPE_IMPLICIT_INSTANTIATION (inst_type))
+      tree instance = TREE_VALUE (inst);
+      if (TYPE_P (instance)
+         ? (COMPLETE_TYPE_P (instance)
+            && CLASSTYPE_IMPLICIT_INSTANTIATION (instance))
+         : DECL_TEMPLATE_INSTANTIATION (instance))
        {
        {
-         tree spec = most_specialized_class (inst_type, tf_none);
-         if (spec && TREE_TYPE (spec) == type)
-           permerror (input_location,
-                      "partial specialization of %qT after instantiation "
-                      "of %qT", type, inst_type);
+         tree spec = most_specialized_partial_spec (instance, tf_none);
+         if (spec && TREE_VALUE (spec) == tmpl)
+           {
+             tree inst_decl = (DECL_P (instance)
+                               ? instance : TYPE_NAME (instance));
+             permerror (input_location,
+                        "partial specialization of %qD after instantiation "
+                        "of %qD", decl, inst_decl);
+           }
        }
     }
 
        }
     }
 
@@ -4361,6 +4443,7 @@ get_template_parm_index (tree parm)
           || TREE_CODE (parm) == TEMPLATE_DECL)
     parm = TREE_TYPE (parm);
   if (TREE_CODE (parm) == TEMPLATE_TYPE_PARM
           || TREE_CODE (parm) == TEMPLATE_DECL)
     parm = TREE_TYPE (parm);
   if (TREE_CODE (parm) == TEMPLATE_TYPE_PARM
+      || TREE_CODE (parm) == BOUND_TEMPLATE_TEMPLATE_PARM
       || TREE_CODE (parm) == TEMPLATE_TEMPLATE_PARM)
     parm = TEMPLATE_TYPE_PARM_INDEX (parm);
   gcc_assert (TREE_CODE (parm) == TEMPLATE_PARM_INDEX);
       || TREE_CODE (parm) == TEMPLATE_TEMPLATE_PARM)
     parm = TEMPLATE_TYPE_PARM_INDEX (parm);
   gcc_assert (TREE_CODE (parm) == TEMPLATE_PARM_INDEX);
@@ -4455,9 +4538,11 @@ check_default_tmpl_args (tree decl, tree parms, bool is_primary,
        local scope.  */
     return true;
 
        local scope.  */
     return true;
 
-  if (TREE_CODE (decl) == TYPE_DECL
-      && TREE_TYPE (decl)
-      && LAMBDA_TYPE_P (TREE_TYPE (decl)))
+  if ((TREE_CODE (decl) == TYPE_DECL
+       && TREE_TYPE (decl)
+       && LAMBDA_TYPE_P (TREE_TYPE (decl)))
+      || (TREE_CODE (decl) == FUNCTION_DECL
+         && LAMBDA_FUNCTION_P (decl)))
     /* A lambda doesn't have an explicit declaration; don't complain
        about the parms of the enclosing class.  */
     return true;
     /* A lambda doesn't have an explicit declaration; don't complain
        about the parms of the enclosing class.  */
     return true;
@@ -4534,13 +4619,8 @@ check_default_tmpl_args (tree decl, tree parms, bool is_primary,
                     parameter pack, at the end of the template
                     parameter list.  */
 
                     parameter pack, at the end of the template
                     parameter list.  */
 
-                 if (TREE_CODE (TREE_VALUE (parm)) == PARM_DECL)
-                   error ("parameter pack %qE must be at the end of the"
-                          " template parameter list", TREE_VALUE (parm));
-                 else
-                   error ("parameter pack %qT must be at the end of the"
-                          " template parameter list", 
-                          TREE_TYPE (TREE_VALUE (parm)));
+                 error ("parameter pack %q+D must be at the end of the"
+                        " template parameter list", TREE_VALUE (parm));
 
                  TREE_VALUE (TREE_VEC_ELT (inner_parms, i)) 
                    = error_mark_node;
 
                  TREE_VALUE (TREE_VEC_ELT (inner_parms, i)) 
                    = error_mark_node;
@@ -4688,9 +4768,13 @@ push_template_decl_real (tree decl, bool is_friend)
     return error_mark_node;
 
   /* See if this is a partial specialization.  */
     return error_mark_node;
 
   /* See if this is a partial specialization.  */
-  is_partial = (DECL_IMPLICIT_TYPEDEF_P (decl)
-               && TREE_CODE (TREE_TYPE (decl)) != ENUMERAL_TYPE
-               && CLASSTYPE_TEMPLATE_SPECIALIZATION (TREE_TYPE (decl)));
+  is_partial = ((DECL_IMPLICIT_TYPEDEF_P (decl)
+                && TREE_CODE (TREE_TYPE (decl)) != ENUMERAL_TYPE
+                && CLASSTYPE_TEMPLATE_SPECIALIZATION (TREE_TYPE (decl)))
+               || (VAR_P (decl)
+                   && DECL_LANG_SPECIFIC (decl)
+                   && DECL_TEMPLATE_SPECIALIZATION (decl)
+                   && TINFO_USED_TEMPLATE_ID (DECL_TEMPLATE_INFO (decl))));
 
   if (TREE_CODE (decl) == FUNCTION_DECL && DECL_FRIEND_P (decl))
     is_friend = true;
 
   if (TREE_CODE (decl) == FUNCTION_DECL && DECL_FRIEND_P (decl))
     is_friend = true;
@@ -4733,7 +4817,7 @@ push_template_decl_real (tree decl, bool is_friend)
       if (DECL_CLASS_SCOPE_P (decl))
        member_template_p = true;
       if (TREE_CODE (decl) == TYPE_DECL
       if (DECL_CLASS_SCOPE_P (decl))
        member_template_p = true;
       if (TREE_CODE (decl) == TYPE_DECL
-         && ANON_AGGRNAME_P (DECL_NAME (decl)))
+         && anon_aggrname_p (DECL_NAME (decl)))
        {
          error ("template class without a name");
          return error_mark_node;
        {
          error ("template class without a name");
          return error_mark_node;
@@ -5036,6 +5120,11 @@ template arguments to %qD do not match original template %qD",
          if (TREE_CODE (parm) == TEMPLATE_DECL)
            DECL_CONTEXT (parm) = tmpl;
        }
          if (TREE_CODE (parm) == TEMPLATE_DECL)
            DECL_CONTEXT (parm) = tmpl;
        }
+
+      if (TREE_CODE (decl) == TYPE_DECL
+         && TYPE_DECL_ALIAS_P (decl)
+         && complex_alias_template_p (tmpl))
+       TEMPLATE_DECL_COMPLEX_ALIAS_P (tmpl) = true;
     }
 
   /* The DECL_TI_ARGS of DECL contains full set of arguments referring
     }
 
   /* The DECL_TI_ARGS of DECL contains full set of arguments referring
@@ -5059,6 +5148,7 @@ template arguments to %qD do not match original template %qD",
 
   if (flag_implicit_templates
       && !is_friend
 
   if (flag_implicit_templates
       && !is_friend
+      && TREE_PUBLIC (decl)
       && VAR_OR_FUNCTION_DECL_P (decl))
     /* Set DECL_COMDAT on template instantiations; if we force
        them to be emitted by explicit instantiation or -frepo,
       && VAR_OR_FUNCTION_DECL_P (decl))
     /* Set DECL_COMDAT on template instantiations; if we force
        them to be emitted by explicit instantiation or -frepo,
@@ -5207,11 +5297,29 @@ redeclare_class_template (tree type, tree parms)
     return true;
 }
 
     return true;
 }
 
+/* The actual substitution part of instantiate_non_dependent_expr_sfinae,
+   to be used when the caller has already checked
+   (processing_template_decl
+    && !instantiation_dependent_expression_p (expr)
+    && potential_constant_expression (expr))
+   and cleared processing_template_decl.  */
+
+tree
+instantiate_non_dependent_expr_internal (tree expr, tsubst_flags_t complain)
+{
+  return tsubst_copy_and_build (expr,
+                               /*args=*/NULL_TREE,
+                               complain,
+                               /*in_decl=*/NULL_TREE,
+                               /*function_p=*/false,
+                               /*integral_constant_expression_p=*/true);
+}
+
 /* Simplify EXPR if it is a non-dependent expression.  Returns the
    (possibly simplified) expression.  */
 
 tree
 /* Simplify EXPR if it is a non-dependent expression.  Returns the
    (possibly simplified) expression.  */
 
 tree
-fold_non_dependent_expr_sfinae (tree expr, tsubst_flags_t complain)
+instantiate_non_dependent_expr_sfinae (tree expr, tsubst_flags_t complain)
 {
   if (expr == NULL_TREE)
     return NULL_TREE;
 {
   if (expr == NULL_TREE)
     return NULL_TREE;
@@ -5227,25 +5335,16 @@ fold_non_dependent_expr_sfinae (tree expr, tsubst_flags_t complain)
       && !instantiation_dependent_expression_p (expr)
       && potential_constant_expression (expr))
     {
       && !instantiation_dependent_expression_p (expr)
       && potential_constant_expression (expr))
     {
-      HOST_WIDE_INT saved_processing_template_decl;
-
-      saved_processing_template_decl = processing_template_decl;
-      processing_template_decl = 0;
-      expr = tsubst_copy_and_build (expr,
-                                   /*args=*/NULL_TREE,
-                                   complain,
-                                   /*in_decl=*/NULL_TREE,
-                                   /*function_p=*/false,
-                                   /*integral_constant_expression_p=*/true);
-      processing_template_decl = saved_processing_template_decl;
+      processing_template_decl_sentinel s;
+      expr = instantiate_non_dependent_expr_internal (expr, complain);
     }
   return expr;
 }
 
 tree
     }
   return expr;
 }
 
 tree
-fold_non_dependent_expr (tree expr)
+instantiate_non_dependent_expr (tree expr)
 {
 {
-  return fold_non_dependent_expr_sfinae (expr, tf_error);
+  return instantiate_non_dependent_expr_sfinae (expr, tf_error);
 }
 
 /* Return TRUE iff T is a type alias, a TEMPLATE_DECL for an alias
 }
 
 /* Return TRUE iff T is a type alias, a TEMPLATE_DECL for an alias
@@ -5263,18 +5362,78 @@ alias_type_or_template_p (tree t)
          || DECL_ALIAS_TEMPLATE_P (t));
 }
 
          || DECL_ALIAS_TEMPLATE_P (t));
 }
 
-/* Return TRUE iff is a specialization of an alias template.  */
+/* Return TRUE iff is a specialization of an alias template.  */
 
 bool
 alias_template_specialization_p (const_tree t)
 {
 
 bool
 alias_template_specialization_p (const_tree t)
 {
-  if (t == NULL_TREE)
-    return false;
-  
-  return (TYPE_P (t)
-         && TYPE_TEMPLATE_INFO (t)
-         && PRIMARY_TEMPLATE_P (TYPE_TI_TEMPLATE (t))
-         && DECL_ALIAS_TEMPLATE_P (TYPE_TI_TEMPLATE (t)));
+  /* It's an alias template specialization if it's an alias and its
+     TYPE_NAME is a specialization of a primary template.  */
+  if (TYPE_ALIAS_P (t))
+    {
+      tree name = TYPE_NAME (t);
+      if (DECL_LANG_SPECIFIC (name))
+       if (tree ti = DECL_TEMPLATE_INFO (name))
+         {
+           tree tmpl = TI_TEMPLATE (ti);
+           return PRIMARY_TEMPLATE_P (tmpl);
+         }
+    }
+  return false;
+}
+
+/* An alias template is complex from a SFINAE perspective if a template-id
+   using that alias can be ill-formed when the expansion is not, as with
+   the void_t template.  We determine this by checking whether the
+   expansion for the alias template uses all its template parameters.  */
+
+struct uses_all_template_parms_data
+{
+  int level;
+  bool *seen;
+};
+
+static int
+uses_all_template_parms_r (tree t, void *data_)
+{
+  struct uses_all_template_parms_data &data
+    = *(struct uses_all_template_parms_data*)data_;
+  tree idx = get_template_parm_index (t);
+
+  if (TEMPLATE_PARM_LEVEL (idx) == data.level)
+    data.seen[TEMPLATE_PARM_IDX (idx)] = true;
+  return 0;
+}
+
+static bool
+complex_alias_template_p (const_tree tmpl)
+{
+  struct uses_all_template_parms_data data;
+  tree pat = DECL_ORIGINAL_TYPE (DECL_TEMPLATE_RESULT (tmpl));
+  tree parms = DECL_TEMPLATE_PARMS (tmpl);
+  data.level = TMPL_PARMS_DEPTH (parms);
+  int len = TREE_VEC_LENGTH (INNERMOST_TEMPLATE_PARMS (parms));
+  data.seen = XALLOCAVEC (bool, len);
+  for (int i = 0; i < len; ++i)
+    data.seen[i] = false;
+
+  for_each_template_parm (pat, uses_all_template_parms_r, &data, NULL, true);
+  for (int i = 0; i < len; ++i)
+    if (!data.seen[i])
+      return true;
+  return false;
+}
+
+/* Return TRUE iff T is a specialization of a complex alias template with
+   dependent template-arguments.  */
+
+bool
+dependent_alias_template_spec_p (const_tree t)
+{
+  return (alias_template_specialization_p (t)
+         && TEMPLATE_DECL_COMPLEX_ALIAS_P (DECL_TI_TEMPLATE (TYPE_NAME (t)))
+         && (any_dependent_template_arguments_p
+             (INNERMOST_TEMPLATE_ARGS (TYPE_TI_ARGS (t)))));
 }
 
 /* Return the number of innermost template parameters in TMPL.  */
 }
 
 /* Return the number of innermost template parameters in TMPL.  */
@@ -5721,11 +5880,15 @@ convert_nontype_argument (tree type, tree expr, tsubst_flags_t complain)
      so that access checking can be performed when the template is
      instantiated -- but here we need the resolved form so that we can
      convert the argument.  */
      so that access checking can be performed when the template is
      instantiated -- but here we need the resolved form so that we can
      convert the argument.  */
+  bool non_dep = false;
   if (TYPE_REF_OBJ_P (type)
       && has_value_dependent_address (expr))
     /* If we want the address and it's value-dependent, don't fold.  */;
   if (TYPE_REF_OBJ_P (type)
       && has_value_dependent_address (expr))
     /* If we want the address and it's value-dependent, don't fold.  */;
-  else if (!type_unknown_p (expr))
-    expr = fold_non_dependent_expr_sfinae (expr, complain);
+  else if (!type_unknown_p (expr)
+          && processing_template_decl
+          && !instantiation_dependent_expression_p (expr)
+          && potential_constant_expression (expr))
+    non_dep = true;
   if (error_operand_p (expr))
     return error_mark_node;
   expr_type = TREE_TYPE (expr);
   if (error_operand_p (expr))
     return error_mark_node;
   expr_type = TREE_TYPE (expr);
@@ -5734,6 +5897,12 @@ convert_nontype_argument (tree type, tree expr, tsubst_flags_t complain)
   else
     expr = mark_rvalue_use (expr);
 
   else
     expr = mark_rvalue_use (expr);
 
+  /* If the argument is non-dependent, perform any conversions in
+     non-dependent context as well.  */
+  processing_template_decl_sentinel s (non_dep);
+  if (non_dep)
+    expr = instantiate_non_dependent_expr_internal (expr, complain);
+
   /* 14.3.2/5: The null pointer{,-to-member} conversion is applied
      to a non-type argument of "nullptr".  */
   if (expr == nullptr_node && TYPE_PTR_OR_PTRMEM_P (type))
   /* 14.3.2/5: The null pointer{,-to-member} conversion is applied
      to a non-type argument of "nullptr".  */
   if (expr == nullptr_node && TYPE_PTR_OR_PTRMEM_P (type))
@@ -6140,7 +6309,7 @@ convert_nontype_argument (tree type, tree expr, tsubst_flags_t complain)
      right type?  */
   gcc_assert (same_type_ignoring_top_level_qualifiers_p
              (type, TREE_TYPE (expr)));
      right type?  */
   gcc_assert (same_type_ignoring_top_level_qualifiers_p
              (type, TREE_TYPE (expr)));
-  return expr;
+  return convert_from_reference (expr);
 }
 
 /* Subroutine of coerce_template_template_parms, which returns 1 if
 }
 
 /* Subroutine of coerce_template_template_parms, which returns 1 if
@@ -6404,20 +6573,14 @@ template_template_parm_bindings_ok_p (tree tparms, tree targs)
 static tree
 canonicalize_type_argument (tree arg, tsubst_flags_t complain)
 {
 static tree
 canonicalize_type_argument (tree arg, tsubst_flags_t complain)
 {
-  tree mv;
   if (!arg || arg == error_mark_node || arg == TYPE_CANONICAL (arg))
     return arg;
   if (!arg || arg == error_mark_node || arg == TYPE_CANONICAL (arg))
     return arg;
-  mv = TYPE_MAIN_VARIANT (arg);
-  arg = strip_typedefs (arg);
-  if (TYPE_ALIGN (arg) != TYPE_ALIGN (mv)
-      || TYPE_ATTRIBUTES (arg) != TYPE_ATTRIBUTES (mv))
-    {
-      if (complain & tf_warning)
-       warning (0, "ignoring attributes on template argument %qT", arg);
-      arg = build_aligned_type (arg, TYPE_ALIGN (mv));
-      arg = cp_build_type_attribute_variant (arg, TYPE_ATTRIBUTES (mv));
-    }
-  return arg;
+  bool removed_attributes = false;
+  tree canon = strip_typedefs (arg, &removed_attributes);
+  if (removed_attributes
+      && (complain & tf_warning))
+    warning (0, "ignoring attributes on template argument %qT", arg);
+  return canon;
 }
 
 /* Convert the indicated template ARG as necessary to match the
 }
 
 /* Convert the indicated template ARG as necessary to match the
@@ -6439,6 +6602,9 @@ convert_template_argument (tree parm,
   tree val;
   int is_type, requires_type, is_tmpl_type, requires_tmpl_type;
 
   tree val;
   int is_type, requires_type, is_tmpl_type, requires_tmpl_type;
 
+  if (parm == error_mark_node)
+    return error_mark_node;
+
   if (TREE_CODE (arg) == TREE_LIST
       && TREE_CODE (TREE_VALUE (arg)) == OFFSET_REF)
     {
   if (TREE_CODE (arg) == TREE_LIST
       && TREE_CODE (TREE_VALUE (arg)) == OFFSET_REF)
     {
@@ -6651,7 +6817,10 @@ convert_template_argument (tree parm,
           argument specification is valid.  */
        val = convert_nontype_argument (t, orig_arg, complain);
       else
           argument specification is valid.  */
        val = convert_nontype_argument (t, orig_arg, complain);
       else
-       val = strip_typedefs_expr (orig_arg);
+       {
+         bool removed_attr = false;
+         val = strip_typedefs_expr (orig_arg, &removed_attr);
+       }
 
       if (val == NULL_TREE)
        val = error_mark_node;
 
       if (val == NULL_TREE)
        val = error_mark_node;
@@ -6733,6 +6902,9 @@ coerce_template_parameter_pack (tree parms,
               if (invalid_nontype_parm_type_p (t, complain))
                 return error_mark_node;
             }
               if (invalid_nontype_parm_type_p (t, complain))
                 return error_mark_node;
             }
+         /* We don't know how many args we have yet, just
+            use the unconverted ones for now.  */
+         return NULL_TREE;
         }
 
       packed_args = make_tree_vec (TREE_VEC_LENGTH (packed_parms));
         }
 
       packed_args = make_tree_vec (TREE_VEC_LENGTH (packed_parms));
@@ -7212,11 +7384,39 @@ template_args_equal (tree ot, tree nt)
       return template_args_equal (ot, nt);
     }
   else if (TYPE_P (nt))
       return template_args_equal (ot, nt);
     }
   else if (TYPE_P (nt))
-    return TYPE_P (ot) && same_type_p (ot, nt);
+    {
+      if (!TYPE_P (ot))
+       return false;
+      /* Don't treat an alias template specialization with dependent
+        arguments as equivalent to its underlying type when used as a
+        template argument; we need them to be distinct so that we
+        substitute into the specialization arguments at instantiation
+        time.  And aliases can't be equivalent without being ==, so
+        we don't need to look any deeper.  */
+      if (TYPE_ALIAS_P (nt) || TYPE_ALIAS_P (ot))
+       return false;
+      else
+       return same_type_p (ot, nt);
+    }
   else if (TREE_CODE (ot) == TREE_VEC || TYPE_P (ot))
     return 0;
   else
   else if (TREE_CODE (ot) == TREE_VEC || TYPE_P (ot))
     return 0;
   else
-    return cp_tree_equal (ot, nt);
+    {
+      /* Try to treat a template non-type argument that has been converted
+        to the parameter type as equivalent to one that hasn't yet.  */
+      for (enum tree_code code1 = TREE_CODE (ot);
+          CONVERT_EXPR_CODE_P (code1)
+            || code1 == NON_LVALUE_EXPR;
+          code1 = TREE_CODE (ot))
+       ot = TREE_OPERAND (ot, 0);
+      for (enum tree_code code2 = TREE_CODE (nt);
+          CONVERT_EXPR_CODE_P (code2)
+            || code2 == NON_LVALUE_EXPR;
+          code2 = TREE_CODE (nt))
+       nt = TREE_OPERAND (nt, 0);
+
+      return cp_tree_equal (ot, nt);
+    }
 }
 
 /* Returns 1 iff the OLDARGS and NEWARGS are in fact identical sets of
 }
 
 /* Returns 1 iff the OLDARGS and NEWARGS are in fact identical sets of
@@ -7413,7 +7613,7 @@ lookup_template_class_1 (tree d1, tree arglist, tree in_decl, tree context,
 {
   tree templ = NULL_TREE, parmlist;
   tree t;
 {
   tree templ = NULL_TREE, parmlist;
   tree t;
-  void **slot;
+  spec_entry **slot;
   spec_entry *entry;
   spec_entry elt;
   hashval_t hash;
   spec_entry *entry;
   spec_entry elt;
   hashval_t hash;
@@ -7601,60 +7801,10 @@ lookup_template_class_1 (tree d1, tree arglist, tree in_decl, tree context,
       /* Calculate the BOUND_ARGS.  These will be the args that are
         actually tsubst'd into the definition to create the
         instantiation.  */
       /* Calculate the BOUND_ARGS.  These will be the args that are
         actually tsubst'd into the definition to create the
         instantiation.  */
-      if (parm_depth > 1)
-       {
-         /* We have multiple levels of arguments to coerce, at once.  */
-         int i;
-         int saved_depth = TMPL_ARGS_DEPTH (arglist);
-
-         tree bound_args = make_tree_vec (parm_depth);
-
-         for (i = saved_depth,
-                t = DECL_TEMPLATE_PARMS (gen_tmpl);
-              i > 0 && t != NULL_TREE;
-              --i, t = TREE_CHAIN (t))
-           {
-             tree a;
-             if (i == saved_depth)
-               a = coerce_template_parms (TREE_VALUE (t),
-                                          arglist, gen_tmpl,
-                                          complain,
-                                          /*require_all_args=*/true,
-                                          /*use_default_args=*/true);
-             else
-               /* Outer levels should have already been coerced.  */
-               a = TMPL_ARGS_LEVEL (arglist, i);
-
-             /* Don't process further if one of the levels fails.  */
-             if (a == error_mark_node)
-               {
-                 /* Restore the ARGLIST to its full size.  */
-                 TREE_VEC_LENGTH (arglist) = saved_depth;
-                 return error_mark_node;
-               }
-
-             SET_TMPL_ARGS_LEVEL (bound_args, i, a);
-
-             /* We temporarily reduce the length of the ARGLIST so
-                that coerce_template_parms will see only the arguments
-                corresponding to the template parameters it is
-                examining.  */
-             TREE_VEC_LENGTH (arglist)--;
-           }
-
-         /* Restore the ARGLIST to its full size.  */
-         TREE_VEC_LENGTH (arglist) = saved_depth;
-
-         arglist = bound_args;
-       }
-      else
-       arglist
-         = coerce_template_parms (INNERMOST_TEMPLATE_PARMS (parmlist),
-                                  INNERMOST_TEMPLATE_ARGS (arglist),
-                                  gen_tmpl,
-                                  complain,
-                                  /*require_all_args=*/true,
-                                  /*use_default_args=*/true);
+      arglist = coerce_innermost_template_parms (parmlist, arglist, gen_tmpl,
+                                                complain,
+                                                /*require_all_args=*/true,
+                                                /*use_default_args=*/true);
 
       if (arglist == error_mark_node)
        /* We were unable to bind the arguments.  */
 
       if (arglist == error_mark_node)
        /* We were unable to bind the arguments.  */
@@ -7679,9 +7829,8 @@ lookup_template_class_1 (tree d1, tree arglist, tree in_decl, tree context,
       /* If we already have this specialization, return it.  */
       elt.tmpl = gen_tmpl;
       elt.args = arglist;
       /* If we already have this specialization, return it.  */
       elt.tmpl = gen_tmpl;
       elt.args = arglist;
-      hash = hash_specialization (&elt);
-      entry = (spec_entry *) htab_find_with_hash (type_specializations,
-                                                 &elt, hash);
+      hash = spec_hasher::hash (&elt);
+      entry = type_specializations->find_with_hash (&elt, hash);
 
       if (entry)
        return entry->spec;
 
       if (entry)
        return entry->spec;
@@ -7821,9 +7970,25 @@ lookup_template_class_1 (tree d1, tree arglist, tree in_decl, tree context,
 
       if (OVERLOAD_TYPE_P (t)
          && !DECL_ALIAS_TEMPLATE_P (gen_tmpl))
 
       if (OVERLOAD_TYPE_P (t)
          && !DECL_ALIAS_TEMPLATE_P (gen_tmpl))
-       if (tree attributes
-           = lookup_attribute ("abi_tag", TYPE_ATTRIBUTES (template_type)))
-         TYPE_ATTRIBUTES (t) = attributes;
+       {
+         static const char *tags[] = {"abi_tag", "may_alias"};
+
+         for (unsigned ix = 0; ix != 2; ix++)
+           {
+             tree attributes
+               = lookup_attribute (tags[ix], TYPE_ATTRIBUTES (template_type));
+
+             if (!attributes)
+               ;
+             else if (!TREE_CHAIN (attributes) && !TYPE_ATTRIBUTES (t))
+               TYPE_ATTRIBUTES (t) = attributes;
+             else
+               TYPE_ATTRIBUTES (t)
+                 = tree_cons (TREE_PURPOSE (attributes),
+                              TREE_VALUE (attributes),
+                              TYPE_ATTRIBUTES (t));
+           }
+       }
 
       /* Let's consider the explicit specialization of a member
          of a class template specialization that is implicitly instantiated,
 
       /* Let's consider the explicit specialization of a member
          of a class template specialization that is implicitly instantiated,
@@ -7916,8 +8081,7 @@ lookup_template_class_1 (tree d1, tree arglist, tree in_decl, tree context,
       SET_TYPE_TEMPLATE_INFO (t, build_template_info (found, arglist));
 
       elt.spec = t;
       SET_TYPE_TEMPLATE_INFO (t, build_template_info (found, arglist));
 
       elt.spec = t;
-      slot = htab_find_slot_with_hash (type_specializations,
-                                      &elt, hash, INSERT);
+      slot = type_specializations->find_slot_with_hash (&elt, hash, INSERT);
       entry = ggc_alloc<spec_entry> ();
       *entry = elt;
       *slot = entry;
       entry = ggc_alloc<spec_entry> ();
       *entry = elt;
       *slot = entry;
@@ -7948,6 +8112,8 @@ lookup_template_class_1 (tree d1, tree arglist, tree in_decl, tree context,
       TREE_PUBLIC (type_decl) = 1;
       determine_visibility (type_decl);
 
       TREE_PUBLIC (type_decl) = 1;
       determine_visibility (type_decl);
 
+      inherit_targ_abi_tags (t);
+
       return t;
     }
 }
       return t;
     }
 }
@@ -7966,22 +8132,36 @@ lookup_template_class (tree d1, tree arglist, tree in_decl, tree context,
   return ret;
 }
 
   return ret;
 }
 
-/* Return a TEMPLATE_ID_EXPR for the given variable template and ARGLIST. 
-   If the ARGLIST refers to any template parameters, the type of the
-   expression is the unknown_type_node since the template-id could
-   refer to an explicit or partial specialization. */
+/* Return a TEMPLATE_ID_EXPR for the given variable template and ARGLIST.
+   The type of the expression is the unknown_type_node since the
+   template-id could refer to an explicit or partial specialization. */
 
 tree
 lookup_template_variable (tree templ, tree arglist)
 {
 
 tree
 lookup_template_variable (tree templ, tree arglist)
 {
-  tree type;
-  if (uses_template_parms (arglist))
-    type = unknown_type_node;
-  else
-    type = TREE_TYPE (templ);
+  tree type = unknown_type_node;
   return build2 (TEMPLATE_ID_EXPR, type, templ, arglist);
 }
 
   return build2 (TEMPLATE_ID_EXPR, type, templ, arglist);
 }
 
+/* Instantiate a variable declaration from a TEMPLATE_ID_EXPR for use. */
+
+tree
+finish_template_variable (tree var)
+{
+  tree templ = TREE_OPERAND (var, 0);
+
+  tree arglist = TREE_OPERAND (var, 1);
+  tree tmpl_args = DECL_TI_ARGS (DECL_TEMPLATE_RESULT (templ));
+  arglist = add_outermost_template_args (tmpl_args, arglist);
+
+  tree parms = DECL_TEMPLATE_PARMS (templ);
+  tsubst_flags_t complain = tf_warning_or_error;
+  arglist = coerce_innermost_template_parms (parms, arglist, templ, complain,
+                                            /*req_all*/true,
+                                            /*use_default*/true);
+
+  return instantiate_template (templ, arglist, complain);
+}
 \f
 struct pair_fn_data
 {
 \f
 struct pair_fn_data
 {
@@ -8230,6 +8410,9 @@ for_each_template_parm (tree t, tree_fn_t fn, void* data,
 int
 uses_template_parms (tree t)
 {
 int
 uses_template_parms (tree t)
 {
+  if (t == NULL_TREE)
+    return false;
+
   bool dependent_p;
   int saved_processing_template_decl;
 
   bool dependent_p;
   int saved_processing_template_decl;
 
@@ -8269,7 +8452,7 @@ uses_template_parms (tree t)
 
 /* Returns true iff current_function_decl is an incompletely instantiated
    template.  Useful instead of processing_template_decl because the latter
 
 /* Returns true iff current_function_decl is an incompletely instantiated
    template.  Useful instead of processing_template_decl because the latter
-   is set to 0 during fold_non_dependent_expr.  */
+   is set to 0 during instantiate_non_dependent_expr.  */
 
 bool
 in_template_function (void)
 
 bool
 in_template_function (void)
@@ -8332,37 +8515,38 @@ static GTY(()) struct tinst_level *last_error_tinst_level;
 /* We're starting to instantiate D; record the template instantiation context
    for diagnostics and to restore it later.  */
 
 /* We're starting to instantiate D; record the template instantiation context
    for diagnostics and to restore it later.  */
 
-int
+bool
 push_tinst_level (tree d)
 push_tinst_level (tree d)
+{
+  return push_tinst_level_loc (d, input_location);
+}
+
+/* We're starting to instantiate D; record the template instantiation context
+   at LOC for diagnostics and to restore it later.  */
+
+bool
+push_tinst_level_loc (tree d, location_t loc)
 {
   struct tinst_level *new_level;
 
   if (tinst_depth >= max_tinst_depth)
     {
 {
   struct tinst_level *new_level;
 
   if (tinst_depth >= max_tinst_depth)
     {
-      last_error_tinst_level = current_tinst_level;
-      if (TREE_CODE (d) == TREE_LIST)
-       error ("template instantiation depth exceeds maximum of %d (use "
-              "-ftemplate-depth= to increase the maximum) substituting %qS",
-              max_tinst_depth, d);
-      else
-       error ("template instantiation depth exceeds maximum of %d (use "
-              "-ftemplate-depth= to increase the maximum) instantiating %qD",
-              max_tinst_depth, d);
-
-      print_instantiation_context ();
-
-      return 0;
+      fatal_error (input_location,
+                  "template instantiation depth exceeds maximum of %d"
+                   " (use -ftemplate-depth= to increase the maximum)",
+                   max_tinst_depth);
+      return false;
     }
 
   /* If the current instantiation caused problems, don't let it instantiate
      anything else.  Do allow deduction substitution and decls usable in
      constant expressions.  */
   if (limit_bad_template_recursion (d))
     }
 
   /* If the current instantiation caused problems, don't let it instantiate
      anything else.  Do allow deduction substitution and decls usable in
      constant expressions.  */
   if (limit_bad_template_recursion (d))
-    return 0;
+    return false;
 
   new_level = ggc_alloc<tinst_level> ();
   new_level->decl = d;
 
   new_level = ggc_alloc<tinst_level> ();
   new_level->decl = d;
-  new_level->locus = input_location;
+  new_level->locus = loc;
   new_level->errors = errorcount+sorrycount;
   new_level->in_system_header_p = in_system_header_at (input_location);
   new_level->next = current_tinst_level;
   new_level->errors = errorcount+sorrycount;
   new_level->in_system_header_p = in_system_header_at (input_location);
   new_level->next = current_tinst_level;
@@ -8372,7 +8556,7 @@ push_tinst_level (tree d)
   if (GATHER_STATISTICS && (tinst_depth > depth_reached))
     depth_reached = tinst_depth;
 
   if (GATHER_STATISTICS && (tinst_depth > depth_reached))
     depth_reached = tinst_depth;
 
-  return 1;
+  return true;
 }
 
 /* We're done instantiating this template; return to the instantiation
 }
 
 /* We're done instantiating this template; return to the instantiation
@@ -8636,7 +8820,7 @@ tsubst_friend_function (tree decl, tree args)
                      elt.args = DECL_TI_ARGS (spec);
                      elt.spec = NULL_TREE;
 
                      elt.args = DECL_TI_ARGS (spec);
                      elt.spec = NULL_TREE;
 
-                     htab_remove_elt (decl_specializations, &elt);
+                     decl_specializations->remove_elt (&elt);
 
                      DECL_TI_ARGS (spec)
                        = add_outermost_template_args (new_args,
 
                      DECL_TI_ARGS (spec)
                        = add_outermost_template_args (new_args,
@@ -8915,6 +9099,21 @@ apply_late_template_attributes (tree *decl_p, tree attributes, int attr_flags,
                      = tree_cons (NULL_TREE, TREE_VALUE (TREE_VALUE (t)),
                                   chain);
                }
                      = tree_cons (NULL_TREE, TREE_VALUE (TREE_VALUE (t)),
                                   chain);
                }
+             else if (TREE_VALUE (t) && PACK_EXPANSION_P (TREE_VALUE (t)))
+               {
+                 /* An attribute pack expansion.  */
+                 tree purp = TREE_PURPOSE (t);
+                 tree pack = (tsubst_pack_expansion
+                              (TREE_VALUE (t), args, complain, in_decl));
+                 int len = TREE_VEC_LENGTH (pack);
+                 for (int i = 0; i < len; ++i)
+                   {
+                     tree elt = TREE_VEC_ELT (pack, i);
+                     *q = build_tree_list (purp, elt);
+                     q = &TREE_CHAIN (*q);
+                   }
+                 continue;
+               }
              else
                TREE_VALUE (t)
                  = tsubst_expr (TREE_VALUE (t), args, complain, in_decl,
              else
                TREE_VALUE (t)
                  = tsubst_expr (TREE_VALUE (t), args, complain, in_decl,
@@ -8995,7 +9194,7 @@ instantiate_class_template_1 (tree type)
 
   /* Determine what specialization of the original template to
      instantiate.  */
 
   /* Determine what specialization of the original template to
      instantiate.  */
-  t = most_specialized_class (type, tf_warning_or_error);
+  t = most_specialized_partial_spec (type, tf_warning_or_error);
   if (t == error_mark_node)
     {
       TYPE_BEING_DEFINED (type) = 1;
   if (t == error_mark_node)
     {
       TYPE_BEING_DEFINED (type) = 1;
@@ -9039,12 +9238,20 @@ instantiate_class_template_1 (tree type)
      it now.  */
   push_deferring_access_checks (dk_no_deferred);
 
      it now.  */
   push_deferring_access_checks (dk_no_deferred);
 
+  int saved_unevaluated_operand = cp_unevaluated_operand;
+  int saved_inhibit_evaluation_warnings = c_inhibit_evaluation_warnings;
+
   fn_context = decl_function_context (TYPE_MAIN_DECL (type));
   /* Also avoid push_to_top_level for a lambda in an NSDMI.  */
   if (!fn_context && LAMBDA_TYPE_P (type) && TYPE_CLASS_SCOPE_P (type))
     fn_context = error_mark_node;
   if (!fn_context)
     push_to_top_level ();
   fn_context = decl_function_context (TYPE_MAIN_DECL (type));
   /* Also avoid push_to_top_level for a lambda in an NSDMI.  */
   if (!fn_context && LAMBDA_TYPE_P (type) && TYPE_CLASS_SCOPE_P (type))
     fn_context = error_mark_node;
   if (!fn_context)
     push_to_top_level ();
+  else
+    {
+      cp_unevaluated_operand = 0;
+      c_inhibit_evaluation_warnings = 0;
+    }
   /* Use #pragma pack from the template context.  */
   saved_maximum_field_alignment = maximum_field_alignment;
   maximum_field_alignment = TYPE_PRECISION (pattern);
   /* Use #pragma pack from the template context.  */
   saved_maximum_field_alignment = maximum_field_alignment;
   maximum_field_alignment = TYPE_PRECISION (pattern);
@@ -9460,6 +9667,14 @@ instantiate_class_template_1 (tree type)
        }
     }
 
        }
     }
 
+  if (fn_context)
+    {
+      /* Restore these before substituting into the lambda capture
+        initializers.  */
+      cp_unevaluated_operand = saved_unevaluated_operand;
+      c_inhibit_evaluation_warnings = saved_inhibit_evaluation_warnings;
+    }
+
   if (tree expr = CLASSTYPE_LAMBDA_EXPR (type))
     {
       tree decl = lambda_function (type);
   if (tree expr = CLASSTYPE_LAMBDA_EXPR (type))
     {
       tree decl = lambda_function (type);
@@ -9610,16 +9825,22 @@ make_fnparm_pack (tree spec_parm)
   return extract_fnparm_pack (NULL_TREE, &spec_parm);
 }
 
   return extract_fnparm_pack (NULL_TREE, &spec_parm);
 }
 
-/* Return true iff the Ith element of the argument pack ARG_PACK is a
-   pack expansion.  */
+/* Return 1 if the Ith element of the argument pack ARG_PACK is a
+   pack expansion with no extra args, 2 if it has extra args, or 0
+   if it is not a pack expansion.  */
 
 
-static bool
+static int
 argument_pack_element_is_expansion_p (tree arg_pack, int i)
 {
   tree vec = ARGUMENT_PACK_ARGS (arg_pack);
   if (i >= TREE_VEC_LENGTH (vec))
 argument_pack_element_is_expansion_p (tree arg_pack, int i)
 {
   tree vec = ARGUMENT_PACK_ARGS (arg_pack);
   if (i >= TREE_VEC_LENGTH (vec))
-    return false;
-  return PACK_EXPANSION_P (TREE_VEC_ELT (vec, i));
+    return 0;
+  tree elt = TREE_VEC_ELT (vec, i);
+  if (!PACK_EXPANSION_P (elt))
+    return 0;
+  if (PACK_EXPANSION_EXTRA_ARGS (elt))
+    return 2;
+  return 1;
 }
 
 
 }
 
 
@@ -9669,7 +9890,12 @@ use_pack_expansion_extra_args_p (tree parm_packs,
        {
          tree arg = TREE_VALUE (parm_pack);
 
        {
          tree arg = TREE_VALUE (parm_pack);
 
-         if (argument_pack_element_is_expansion_p (arg, i))
+         int exp = argument_pack_element_is_expansion_p (arg, i);
+         if (exp == 2)
+           /* We can't substitute a pack expansion with extra args into
+              our pattern.  */
+           return true;
+         else if (exp)
            has_expansion_arg = true;
          else
            has_non_expansion_arg = true;
            has_expansion_arg = true;
          else
            has_non_expansion_arg = true;
@@ -9733,7 +9959,8 @@ gen_elem_of_pack_expansion_instantiation (tree pattern,
          if (index == 0)
            {
              aps = make_argument_pack_select (arg_pack, index);
          if (index == 0)
            {
              aps = make_argument_pack_select (arg_pack, index);
-             mark_used (parm);
+             if (!mark_used (parm, complain) && !(complain & tf_error))
+               return error_mark_node;
              register_local_specialization (aps, parm);
            }
          else
              register_local_specialization (aps, parm);
            }
          else
@@ -9911,6 +10138,17 @@ tsubst_pack_expansion (tree t, tree args, tsubst_flags_t complain,
        }
     }
 
        }
     }
 
+  /* If the expansion is just T..., return the matching argument pack.  */
+  if (!unsubstituted_packs
+      && TREE_PURPOSE (packs) == pattern)
+    {
+      tree args = ARGUMENT_PACK_ARGS (TREE_VALUE (packs));
+      if (TREE_CODE (t) == TYPE_PACK_EXPANSION
+         || pack_expansion_args_count (args))
+       return args;
+      /* Otherwise use the normal path so we get convert_from_reference.  */
+    }
+
   /* We cannot expand this expansion expression, because we don't have
      all of the argument packs we need.  */
   if (use_pack_expansion_extra_args_p (packs, len, unsubstituted_packs))
   /* We cannot expand this expansion expression, because we don't have
      all of the argument packs we need.  */
   if (use_pack_expansion_extra_args_p (packs, len, unsubstituted_packs))
@@ -10446,7 +10684,7 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
            if (new_type == error_mark_node)
              RETURN (error_mark_node);
            /* If we get a real template back, return it.  This can happen in
            if (new_type == error_mark_node)
              RETURN (error_mark_node);
            /* If we get a real template back, return it.  This can happen in
-              the context of most_specialized_class.  */
+              the context of most_specialized_partial_spec.  */
            if (TREE_CODE (new_type) == TEMPLATE_DECL)
              return new_type;
 
            if (TREE_CODE (new_type) == TEMPLATE_DECL)
              return new_type;
 
@@ -10554,7 +10792,7 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
        if (PRIMARY_TEMPLATE_P (t))
          DECL_PRIMARY_TEMPLATE (r) = r;
 
        if (PRIMARY_TEMPLATE_P (t))
          DECL_PRIMARY_TEMPLATE (r) = r;
 
-       if (TREE_CODE (decl) != TYPE_DECL && TREE_CODE (decl) != VAR_DECL)
+       if (TREE_CODE (decl) != TYPE_DECL && !VAR_P (decl))
          /* Record this non-type partial instantiation.  */
          register_specialization (r, t,
                                   DECL_TI_ARGS (DECL_TEMPLATE_RESULT (r)),
          /* Record this non-type partial instantiation.  */
          register_specialization (r, t,
                                   DECL_TI_ARGS (DECL_TEMPLATE_RESULT (r)),
@@ -11106,8 +11344,7 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
          {
            /* T is a static data member or namespace-scope entity.
               We have to substitute into namespace-scope variables
          {
            /* T is a static data member or namespace-scope entity.
               We have to substitute into namespace-scope variables
-              (even though such entities are never templates) because
-              of cases like:
+              (not just variable templates) because of cases like:
               
                 template <class T> void f() { extern T t; }
 
               
                 template <class T> void f() { extern T t; }
 
@@ -11127,13 +11364,12 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
                   same_type_p, because DECL_CONTEXT is always
                   canonical...  */
                if (ctx == DECL_CONTEXT (t)
                   same_type_p, because DECL_CONTEXT is always
                   canonical...  */
                if (ctx == DECL_CONTEXT (t)
-                   && (TREE_CODE (t) != TYPE_DECL
-                       /* ... unless T is a member template; in which
-                          case our caller can be willing to create a
-                          specialization of that template represented
-                          by T.  */
-                       || !(DECL_TI_TEMPLATE (t)
-                            && DECL_MEMBER_TEMPLATE_P (DECL_TI_TEMPLATE (t)))))
+                   /* ... unless T is a member template; in which
+                      case our caller can be willing to create a
+                      specialization of that template represented
+                      by T.  */
+                   && !(DECL_TI_TEMPLATE (t)
+                        && DECL_MEMBER_TEMPLATE_P (DECL_TI_TEMPLATE (t))))
                  spec = t;
              }
 
                  spec = t;
              }
 
@@ -11142,6 +11378,11 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
                tmpl = DECL_TI_TEMPLATE (t);
                gen_tmpl = most_general_template (tmpl);
                argvec = tsubst (DECL_TI_ARGS (t), args, complain, in_decl);
                tmpl = DECL_TI_TEMPLATE (t);
                gen_tmpl = most_general_template (tmpl);
                argvec = tsubst (DECL_TI_ARGS (t), args, complain, in_decl);
+               if (argvec != error_mark_node)
+                 argvec = (coerce_innermost_template_parms
+                           (DECL_TEMPLATE_PARMS (gen_tmpl),
+                            argvec, t, complain,
+                            /*all*/true, /*defarg*/true));
                if (argvec == error_mark_node)
                  RETURN (error_mark_node);
                hash = hash_tmpl_and_args (gen_tmpl, argvec);
                if (argvec == error_mark_node)
                  RETURN (error_mark_node);
                hash = hash_tmpl_and_args (gen_tmpl, argvec);
@@ -11226,6 +11467,9 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
                  }
                SET_DECL_VALUE_EXPR (r, ve);
              }
                  }
                SET_DECL_VALUE_EXPR (r, ve);
              }
+           if (CP_DECL_THREAD_LOCAL_P (r)
+               && !processing_template_decl)
+             set_decl_tls_model (r, decl_default_tls_model (r));
          }
        else if (DECL_SELF_REFERENCE_P (t))
          SET_DECL_SELF_REFERENCE_P (r);
          }
        else if (DECL_SELF_REFERENCE_P (t))
          SET_DECL_SELF_REFERENCE_P (r);
@@ -11262,10 +11506,12 @@ tsubst_decl (tree t, tree args, tsubst_flags_t complain)
               initializer is present.  We mimic the non-template
               processing here.  */
            DECL_EXTERNAL (r) = 1;
               initializer is present.  We mimic the non-template
               processing here.  */
            DECL_EXTERNAL (r) = 1;
+           if (DECL_NAMESPACE_SCOPE_P (t))
+             DECL_NOT_REALLY_EXTERN (r) = 1;
 
 
-           register_specialization (r, gen_tmpl, argvec, false, hash);
            DECL_TEMPLATE_INFO (r) = build_template_info (tmpl, argvec);
            SET_DECL_IMPLICIT_INSTANTIATION (r);
            DECL_TEMPLATE_INFO (r) = build_template_info (tmpl, argvec);
            SET_DECL_IMPLICIT_INSTANTIATION (r);
+           register_specialization (r, gen_tmpl, argvec, false, hash);
          }
        else if (!cp_unevaluated_operand)
          register_local_specialization (r, t);
          }
        else if (!cp_unevaluated_operand)
          register_local_specialization (r, t);
@@ -11828,7 +12074,11 @@ tsubst (tree t, tree args, tsubst_flags_t complain, tree in_decl)
                   gen_elem_of_pack_expansion_instantiation will
                   build the resulting pack expansion from it.  */
                if (PACK_EXPANSION_P (arg))
                   gen_elem_of_pack_expansion_instantiation will
                   build the resulting pack expansion from it.  */
                if (PACK_EXPANSION_P (arg))
-                 arg = PACK_EXPANSION_PATTERN (arg);
+                 {
+                   /* Make sure we aren't throwing away arg info.  */
+                   gcc_assert (!PACK_EXPANSION_EXTRA_ARGS (arg));
+                   arg = PACK_EXPANSION_PATTERN (arg);
+                 }
              }
          }
 
              }
          }
 
@@ -12131,21 +12381,6 @@ tsubst (tree t, tree args, tsubst_flags_t complain, tree in_decl)
          r = cp_build_reference_type (type, TYPE_REF_IS_RVALUE (t));
        r = cp_build_qualified_type_real (r, cp_type_quals (t), complain);
 
          r = cp_build_reference_type (type, TYPE_REF_IS_RVALUE (t));
        r = cp_build_qualified_type_real (r, cp_type_quals (t), complain);
 
-       if (cxx_dialect >= cxx1y
-           && !(TREE_CODE (t) == REFERENCE_TYPE && REFERENCE_VLA_OK (t))
-           && array_of_runtime_bound_p (type)
-           && (flag_iso || warn_vla > 0))
-         {
-           if (complain & tf_warning_or_error)
-             pedwarn
-               (input_location, OPT_Wvla,
-                code == REFERENCE_TYPE
-                ? G_("cannot declare reference to array of runtime bound")
-                : G_("cannot declare pointer to array of runtime bound"));
-           else
-             r = error_mark_node;
-         }
-
        if (r != error_mark_node)
          /* Will this ever be needed for TYPE_..._TO values?  */
          layout_type (r);
        if (r != error_mark_node)
          /* Will this ever be needed for TYPE_..._TO values?  */
          layout_type (r);
@@ -12401,7 +12636,7 @@ tsubst (tree t, tree args, tsubst_flags_t complain, tree in_decl)
        return cp_build_qualified_type_real (type,
                                             cp_type_quals (t)
                                             | cp_type_quals (type),
        return cp_build_qualified_type_real (type,
                                             cp_type_quals (t)
                                             | cp_type_quals (type),
-                                            complain);
+                                            complain | tf_ignore_bad_quals);
       }
 
     case UNDERLYING_TYPE:
       }
 
     case UNDERLYING_TYPE:
@@ -12502,8 +12737,9 @@ tsubst_baselink (tree baselink, tree object_type,
        point.)  */
     if (BASELINK_P (baselink))
       fns = BASELINK_FUNCTIONS (baselink);
        point.)  */
     if (BASELINK_P (baselink))
       fns = BASELINK_FUNCTIONS (baselink);
-    if (!template_id_p && !really_overloaded_fn (fns))
-      mark_used (OVL_CURRENT (fns));
+    if (!template_id_p && !really_overloaded_fn (fns)
+       && !mark_used (OVL_CURRENT (fns), complain) && !(complain & tf_error))
+      return error_mark_node;
 
     /* Add back the template arguments, if present.  */
     if (BASELINK_P (baselink) && template_id_p)
 
     /* Add back the template arguments, if present.  */
     if (BASELINK_P (baselink) && template_id_p)
@@ -12618,7 +12854,8 @@ tsubst_qualified_id (tree qualified_id, tree args,
       check_accessibility_of_qualified_id (expr, /*object_type=*/NULL_TREE,
                                           scope);
       /* Remember that there was a reference to this entity.  */
       check_accessibility_of_qualified_id (expr, /*object_type=*/NULL_TREE,
                                           scope);
       /* Remember that there was a reference to this entity.  */
-      mark_used (expr);
+      if (!mark_used (expr, complain) && !(complain & tf_error))
+       return error_mark_node;
     }
 
   if (expr == error_mark_node || TREE_CODE (expr) == TREE_LIST)
     }
 
   if (expr == error_mark_node || TREE_CODE (expr) == TREE_LIST)
@@ -12728,7 +12965,8 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
       
       if (TREE_CODE (r) == ARGUMENT_PACK_SELECT)
        r = ARGUMENT_PACK_SELECT_ARG (r);
       
       if (TREE_CODE (r) == ARGUMENT_PACK_SELECT)
        r = ARGUMENT_PACK_SELECT_ARG (r);
-      mark_used (r);
+      if (!mark_used (r, complain) && !(complain & tf_error))
+       return error_mark_node;
       return r;
 
     case CONST_DECL:
       return r;
 
     case CONST_DECL:
@@ -12744,7 +12982,7 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
          return t;
        /* If ARGS is NULL, then T is known to be non-dependent.  */
        if (args == NULL_TREE)
          return t;
        /* If ARGS is NULL, then T is known to be non-dependent.  */
        if (args == NULL_TREE)
-         return integral_constant_value (t);
+         return scalar_constant_value (t);
 
        /* Unfortunately, we cannot just call lookup_name here.
           Consider:
 
        /* Unfortunately, we cannot just call lookup_name here.
           Consider:
@@ -12872,10 +13110,8 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
                      if (TREE_STATIC (r))
                        rest_of_decl_compilation (r, toplevel_bindings_p (),
                                                  at_eof);
                      if (TREE_STATIC (r))
                        rest_of_decl_compilation (r, toplevel_bindings_p (),
                                                  at_eof);
-                     else if (decl_constant_var_p (r))
-                       /* A use of a local constant decays to its value.
-                          FIXME update for core DR 696.  */
-                       r = integral_constant_value (r);
+                     else
+                       r = process_outer_var_ref (r, complain);
                    }
                }
              /* Remember this for subsequent uses.  */
                    }
                }
              /* Remember this for subsequent uses.  */
@@ -12885,7 +13121,8 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
        }
       else
        r = t;
        }
       else
        r = t;
-      mark_used (r);
+      if (!mark_used (r, complain) && !(complain & tf_error))
+       return error_mark_node;
       return r;
 
     case NAMESPACE_DECL:
       return r;
 
     case NAMESPACE_DECL:
@@ -13249,7 +13486,9 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
        tree op1 = tsubst_copy (TREE_OPERAND (t, 1), args, complain, in_decl);
        r = build2 (code, type, op0, op1);
        PTRMEM_OK_P (r) = PTRMEM_OK_P (t);
        tree op1 = tsubst_copy (TREE_OPERAND (t, 1), args, complain, in_decl);
        r = build2 (code, type, op0, op1);
        PTRMEM_OK_P (r) = PTRMEM_OK_P (t);
-       mark_used (TREE_OPERAND (r, 1));
+       if (!mark_used (TREE_OPERAND (r, 1), complain)
+           && !(complain & tf_error))
+         return error_mark_node;
        return r;
       }
 
        return r;
       }
 
@@ -13290,6 +13529,32 @@ tsubst_copy (tree t, tree args, tsubst_flags_t complain, tree in_decl)
     }
 }
 
     }
 }
 
+/* Helper function for tsubst_omp_clauses, used for instantiation of
+   OMP_CLAUSE_DECL of clauses that handles also OpenMP array sections
+   represented with TREE_LIST.  */
+
+static tree
+tsubst_omp_clause_decl (tree decl, tree args, tsubst_flags_t complain,
+                       tree in_decl)
+{
+  if (TREE_CODE (decl) == TREE_LIST)
+    {
+      tree low_bound
+       = tsubst_expr (TREE_PURPOSE (decl), args, complain, in_decl,
+                      /*integral_constant_expression_p=*/false);
+      tree length = tsubst_expr (TREE_VALUE (decl), args, complain, in_decl,
+                                /*integral_constant_expression_p=*/false);
+      tree chain = tsubst_omp_clause_decl (TREE_CHAIN (decl), args, complain,
+                                          in_decl);
+      if (TREE_PURPOSE (decl) == low_bound
+         && TREE_VALUE (decl) == length
+         && TREE_CHAIN (decl) == chain)
+       return decl;
+      return tree_cons (low_bound, length, chain);
+    }
+  return tsubst_copy (decl, args, complain, in_decl);
+}
+
 /* Like tsubst_copy, but specifically for OpenMP clauses.  */
 
 static tree
 /* Like tsubst_copy, but specifically for OpenMP clauses.  */
 
 static tree
@@ -13321,16 +13586,23 @@ tsubst_omp_clauses (tree clauses, bool declare_simd,
        case OMP_CLAUSE_FIRSTPRIVATE:
        case OMP_CLAUSE_COPYIN:
        case OMP_CLAUSE_COPYPRIVATE:
        case OMP_CLAUSE_FIRSTPRIVATE:
        case OMP_CLAUSE_COPYIN:
        case OMP_CLAUSE_COPYPRIVATE:
+       case OMP_CLAUSE_UNIFORM:
+         OMP_CLAUSE_DECL (nc) = tsubst_copy (OMP_CLAUSE_DECL (oc), args,
+                                             complain, in_decl);
+         break;
+       case OMP_CLAUSE_DEPEND:
+       case OMP_CLAUSE_FROM:
+       case OMP_CLAUSE_TO:
+       case OMP_CLAUSE_MAP:
+         OMP_CLAUSE_DECL (nc)
+           = tsubst_omp_clause_decl (OMP_CLAUSE_DECL (oc), args, complain,
+                                     in_decl);
+         break;
        case OMP_CLAUSE_IF:
        case OMP_CLAUSE_NUM_THREADS:
        case OMP_CLAUSE_SCHEDULE:
        case OMP_CLAUSE_COLLAPSE:
        case OMP_CLAUSE_FINAL:
        case OMP_CLAUSE_IF:
        case OMP_CLAUSE_NUM_THREADS:
        case OMP_CLAUSE_SCHEDULE:
        case OMP_CLAUSE_COLLAPSE:
        case OMP_CLAUSE_FINAL:
-       case OMP_CLAUSE_DEPEND:
-       case OMP_CLAUSE_FROM:
-       case OMP_CLAUSE_TO:
-       case OMP_CLAUSE_UNIFORM:
-       case OMP_CLAUSE_MAP:
        case OMP_CLAUSE_DEVICE:
        case OMP_CLAUSE_DIST_SCHEDULE:
        case OMP_CLAUSE_NUM_TEAMS:
        case OMP_CLAUSE_DEVICE:
        case OMP_CLAUSE_DIST_SCHEDULE:
        case OMP_CLAUSE_NUM_TEAMS:
@@ -13357,20 +13629,17 @@ tsubst_omp_clauses (tree clauses, bool declare_simd,
              else
                gcc_assert (identifier_p (placeholder));
            }
              else
                gcc_assert (identifier_p (placeholder));
            }
-         OMP_CLAUSE_OPERAND (nc, 0)
-           = tsubst_expr (OMP_CLAUSE_OPERAND (oc, 0), args, complain,
-                          in_decl, /*integral_constant_expression_p=*/false);
+         OMP_CLAUSE_DECL (nc) = tsubst_copy (OMP_CLAUSE_DECL (oc), args,
+                                             complain, in_decl);
          break;
        case OMP_CLAUSE_LINEAR:
        case OMP_CLAUSE_ALIGNED:
          break;
        case OMP_CLAUSE_LINEAR:
        case OMP_CLAUSE_ALIGNED:
-         OMP_CLAUSE_OPERAND (nc, 0)
-           = tsubst_expr (OMP_CLAUSE_OPERAND (oc, 0), args, complain,
-                          in_decl, /*integral_constant_expression_p=*/false);
+         OMP_CLAUSE_DECL (nc) = tsubst_copy (OMP_CLAUSE_DECL (oc), args,
+                                             complain, in_decl);
          OMP_CLAUSE_OPERAND (nc, 1)
            = tsubst_expr (OMP_CLAUSE_OPERAND (oc, 1), args, complain,
                           in_decl, /*integral_constant_expression_p=*/false);
          break;
          OMP_CLAUSE_OPERAND (nc, 1)
            = tsubst_expr (OMP_CLAUSE_OPERAND (oc, 1), args, complain,
                           in_decl, /*integral_constant_expression_p=*/false);
          break;
-
        case OMP_CLAUSE_NOWAIT:
        case OMP_CLAUSE_ORDERED:
        case OMP_CLAUSE_DEFAULT:
        case OMP_CLAUSE_NOWAIT:
        case OMP_CLAUSE_ORDERED:
        case OMP_CLAUSE_DEFAULT:
@@ -14011,6 +14280,7 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl,
     case OMP_FOR:
     case OMP_SIMD:
     case CILK_SIMD:
     case OMP_FOR:
     case OMP_SIMD:
     case CILK_SIMD:
+    case CILK_FOR:
     case OMP_DISTRIBUTE:
       {
        tree clauses, body, pre_body;
     case OMP_DISTRIBUTE:
       {
        tree clauses, body, pre_body;
@@ -14065,8 +14335,6 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl,
     case OMP_SECTIONS:
     case OMP_SINGLE:
     case OMP_TEAMS:
     case OMP_SECTIONS:
     case OMP_SINGLE:
     case OMP_TEAMS:
-    case OMP_TARGET_DATA:
-    case OMP_TARGET:
       tmp = tsubst_omp_clauses (OMP_CLAUSES (t), false,
                                args, complain, in_decl);
       stmt = push_stmt_list ();
       tmp = tsubst_omp_clauses (OMP_CLAUSES (t), false,
                                args, complain, in_decl);
       stmt = push_stmt_list ();
@@ -14079,11 +14347,27 @@ tsubst_expr (tree t, tree args, tsubst_flags_t complain, tree in_decl,
       add_stmt (t);
       break;
 
       add_stmt (t);
       break;
 
+    case OMP_TARGET_DATA:
+    case OMP_TARGET:
+      tmp = tsubst_omp_clauses (OMP_CLAUSES (t), false,
+                               args, complain, in_decl);
+      keep_next_level (true);
+      stmt = begin_omp_structured_block ();
+
+      RECUR (OMP_BODY (t));
+      stmt = finish_omp_structured_block (stmt);
+
+      t = copy_node (t);
+      OMP_BODY (t) = stmt;
+      OMP_CLAUSES (t) = tmp;
+      add_stmt (t);
+      break;
+
     case OMP_TARGET_UPDATE:
       tmp = tsubst_omp_clauses (OMP_TARGET_UPDATE_CLAUSES (t), false,
                                args, complain, in_decl);
       t = copy_node (t);
     case OMP_TARGET_UPDATE:
       tmp = tsubst_omp_clauses (OMP_TARGET_UPDATE_CLAUSES (t), false,
                                args, complain, in_decl);
       t = copy_node (t);
-      OMP_CLAUSES (t) = tmp;
+      OMP_TARGET_UPDATE_CLAUSES (t) = tmp;
       add_stmt (t);
       break;
 
       add_stmt (t);
       break;
 
@@ -14328,16 +14612,6 @@ tsubst_non_call_postfix_expression (tree t, tree args,
   return t;
 }
 
   return t;
 }
 
-/* Sentinel to disable certain warnings during template substitution.  */
-
-struct warning_sentinel {
-  int &flag;
-  int val;
-  warning_sentinel(int& flag, bool suppress=true)
-    : flag(flag), val(flag) { if (suppress) flag = 0; }
-  ~warning_sentinel() { flag = val; }
-};
-
 /* Like tsubst but deals with expressions and performs semantic
    analysis.  FUNCTION_P is true if T is the "F" in "F (ARGS)".  */
 
 /* Like tsubst but deals with expressions and performs semantic
    analysis.  FUNCTION_P is true if T is the "F" in "F (ARGS)".  */
 
@@ -14729,11 +15003,13 @@ tsubst_copy_and_build (tree t,
       op1 = TREE_OPERAND (t, 0);
       ++cp_unevaluated_operand;
       ++c_inhibit_evaluation_warnings;
       op1 = TREE_OPERAND (t, 0);
       ++cp_unevaluated_operand;
       ++c_inhibit_evaluation_warnings;
+      ++cp_noexcept_operand;
       op1 = tsubst_copy_and_build (op1, args, complain, in_decl,
                                   /*function_p=*/false,
                                   /*integral_constant_expression_p=*/false);
       --cp_unevaluated_operand;
       --c_inhibit_evaluation_warnings;
       op1 = tsubst_copy_and_build (op1, args, complain, in_decl,
                                   /*function_p=*/false,
                                   /*integral_constant_expression_p=*/false);
       --cp_unevaluated_operand;
       --c_inhibit_evaluation_warnings;
+      --cp_noexcept_operand;
       RETURN (finish_noexcept_expr (op1, complain));
 
     case MODOP_EXPR:
       RETURN (finish_noexcept_expr (op1, complain));
 
     case MODOP_EXPR:
@@ -14760,8 +15036,9 @@ tsubst_copy_and_build (tree t,
       op1 = tsubst_non_call_postfix_expression (TREE_OPERAND (t, 0),
                                                args, complain, in_decl);
       /* Remember that there was a reference to this entity.  */
       op1 = tsubst_non_call_postfix_expression (TREE_OPERAND (t, 0),
                                                args, complain, in_decl);
       /* Remember that there was a reference to this entity.  */
-      if (DECL_P (op1))
-       mark_used (op1);
+      if (DECL_P (op1)
+         && !mark_used (op1, complain) && !(complain & tf_error))
+       RETURN (error_mark_node);
       RETURN (build_x_arrow (input_location, op1, complain));
 
     case NEW_EXPR:
       RETURN (build_x_arrow (input_location, op1, complain));
 
     case NEW_EXPR:
@@ -15012,8 +15289,9 @@ tsubst_copy_and_build (tree t,
          }
 
        /* Remember that there was a reference to this entity.  */
          }
 
        /* Remember that there was a reference to this entity.  */
-       if (DECL_P (function))
-         mark_used (function);
+       if (DECL_P (function)
+           && !mark_used (function, complain) && !(complain & tf_error))
+         RETURN (error_mark_node);
 
        /* Put back tf_decltype for the actual call.  */
        complain |= decltype_flag;
 
        /* Put back tf_decltype for the actual call.  */
        complain |= decltype_flag;
@@ -15060,11 +15338,12 @@ tsubst_copy_and_build (tree t,
     case COND_EXPR:
       {
        tree cond = RECUR (TREE_OPERAND (t, 0));
     case COND_EXPR:
       {
        tree cond = RECUR (TREE_OPERAND (t, 0));
+       tree folded_cond = fold_non_dependent_expr (cond);
        tree exp1, exp2;
 
        tree exp1, exp2;
 
-       if (TREE_CODE (cond) == INTEGER_CST)
+       if (TREE_CODE (folded_cond) == INTEGER_CST)
          {
          {
-           if (integer_zerop (cond))
+           if (integer_zerop (folded_cond))
              {
                ++c_inhibit_evaluation_warnings;
                exp1 = RECUR (TREE_OPERAND (t, 1));
              {
                ++c_inhibit_evaluation_warnings;
                exp1 = RECUR (TREE_OPERAND (t, 1));
@@ -15078,6 +15357,7 @@ tsubst_copy_and_build (tree t,
                exp2 = RECUR (TREE_OPERAND (t, 2));
                --c_inhibit_evaluation_warnings;
              }
                exp2 = RECUR (TREE_OPERAND (t, 2));
                --c_inhibit_evaluation_warnings;
              }
+           cond = folded_cond;
          }
        else
          {
          }
        else
          {
@@ -15194,8 +15474,9 @@ tsubst_copy_and_build (tree t,
        object = tsubst_non_call_postfix_expression (TREE_OPERAND (t, 0),
                                                     args, complain, in_decl);
        /* Remember that there was a reference to this entity.  */
        object = tsubst_non_call_postfix_expression (TREE_OPERAND (t, 0),
                                                     args, complain, in_decl);
        /* Remember that there was a reference to this entity.  */
-       if (DECL_P (object))
-         mark_used (object);
+       if (DECL_P (object)
+           && !mark_used (object, complain) && !(complain & tf_error))
+         RETURN (error_mark_node);
        object_type = TREE_TYPE (object);
 
        member = TREE_OPERAND (t, 1);
        object_type = TREE_TYPE (object);
 
        member = TREE_OPERAND (t, 1);
@@ -15411,6 +15692,24 @@ tsubst_copy_and_build (tree t,
     case PARM_DECL:
       {
        tree r = tsubst_copy (t, args, complain, in_decl);
     case PARM_DECL:
       {
        tree r = tsubst_copy (t, args, complain, in_decl);
+       /* ??? We're doing a subset of finish_id_expression here.  */
+       if (VAR_P (r)
+           && !processing_template_decl
+           && !cp_unevaluated_operand
+           && (TREE_STATIC (r) || DECL_EXTERNAL (r))
+           && CP_DECL_THREAD_LOCAL_P (r))
+         {
+           if (tree wrap = get_tls_wrapper_fn (r))
+             /* Replace an evaluated use of the thread_local variable with
+                a call to its wrapper.  */
+             r = build_cxx_call (wrap, 0, NULL, tf_warning_or_error);
+         }
+       else if (outer_automatic_var_p (r))
+         {
+           r = process_outer_var_ref (r, complain);
+           if (is_capture_proxy (r))
+             register_local_specialization (r, t);
+         }
 
        if (TREE_CODE (TREE_TYPE (t)) != REFERENCE_TYPE)
          /* If the original type was a reference, we'll be wrapped in
 
        if (TREE_CODE (TREE_TYPE (t)) != REFERENCE_TYPE)
          /* If the original type was a reference, we'll be wrapped in
@@ -15427,7 +15726,8 @@ tsubst_copy_and_build (tree t,
       }
 
     case OFFSETOF_EXPR:
       }
 
     case OFFSETOF_EXPR:
-      RETURN (finish_offsetof (RECUR (TREE_OPERAND (t, 0))));
+      RETURN (finish_offsetof (RECUR (TREE_OPERAND (t, 0)),
+                              EXPR_LOCATION (t)));
 
     case TRAIT_EXPR:
       {
 
     case TRAIT_EXPR:
       {
@@ -15435,7 +15735,9 @@ tsubst_copy_and_build (tree t,
                             complain, in_decl);
 
        tree type2 = TRAIT_EXPR_TYPE2 (t);
                             complain, in_decl);
 
        tree type2 = TRAIT_EXPR_TYPE2 (t);
-       if (type2)
+       if (type2 && TREE_CODE (type2) == TREE_LIST)
+         type2 = RECUR (type2);
+       else if (type2)
          type2 = tsubst (type2, args, complain, in_decl);
        
        RETURN (finish_trait_expr (TRAIT_EXPR_KIND (t), type1, type2));
          type2 = tsubst (type2, args, complain, in_decl);
        
        RETURN (finish_trait_expr (TRAIT_EXPR_KIND (t), type1, type2));
@@ -15624,6 +15926,7 @@ check_instantiated_arg (tree tmpl, tree t, tsubst_flags_t complain)
      constant.  */
   else if (TREE_TYPE (t)
           && INTEGRAL_OR_ENUMERATION_TYPE_P (TREE_TYPE (t))
      constant.  */
   else if (TREE_TYPE (t)
           && INTEGRAL_OR_ENUMERATION_TYPE_P (TREE_TYPE (t))
+          && !REFERENCE_REF_P (t)
           && !TREE_CONSTANT (t))
     {
       if (complain & tf_error)
           && !TREE_CONSTANT (t))
     {
       if (complain & tf_error)
@@ -15759,13 +16062,32 @@ instantiate_template_1 (tree tmpl, tree orig_args, tsubst_flags_t complain)
     ++processing_template_decl;
   if (DECL_CLASS_SCOPE_P (gen_tmpl))
     {
     ++processing_template_decl;
   if (DECL_CLASS_SCOPE_P (gen_tmpl))
     {
-      tree ctx = tsubst (DECL_CONTEXT (gen_tmpl), targ_ptr,
-                        complain, gen_tmpl);
+      tree ctx = tsubst_aggr_type (DECL_CONTEXT (gen_tmpl), targ_ptr,
+                                  complain, gen_tmpl, true);
       push_nested_class (ctx);
     }
       push_nested_class (ctx);
     }
+
+  tree pattern = DECL_TEMPLATE_RESULT (gen_tmpl);
+
+  if (VAR_P (pattern))
+    {
+      /* We need to determine if we're using a partial or explicit
+        specialization now, because the type of the variable could be
+        different.  */
+      tree tid = lookup_template_variable (gen_tmpl, targ_ptr);
+      tree elt = most_specialized_partial_spec (tid, complain);
+      if (elt == error_mark_node)
+       pattern = error_mark_node;
+      else if (elt)
+       {
+         tmpl = TREE_VALUE (elt);
+         pattern = DECL_TEMPLATE_RESULT (tmpl);
+         targ_ptr = TREE_PURPOSE (elt);
+       }
+    }
+
   /* Substitute template parameters to obtain the specialization.  */
   /* Substitute template parameters to obtain the specialization.  */
-  fndecl = tsubst (DECL_TEMPLATE_RESULT (gen_tmpl),
-                  targ_ptr, complain, gen_tmpl);
+  fndecl = tsubst (pattern, targ_ptr, complain, gen_tmpl);
   if (DECL_CLASS_SCOPE_P (gen_tmpl))
     pop_nested_class ();
   pop_from_top_level ();
   if (DECL_CLASS_SCOPE_P (gen_tmpl))
     pop_nested_class ();
   pop_from_top_level ();
@@ -16247,15 +16569,11 @@ maybe_adjust_types_for_deduction (unification_kind_t strict,
       break;
 
     case DEDUCE_CONV:
       break;
 
     case DEDUCE_CONV:
-      {
-       /* Swap PARM and ARG throughout the remainder of this
-          function; the handling is precisely symmetric since PARM
-          will initialize ARG rather than vice versa.  */
-       tree* temp = parm;
-       parm = arg;
-       arg = temp;
-       break;
-      }
+      /* Swap PARM and ARG throughout the remainder of this
+        function; the handling is precisely symmetric since PARM
+        will initialize ARG rather than vice versa.  */
+      std::swap (parm, arg);
+      break;
 
     case DEDUCE_EXACT:
       /* Core issue #873: Do the DR606 thing (see below) for these cases,
 
     case DEDUCE_EXACT:
       /* Core issue #873: Do the DR606 thing (see below) for these cases,
@@ -16509,7 +16827,7 @@ uses_deducible_template_parms (tree type)
 
 static int
 unify_one_argument (tree tparms, tree targs, tree parm, tree arg,
 
 static int
 unify_one_argument (tree tparms, tree targs, tree parm, tree arg,
-                   int subr, unification_kind_t strict, int flags,
+                   int subr, unification_kind_t strict,
                    bool explain_p)
 {
   tree arg_expr = NULL_TREE;
                    bool explain_p)
 {
   tree arg_expr = NULL_TREE;
@@ -16526,16 +16844,10 @@ unify_one_argument (tree tparms, tree targs, tree parm, tree arg,
      argument to convert it to the type of the corresponding function
      parameter if the parameter type contains no template-parameters that
      participate in template argument deduction.  */
      argument to convert it to the type of the corresponding function
      parameter if the parameter type contains no template-parameters that
      participate in template argument deduction.  */
-  if (TYPE_P (parm) && !uses_template_parms (parm))
-    /* For function parameters that contain no template-parameters at all,
-       we have historically checked for convertibility in order to shortcut
-       consideration of this candidate.  */
-    return check_non_deducible_conversion (parm, arg, strict, flags,
-                                          explain_p);
-  else if (strict == DEDUCE_CALL
-          && TYPE_P (parm) && !uses_deducible_template_parms (parm))
-    /* For function parameters with only non-deducible template parameters,
-       just return.  */
+  if (strict != DEDUCE_EXACT
+      && TYPE_P (parm) && !uses_deducible_template_parms (parm))
+    /* For function parameters with no deducible template parameters,
+       just return.  We'll check non-dependent conversions later.  */
     return unify_success (explain_p);
 
   switch (strict)
     return unify_success (explain_p);
 
   switch (strict)
@@ -16674,7 +16986,7 @@ type_unification_real (tree tparms,
       ++ia;
 
       if (unify_one_argument (tparms, targs, parm, arg, subr, strict,
       ++ia;
 
       if (unify_one_argument (tparms, targs, parm, arg, subr, strict,
-                             flags, explain_p))
+                             explain_p))
        return 1;
     }
 
        return 1;
     }
 
@@ -16756,8 +17068,11 @@ type_unification_real (tree tparms,
             this parameter can be deduced.  */
          if (TREE_CODE (tparm) == PARM_DECL
              && uses_template_parms (TREE_TYPE (tparm))
             this parameter can be deduced.  */
          if (TREE_CODE (tparm) == PARM_DECL
              && uses_template_parms (TREE_TYPE (tparm))
-             && !saw_undeduced++)
-           goto again;
+             && saw_undeduced < 2)
+           {
+             saw_undeduced = 1;
+             continue;
+           }
 
          /* Core issue #226 (C++0x) [temp.deduct]:
 
 
          /* Core issue #226 (C++0x) [temp.deduct]:
 
@@ -16768,32 +17083,9 @@ type_unification_real (tree tparms,
             be NULL_TREE or ERROR_MARK_NODE, so we do not need
             to explicitly check cxx_dialect here.  */
          if (TREE_PURPOSE (TREE_VEC_ELT (tparms, i)))
             be NULL_TREE or ERROR_MARK_NODE, so we do not need
             to explicitly check cxx_dialect here.  */
          if (TREE_PURPOSE (TREE_VEC_ELT (tparms, i)))
-           {
-             tree parm = TREE_VALUE (TREE_VEC_ELT (tparms, i));
-             tree arg = TREE_PURPOSE (TREE_VEC_ELT (tparms, i));
-             reopen_deferring_access_checks (*checks);
-             location_t save_loc = input_location;
-             if (DECL_P (parm))
-               input_location = DECL_SOURCE_LOCATION (parm);
-             arg = tsubst_template_arg (arg, targs, complain, NULL_TREE);
-             arg = convert_template_argument (parm, arg, targs, complain,
-                                              i, NULL_TREE);
-             input_location = save_loc;
-             *checks = get_deferred_access_checks ();
-             pop_deferring_access_checks ();
-             if (arg == error_mark_node)
-               return 1;
-             else
-               {
-                 TREE_VEC_ELT (targs, i) = arg;
-                 /* The position of the first default template argument,
-                    is also the number of non-defaulted arguments in TARGS.
-                    Record that.  */
-                 if (!NON_DEFAULT_TEMPLATE_ARGS_COUNT (targs))
-                   SET_NON_DEFAULT_TEMPLATE_ARGS_COUNT (targs, i);
-                 continue;
-               }
-           }
+           /* OK, there is a default argument.  Wait until after the
+              conversion check to do substitution.  */
+           continue;
 
          /* If the type parameter is a parameter pack, then it will
             be deduced to an empty parameter pack.  */
 
          /* If the type parameter is a parameter pack, then it will
             be deduced to an empty parameter pack.  */
@@ -16818,6 +17110,84 @@ type_unification_real (tree tparms,
 
          return unify_parameter_deduction_failure (explain_p, tparm);
        }
 
          return unify_parameter_deduction_failure (explain_p, tparm);
        }
+
+      /* DR 1391: All parameters have args, now check non-dependent parms for
+        convertibility.  */
+      if (saw_undeduced < 2)
+       for (ia = 0, parms = xparms, args = xargs, nargs = xnargs;
+            parms && parms != void_list_node && ia < nargs; )
+         {
+           parm = TREE_VALUE (parms);
+
+           if (TREE_CODE (parm) == TYPE_PACK_EXPANSION
+               && (!TREE_CHAIN (parms)
+                   || TREE_CHAIN (parms) == void_list_node))
+             /* For a function parameter pack that occurs at the end of the
+                parameter-declaration-list, the type A of each remaining
+                argument of the call is compared with the type P of the
+                declarator-id of the function parameter pack.  */
+             break;
+
+           parms = TREE_CHAIN (parms);
+
+           if (TREE_CODE (parm) == TYPE_PACK_EXPANSION)
+             /* For a function parameter pack that does not occur at the
+                end of the parameter-declaration-list, the type of the
+                parameter pack is a non-deduced context.  */
+             continue;
+
+           arg = args[ia];
+           ++ia;
+
+           if (uses_template_parms (parm))
+             continue;
+           if (check_non_deducible_conversion (parm, arg, strict, flags,
+                                               explain_p))
+             return 1;
+         }
+
+      /* Now substitute into the default template arguments.  */
+      for (i = 0; i < ntparms; i++)
+       {
+         tree targ = TREE_VEC_ELT (targs, i);
+         tree tparm = TREE_VEC_ELT (tparms, i);
+
+         if (targ || tparm == error_mark_node)
+           continue;
+         tree parm = TREE_VALUE (tparm);
+
+         if (TREE_CODE (parm) == PARM_DECL
+             && uses_template_parms (TREE_TYPE (parm))
+             && saw_undeduced < 2)
+           continue;
+
+         tree arg = TREE_PURPOSE (tparm);
+         reopen_deferring_access_checks (*checks);
+         location_t save_loc = input_location;
+         if (DECL_P (parm))
+           input_location = DECL_SOURCE_LOCATION (parm);
+         arg = tsubst_template_arg (arg, targs, complain, NULL_TREE);
+         arg = convert_template_argument (parm, arg, targs, complain,
+                                          i, NULL_TREE);
+         input_location = save_loc;
+         *checks = get_deferred_access_checks ();
+         pop_deferring_access_checks ();
+         if (arg == error_mark_node)
+           return 1;
+         else
+           {
+             TREE_VEC_ELT (targs, i) = arg;
+             /* The position of the first default template argument,
+                is also the number of non-defaulted arguments in TARGS.
+                Record that.  */
+             if (!NON_DEFAULT_TEMPLATE_ARGS_COUNT (targs))
+               SET_NON_DEFAULT_TEMPLATE_ARGS_COUNT (targs, i);
+             continue;
+           }
+       }
+
+      if (saw_undeduced++ == 1)
+       goto again;
     }
 #ifdef ENABLE_CHECKING
   if (!NON_DEFAULT_TEMPLATE_ARGS_COUNT (targs))
     }
 #ifdef ENABLE_CHECKING
   if (!NON_DEFAULT_TEMPLATE_ARGS_COUNT (targs))
@@ -17432,7 +17802,7 @@ unify_pack_expansion (tree tparms, tree targs, tree packed_parms,
 
       /* Unify the pattern with the current argument.  */
       if (unify_one_argument (tparms, targs, parm, arg, subr, strict,
 
       /* Unify the pattern with the current argument.  */
       if (unify_one_argument (tparms, targs, parm, arg, subr, strict,
-                             LOOKUP_IMPLICIT, explain_p))
+                             explain_p))
        return 1;
 
       /* For each parameter pack, collect the deduced value.  */
        return 1;
 
       /* For each parameter pack, collect the deduced value.  */
@@ -17691,7 +18061,13 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
       if (TREE_CODE (parm) == ARRAY_TYPE)
        elttype = TREE_TYPE (parm);
       else
       if (TREE_CODE (parm) == ARRAY_TYPE)
        elttype = TREE_TYPE (parm);
       else
-       elttype = TREE_VEC_ELT (CLASSTYPE_TI_ARGS (parm), 0);
+       {
+         elttype = TREE_VEC_ELT (CLASSTYPE_TI_ARGS (parm), 0);
+         /* Deduction is defined in terms of a single type, so just punt
+            on the (bizarre) std::initializer_list<T...>.  */
+         if (PACK_EXPANSION_P (elttype))
+           return unify_success (explain_p);
+       }
 
       FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (arg), i, elt)
        {
 
       FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (arg), i, elt)
        {
@@ -17703,6 +18079,8 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
          if (!BRACE_ENCLOSED_INITIALIZER_P (elt))
            {
              tree type = TREE_TYPE (elt);
          if (!BRACE_ENCLOSED_INITIALIZER_P (elt))
            {
              tree type = TREE_TYPE (elt);
+             if (type == error_mark_node)
+               return unify_invalid (explain_p);
              /* It should only be possible to get here for a call.  */
              gcc_assert (elt_strict & UNIFY_ALLOW_OUTER_LEVEL);
              elt_strict |= maybe_adjust_types_for_deduction
              /* It should only be possible to get here for a call.  */
              gcc_assert (elt_strict & UNIFY_ALLOW_OUTER_LEVEL);
              elt_strict |= maybe_adjust_types_for_deduction
@@ -18037,7 +18415,10 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
          && !TEMPLATE_PARM_PARAMETER_PACK (parm))
        return unify_parameter_pack_mismatch (explain_p, parm, arg);
 
          && !TEMPLATE_PARM_PARAMETER_PACK (parm))
        return unify_parameter_pack_mismatch (explain_p, parm, arg);
 
-      arg = strip_typedefs_expr (arg);
+      {
+       bool removed_attr = false;
+       arg = strip_typedefs_expr (arg, &removed_attr);
+      }
       TREE_VEC_ELT (INNERMOST_TEMPLATE_ARGS (targs), idx) = arg;
       return unify_success (explain_p);
 
       TREE_VEC_ELT (INNERMOST_TEMPLATE_ARGS (targs), idx) = arg;
       return unify_success (explain_p);
 
@@ -18323,7 +18704,7 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
     case CONST_DECL:
       if (DECL_TEMPLATE_PARM_P (parm))
        return unify (tparms, targs, DECL_INITIAL (parm), arg, strict, explain_p);
     case CONST_DECL:
       if (DECL_TEMPLATE_PARM_P (parm))
        return unify (tparms, targs, DECL_INITIAL (parm), arg, strict, explain_p);
-      if (arg != integral_constant_value (parm))
+      if (arg != scalar_constant_value (parm))
        return unify_template_argument_mismatch (explain_p, parm, arg);
       return unify_success (explain_p);
 
        return unify_template_argument_mismatch (explain_p, parm, arg);
       return unify_success (explain_p);
 
@@ -18357,8 +18738,12 @@ unify (tree tparms, tree targs, tree parm, tree arg, int strict,
 
     case INDIRECT_REF:
       if (REFERENCE_REF_P (parm))
 
     case INDIRECT_REF:
       if (REFERENCE_REF_P (parm))
-       return unify (tparms, targs, TREE_OPERAND (parm, 0), arg,
-                     strict, explain_p);
+       {
+         if (REFERENCE_REF_P (arg))
+           arg = TREE_OPERAND (arg, 0);
+         return unify (tparms, targs, TREE_OPERAND (parm, 0), arg,
+                       strict, explain_p);
+       }
       /* FALLTHRU */
 
     default:
       /* FALLTHRU */
 
     default:
@@ -18762,8 +19147,8 @@ more_specialized_fn (tree pat1, tree pat2, int len)
 /* Determine which of two partial specializations of TMPL is more
    specialized.
 
 /* Determine which of two partial specializations of TMPL is more
    specialized.
 
-   PAT1 is a TREE_LIST whose TREE_TYPE is the _TYPE node corresponding
-   to the first partial specialization.  The TREE_VALUE is the
+   PAT1 is a TREE_LIST whose TREE_VALUE is the TEMPLATE_DECL corresponding
+   to the first partial specialization.  The TREE_PURPOSE is the
    innermost set of template parameters for the partial
    specialization.  PAT2 is similar, but for the second template.
 
    innermost set of template parameters for the partial
    specialization.  PAT2 is similar, but for the second template.
 
@@ -18775,33 +19160,32 @@ more_specialized_fn (tree pat1, tree pat2, int len)
    two templates is more specialized.  */
 
 static int
    two templates is more specialized.  */
 
 static int
-more_specialized_class (tree tmpl, tree pat1, tree pat2)
+more_specialized_partial_spec (tree tmpl, tree pat1, tree pat2)
 {
   tree targs;
 {
   tree targs;
-  tree tmpl1, tmpl2;
   int winner = 0;
   bool any_deductions = false;
 
   int winner = 0;
   bool any_deductions = false;
 
-  tmpl1 = TREE_TYPE (pat1);
-  tmpl2 = TREE_TYPE (pat2);
+  tree tmpl1 = TREE_VALUE (pat1);
+  tree tmpl2 = TREE_VALUE (pat2);
+  tree parms1 = DECL_INNERMOST_TEMPLATE_PARMS (tmpl1);
+  tree parms2 = DECL_INNERMOST_TEMPLATE_PARMS (tmpl2);
+  tree specargs1 = TI_ARGS (get_template_info (DECL_TEMPLATE_RESULT (tmpl1)));
+  tree specargs2 = TI_ARGS (get_template_info (DECL_TEMPLATE_RESULT (tmpl2)));
 
   /* Just like what happens for functions, if we are ordering between
 
   /* Just like what happens for functions, if we are ordering between
-     different class template specializations, we may encounter dependent
+     different template specializations, we may encounter dependent
      types in the arguments, and we need our dependency check functions
      to behave correctly.  */
   ++processing_template_decl;
      types in the arguments, and we need our dependency check functions
      to behave correctly.  */
   ++processing_template_decl;
-  targs = get_class_bindings (tmpl, TREE_VALUE (pat1),
-                             CLASSTYPE_TI_ARGS (tmpl1),
-                             CLASSTYPE_TI_ARGS (tmpl2));
+  targs = get_partial_spec_bindings (tmpl, parms1, specargs1, specargs2);
   if (targs)
     {
       --winner;
       any_deductions = true;
     }
 
   if (targs)
     {
       --winner;
       any_deductions = true;
     }
 
-  targs = get_class_bindings (tmpl, TREE_VALUE (pat2),
-                             CLASSTYPE_TI_ARGS (tmpl2),
-                             CLASSTYPE_TI_ARGS (tmpl1));
+  targs = get_partial_spec_bindings (tmpl, parms2, specargs2, specargs1);
   if (targs)
     {
       ++winner;
   if (targs)
     {
       ++winner;
@@ -18809,7 +19193,7 @@ more_specialized_class (tree tmpl, tree pat1, tree pat2)
     }
   --processing_template_decl;
 
     }
   --processing_template_decl;
 
-  /* In the case of a tie where at least one of the class templates
+  /* In the case of a tie where at least one of the templates
      has a parameter pack at the end, the template with the most
      non-packed parameters wins.  */
   if (winner == 0
      has a parameter pack at the end, the template with the most
      non-packed parameters wins.  */
   if (winner == 0
@@ -18895,7 +19279,7 @@ get_bindings (tree fn, tree decl, tree explicit_args, bool check_rettype)
    is bound to `double'.  */
 
 static tree
    is bound to `double'.  */
 
 static tree
-get_class_bindings (tree tmpl, tree tparms, tree spec_args, tree args)
+get_partial_spec_bindings (tree tmpl, tree tparms, tree spec_args, tree args)
 {
   int i, ntparms = TREE_VEC_LENGTH (tparms);
   tree deduced_args;
 {
   int i, ntparms = TREE_VEC_LENGTH (tparms);
   tree deduced_args;
@@ -19063,6 +19447,7 @@ most_general_template (tree decl)
        break;
 
       if (CLASS_TYPE_P (TREE_TYPE (decl))
        break;
 
       if (CLASS_TYPE_P (TREE_TYPE (decl))
+         && !TYPE_DECL_ALIAS_P (TYPE_NAME (TREE_TYPE (decl)))
          && CLASSTYPE_TEMPLATE_SPECIALIZATION (TREE_TYPE (decl)))
        break;
 
          && CLASSTYPE_TEMPLATE_SPECIALIZATION (TREE_TYPE (decl)))
        break;
 
@@ -19078,20 +19463,20 @@ most_general_template (tree decl)
   return decl;
 }
 
   return decl;
 }
 
-/* Return the most specialized of the class template partial
-   specializations which can produce TYPE, a specialization of some class
-   template.  The value returned is actually a TREE_LIST; the TREE_TYPE is
-   a _TYPE node corresponding to the partial specialization, while the
-   TREE_PURPOSE is the set of template arguments that must be
-   substituted into the TREE_TYPE in order to generate TYPE.
+/* Return the most specialized of the template partial specializations
+   which can produce TARGET, a specialization of some class or variable
+   template.  The value returned is actually a TREE_LIST; the TREE_VALUE is
+   a TEMPLATE_DECL node corresponding to the partial specialization, while
+   the TREE_PURPOSE is the set of template arguments that must be
+   substituted into the template pattern in order to generate TARGET.
 
    If the choice of partial specialization is ambiguous, a diagnostic
    is issued, and the error_mark_node is returned.  If there are no
 
    If the choice of partial specialization is ambiguous, a diagnostic
    is issued, and the error_mark_node is returned.  If there are no
-   partial specializations matching TYPE, then NULL_TREE is
+   partial specializations matching TARGET, then NULL_TREE is
    returned, indicating that the primary template should be used.  */
 
 static tree
    returned, indicating that the primary template should be used.  */
 
 static tree
-most_specialized_class (tree type, tsubst_flags_t complain)
+most_specialized_partial_spec (tree target, tsubst_flags_t complain)
 {
   tree list = NULL_TREE;
   tree t;
 {
   tree list = NULL_TREE;
   tree t;
@@ -19099,10 +19484,29 @@ most_specialized_class (tree type, tsubst_flags_t complain)
   int fate;
   bool ambiguous_p;
   tree outer_args = NULL_TREE;
   int fate;
   bool ambiguous_p;
   tree outer_args = NULL_TREE;
+  tree tmpl, args;
+
+  if (TYPE_P (target))
+    {
+      tree tinfo = CLASSTYPE_TEMPLATE_INFO (target);
+      tmpl = TI_TEMPLATE (tinfo);
+      args = TI_ARGS (tinfo);
+    }
+  else if (TREE_CODE (target) == TEMPLATE_ID_EXPR)
+    {
+      tmpl = TREE_OPERAND (target, 0);
+      args = TREE_OPERAND (target, 1);
+    }
+  else if (VAR_P (target))
+    {
+      tree tinfo = DECL_TEMPLATE_INFO (target);
+      tmpl = TI_TEMPLATE (tinfo);
+      args = TI_ARGS (tinfo);
+    }
+  else
+    gcc_unreachable ();
 
 
-  tree tmpl = CLASSTYPE_TI_TEMPLATE (type);
   tree main_tmpl = most_general_template (tmpl);
   tree main_tmpl = most_general_template (tmpl);
-  tree args = CLASSTYPE_TI_ARGS (type);
 
   /* For determining which partial specialization to use, only the
      innermost args are interesting.  */
 
   /* For determining which partial specialization to use, only the
      innermost args are interesting.  */
@@ -19117,9 +19521,8 @@ most_specialized_class (tree type, tsubst_flags_t complain)
       tree partial_spec_args;
       tree spec_args;
       tree spec_tmpl = TREE_VALUE (t);
       tree partial_spec_args;
       tree spec_args;
       tree spec_tmpl = TREE_VALUE (t);
-      tree orig_parms = DECL_INNERMOST_TEMPLATE_PARMS (spec_tmpl);
 
 
-      partial_spec_args = CLASSTYPE_TI_ARGS (TREE_TYPE (t));
+      partial_spec_args = TREE_PURPOSE (t);
 
       ++processing_template_decl;
 
 
       ++processing_template_decl;
 
@@ -19150,14 +19553,14 @@ most_specialized_class (tree type, tsubst_flags_t complain)
        return error_mark_node;
 
       tree parms = DECL_INNERMOST_TEMPLATE_PARMS (spec_tmpl);
        return error_mark_node;
 
       tree parms = DECL_INNERMOST_TEMPLATE_PARMS (spec_tmpl);
-      spec_args = get_class_bindings (tmpl, parms,
+      spec_args = get_partial_spec_bindings (tmpl, parms,
                                      partial_spec_args,
                                      args);
       if (spec_args)
        {
          if (outer_args)
            spec_args = add_to_template_args (outer_args, spec_args);
                                      partial_spec_args,
                                      args);
       if (spec_args)
        {
          if (outer_args)
            spec_args = add_to_template_args (outer_args, spec_args);
-         list = tree_cons (spec_args, orig_parms, list);
+         list = tree_cons (spec_args, TREE_VALUE (t), list);
          TREE_TYPE (list) = TREE_TYPE (t);
        }
     }
          TREE_TYPE (list) = TREE_TYPE (t);
        }
     }
@@ -19171,7 +19574,7 @@ most_specialized_class (tree type, tsubst_flags_t complain)
   t = TREE_CHAIN (t);
   for (; t; t = TREE_CHAIN (t))
     {
   t = TREE_CHAIN (t);
   for (; t; t = TREE_CHAIN (t))
     {
-      fate = more_specialized_class (tmpl, champ, t);
+      fate = more_specialized_partial_spec (tmpl, champ, t);
       if (fate == 1)
        ;
       else
       if (fate == 1)
        ;
       else
@@ -19192,7 +19595,7 @@ most_specialized_class (tree type, tsubst_flags_t complain)
   if (!ambiguous_p)
     for (t = list; t && t != champ; t = TREE_CHAIN (t))
       {
   if (!ambiguous_p)
     for (t = list; t && t != champ; t = TREE_CHAIN (t))
       {
-       fate = more_specialized_class (tmpl, champ, t);
+       fate = more_specialized_partial_spec (tmpl, champ, t);
        if (fate != 1)
          {
            ambiguous_p = true;
        if (fate != 1)
          {
            ambiguous_p = true;
@@ -19206,11 +19609,16 @@ most_specialized_class (tree type, tsubst_flags_t complain)
       char *spaces = NULL;
       if (!(complain & tf_error))
        return error_mark_node;
       char *spaces = NULL;
       if (!(complain & tf_error))
        return error_mark_node;
-      error ("ambiguous class template instantiation for %q#T", type);
+      if (TYPE_P (target))
+       error ("ambiguous template instantiation for %q#T", target);
+      else
+       error ("ambiguous template instantiation for %q#D", target);
       str = ngettext ("candidate is:", "candidates are:", list_length (list));
       for (t = list; t; t = TREE_CHAIN (t))
         {
       str = ngettext ("candidate is:", "candidates are:", list_length (list));
       for (t = list; t; t = TREE_CHAIN (t))
         {
-          error ("%s %+#T", spaces ? spaces : str, TREE_TYPE (t));
+         tree subst = build_tree_list (TREE_VALUE (t), TREE_PURPOSE (t));
+          inform (DECL_SOURCE_LOCATION (TREE_VALUE (t)),
+                 "%s %#S", spaces ? spaces : str, subst);
           spaces = spaces ? spaces : get_spaces (str);
         }
       free (spaces);
           spaces = spaces ? spaces : get_spaces (str);
         }
       free (spaces);
@@ -19712,8 +20120,6 @@ template_for_substitution (tree decl)
         cannot restructure the loop to just keep going until we find
         a template with a definition, since that might go too far if
         a specialization was declared, but not defined.  */
         cannot restructure the loop to just keep going until we find
         a template with a definition, since that might go too far if
         a specialization was declared, but not defined.  */
-      gcc_assert (!VAR_P (decl)
-                 || DECL_IN_AGGR_P (DECL_TEMPLATE_RESULT (tmpl)));
 
       /* Fetch the more general template.  */
       tmpl = DECL_TI_TEMPLATE (tmpl);
 
       /* Fetch the more general template.  */
       tmpl = DECL_TI_TEMPLATE (tmpl);
@@ -19985,13 +20391,18 @@ instantiate_decl (tree d, int defer_ok,
                              args,
                              tf_warning_or_error, NULL_TREE,
                              /*integral_constant_expression_p=*/false);
                              args,
                              tf_warning_or_error, NULL_TREE,
                              /*integral_constant_expression_p=*/false);
-         /* Make sure the initializer is still constant, in case of
-            circular dependency (template/instantiate6.C). */
-         const_init
-           = DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P (code_pattern);
-         cp_finish_decl (d, init, /*init_const_expr_p=*/const_init,
-                         /*asmspec_tree=*/NULL_TREE,
-                         LOOKUP_ONLYCONVERTING);
+         /* If instantiating the initializer involved instantiating this
+            again, don't call cp_finish_decl twice.  */
+         if (!DECL_INITIAL (d))
+           {
+             /* Make sure the initializer is still constant, in case of
+                circular dependency (template/instantiate6.C). */
+             const_init
+               = DECL_INITIALIZED_BY_CONSTANT_EXPRESSION_P (code_pattern);
+             cp_finish_decl (d, init, /*init_const_expr_p=*/const_init,
+                             /*asmspec_tree=*/NULL_TREE,
+                             LOOKUP_ONLYCONVERTING);
+           }
          if (enter_context)
            pop_nested_class ();
          pop_nested_namespace (ns);
          if (enter_context)
            pop_nested_class ();
          pop_nested_namespace (ns);
@@ -20236,10 +20647,11 @@ instantiate_pending_templates (int retries)
     {
       tree decl = pending_templates->tinst->decl;
 
     {
       tree decl = pending_templates->tinst->decl;
 
-      error ("template instantiation depth exceeds maximum of %d"
-            " instantiating %q+D, possibly from virtual table generation"
-            " (use -ftemplate-depth= to increase the maximum)",
-            max_tinst_depth, decl);
+      fatal_error (input_location,
+                  "template instantiation depth exceeds maximum of %d"
+                   " instantiating %q+D, possibly from virtual table generation"
+                   " (use -ftemplate-depth= to increase the maximum)",
+                   max_tinst_depth, decl);
       if (TREE_CODE (decl) == FUNCTION_DECL)
        /* Pretend that we defined it.  */
        DECL_INITIAL (decl) = error_mark_node;
       if (TREE_CODE (decl) == FUNCTION_DECL)
        /* Pretend that we defined it.  */
        DECL_INITIAL (decl) = error_mark_node;
@@ -20489,9 +20901,10 @@ tsubst_enum (tree tag, tree newtag, tree args)
       /* Give this enumeration constant the correct access.  */
       set_current_access_from_decl (decl);
 
       /* Give this enumeration constant the correct access.  */
       set_current_access_from_decl (decl);
 
-      /* Actually build the enumerator itself.  */
-      build_enumerator
-       (DECL_NAME (decl), value, newtag, DECL_SOURCE_LOCATION (decl));
+      /* Actually build the enumerator itself.  Here we're assuming that
+        enumerators can't have dependent attributes.  */
+      build_enumerator (DECL_NAME (decl), value, newtag,
+                       DECL_ATTRIBUTES (decl), DECL_SOURCE_LOCATION (decl));
     }
 
   if (SCOPED_ENUM_P (newtag))
     }
 
   if (SCOPED_ENUM_P (newtag))
@@ -20512,67 +20925,13 @@ tsubst_enum (tree tag, tree newtag, tree args)
 tree
 get_mostly_instantiated_function_type (tree decl)
 {
 tree
 get_mostly_instantiated_function_type (tree decl)
 {
-  tree fn_type;
-  tree tmpl;
-  tree targs;
-  tree tparms;
-  int parm_depth;
-
-  tmpl = most_general_template (DECL_TI_TEMPLATE (decl));
-  targs = DECL_TI_ARGS (decl);
-  tparms = DECL_TEMPLATE_PARMS (tmpl);
-  parm_depth = TMPL_PARMS_DEPTH (tparms);
-
-  /* There should be as many levels of arguments as there are levels
-     of parameters.  */
-  gcc_assert (parm_depth == TMPL_ARGS_DEPTH (targs));
-
-  fn_type = TREE_TYPE (tmpl);
-
-  if (parm_depth == 1)
-    /* No substitution is necessary.  */
-    ;
-  else
-    {
-      int i;
-      tree partial_args;
-
-      /* Replace the innermost level of the TARGS with NULL_TREEs to
-        let tsubst know not to substitute for those parameters.  */
-      partial_args = make_tree_vec (TREE_VEC_LENGTH (targs));
-      for (i = 1; i < TMPL_ARGS_DEPTH (targs); ++i)
-       SET_TMPL_ARGS_LEVEL (partial_args, i,
-                            TMPL_ARGS_LEVEL (targs, i));
-      SET_TMPL_ARGS_LEVEL (partial_args,
-                          TMPL_ARGS_DEPTH (targs),
-                          make_tree_vec (DECL_NTPARMS (tmpl)));
-
-      /* Make sure that we can see identifiers, and compute access
-        correctly.  */
-      push_access_scope (decl);
-
-      ++processing_template_decl;
-      /* Now, do the (partial) substitution to figure out the
-        appropriate function type.  */
-      fn_type = tsubst (fn_type, partial_args, tf_error, NULL_TREE);
-      --processing_template_decl;
-
-      /* Substitute into the template parameters to obtain the real
-        innermost set of parameters.  This step is important if the
-        innermost set of template parameters contains value
-        parameters whose types depend on outer template parameters.  */
-      TREE_VEC_LENGTH (partial_args)--;
-      tparms = tsubst_template_parms (tparms, partial_args, tf_error);
-
-      pop_access_scope (decl);
-    }
-
-  return fn_type;
+  /* For a function, DECL_TI_TEMPLATE is partially instantiated.  */
+  return TREE_TYPE (DECL_TI_TEMPLATE (decl));
 }
 
 /* Return truthvalue if we're processing a template different from
    the last one involved in diagnostics.  */
 }
 
 /* Return truthvalue if we're processing a template different from
    the last one involved in diagnostics.  */
-int
+bool
 problematic_instantiation_changed (void)
 {
   return current_tinst_level != last_error_tinst_level;
 problematic_instantiation_changed (void)
 {
   return current_tinst_level != last_error_tinst_level;
@@ -20591,6 +20950,16 @@ current_instantiation (void)
   return current_tinst_level;
 }
 
   return current_tinst_level;
 }
 
+/* Return TRUE if current_function_decl is being instantiated, false
+   otherwise.  */
+
+bool
+instantiating_current_function_p (void)
+{
+  return (current_instantiation ()
+         && current_instantiation ()->decl == current_function_decl);
+}
+
 /* [temp.param] Check that template non-type parm TYPE is of an allowable
    type. Return zero for ok, nonzero for disallowed. Issue error and
    warning messages under control of COMPLAIN.  */
 /* [temp.param] Check that template non-type parm TYPE is of an allowable
    type. Return zero for ok, nonzero for disallowed. Issue error and
    warning messages under control of COMPLAIN.  */
@@ -20647,9 +21016,17 @@ dependent_type_p_r (tree type)
        names a dependent type.  */
   if (TREE_CODE (type) == TYPENAME_TYPE)
     return true;
        names a dependent type.  */
   if (TREE_CODE (type) == TYPENAME_TYPE)
     return true;
+
+  /* An alias template specialization can be dependent even if the
+     resulting type is not.  */
+  if (dependent_alias_template_spec_p (type))
+    return true;
+
   /* -- a cv-qualified type where the cv-unqualified type is
   /* -- a cv-qualified type where the cv-unqualified type is
-       dependent.  */
-  type = TYPE_MAIN_VARIANT (type);
+       dependent.
+     No code is necessary for this bullet; the code below handles
+     cv-qualified types, and we don't want to strip aliases with
+     TYPE_MAIN_VARIANT because of DR 1558.  */
   /* -- a compound type constructed from any dependent type.  */
   if (TYPE_PTRMEM_P (type))
     return (dependent_type_p (TYPE_PTRMEM_CLASS_TYPE (type))
   /* -- a compound type constructed from any dependent type.  */
   if (TYPE_PTRMEM_P (type))
     return (dependent_type_p (TYPE_PTRMEM_CLASS_TYPE (type))
@@ -20857,6 +21234,8 @@ value_dependent_expression_p (tree expression)
       if (DECL_INITIAL (expression)
          && decl_constant_var_p (expression)
          && (TREE_CODE (DECL_INITIAL (expression)) == TREE_LIST
       if (DECL_INITIAL (expression)
          && decl_constant_var_p (expression)
          && (TREE_CODE (DECL_INITIAL (expression)) == TREE_LIST
+             /* cp_finish_decl doesn't fold reference initializers.  */
+             || TREE_CODE (TREE_TYPE (expression)) == REFERENCE_TYPE
              || value_dependent_expression_p (DECL_INITIAL (expression))))
        return true;
       return false;
              || value_dependent_expression_p (DECL_INITIAL (expression))))
        return true;
       return false;
@@ -20997,6 +21376,8 @@ value_dependent_expression_p (tree expression)
       {
        unsigned ix;
        tree val;
       {
        unsigned ix;
        tree val;
+       if (dependent_type_p (TREE_TYPE (expression)))
+         return true;
        FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (expression), ix, val)
          if (value_dependent_expression_p (val))
            return true;
        FOR_EACH_CONSTRUCTOR_VALUE (CONSTRUCTOR_ELTS (expression), ix, val)
          if (value_dependent_expression_p (val))
            return true;
@@ -21005,7 +21386,7 @@ value_dependent_expression_p (tree expression)
 
     case STMT_EXPR:
       /* Treat a GNU statement expression as dependent to avoid crashing
 
     case STMT_EXPR:
       /* Treat a GNU statement expression as dependent to avoid crashing
-        under fold_non_dependent_expr; it can't be constant.  */
+        under instantiate_non_dependent_expr; it can't be constant.  */
       return true;
 
     default:
       return true;
 
     default:
@@ -21179,6 +21560,18 @@ type_dependent_expression_p (tree expression)
       && DECL_INITIAL (expression))
    return true;
 
       && DECL_INITIAL (expression))
    return true;
 
+  /* A variable template specialization is type-dependent if it has any
+     dependent template arguments.  */
+  if (VAR_P (expression)
+      && DECL_LANG_SPECIFIC (expression)
+      && DECL_TEMPLATE_INFO (expression)
+      && variable_template_p (DECL_TI_TEMPLATE (expression)))
+    return any_dependent_template_arguments_p (DECL_TI_ARGS (expression));
+
+  /* Always dependent, on the number of arguments if nothing else.  */
+  if (TREE_CODE (expression) == EXPR_PACK_EXPANSION)
+    return true;
+
   if (TREE_TYPE (expression) == unknown_type_node)
     {
       if (TREE_CODE (expression) == ADDR_EXPR)
   if (TREE_TYPE (expression) == unknown_type_node)
     {
       if (TREE_CODE (expression) == ADDR_EXPR)
@@ -21196,10 +21589,6 @@ type_dependent_expression_p (tree expression)
       if (TREE_CODE (expression) == SCOPE_REF)
        return false;
 
       if (TREE_CODE (expression) == SCOPE_REF)
        return false;
 
-      /* Always dependent, on the number of arguments if nothing else.  */
-      if (TREE_CODE (expression) == EXPR_PACK_EXPANSION)
-       return true;
-
       if (BASELINK_P (expression))
        {
          if (BASELINK_OPTYPE (expression)
       if (BASELINK_P (expression))
        {
          if (BASELINK_OPTYPE (expression)
@@ -21759,7 +22148,7 @@ build_non_dependent_expr (tree expr)
   /* Try to get a constant value for all non-dependent expressions in
       order to expose bugs in *_dependent_expression_p and constexpr.  */
   if (cxx_dialect >= cxx11)
   /* Try to get a constant value for all non-dependent expressions in
       order to expose bugs in *_dependent_expression_p and constexpr.  */
   if (cxx_dialect >= cxx11)
-    maybe_constant_value (fold_non_dependent_expr_sfinae (expr, tf_none));
+    fold_non_dependent_expr (expr);
 #endif
 
   /* Preserve OVERLOADs; the functions must be available to resolve
 #endif
 
   /* Preserve OVERLOADs; the functions must be available to resolve
@@ -21931,7 +22320,21 @@ do_auto_deduction (tree type, tree init, tree auto_node)
      initializer is a braced-init-list (8.5.4), with
      std::initializer_list<U>.  */
   if (BRACE_ENCLOSED_INITIALIZER_P (init))
      initializer is a braced-init-list (8.5.4), with
      std::initializer_list<U>.  */
   if (BRACE_ENCLOSED_INITIALIZER_P (init))
-    type = listify_autos (type, auto_node);
+    {
+      if (!DIRECT_LIST_INIT_P (init))
+       type = listify_autos (type, auto_node);
+      else if (CONSTRUCTOR_NELTS (init) == 1)
+       init = CONSTRUCTOR_ELT (init, 0)->value;
+      else
+       {
+         if (permerror (input_location, "direct-list-initialization of "
+                        "%<auto%> requires exactly one element"))
+           inform (input_location,
+                   "for deduction to %<std::initializer_list%>, use copy-"
+                   "list-initialization (i.e. add %<=%> before the %<{%>)");
+         type = listify_autos (type, auto_node);
+       }
+    }
 
   init = resolve_nondeduced_context (init);
 
 
   init = resolve_nondeduced_context (init);
 
@@ -22245,14 +22648,8 @@ convert_generic_types_to_packs (tree parm, int start_idx, int end_idx)
 void
 init_template_processing (void)
 {
 void
 init_template_processing (void)
 {
-  decl_specializations = htab_create_ggc (37,
-                                         hash_specialization,
-                                         eq_specializations,
-                                         ggc_free);
-  type_specializations = htab_create_ggc (37,
-                                         hash_specialization,
-                                         eq_specializations,
-                                         ggc_free);
+  decl_specializations = hash_table<spec_hasher>::create_ggc (37);
+  type_specializations = hash_table<spec_hasher>::create_ggc (37);
 }
 
 /* Print stats about the template hash tables for -fstats.  */
 }
 
 /* Print stats about the template hash tables for -fstats.  */
@@ -22261,13 +22658,13 @@ void
 print_template_statistics (void)
 {
   fprintf (stderr, "decl_specializations: size %ld, %ld elements, "
 print_template_statistics (void)
 {
   fprintf (stderr, "decl_specializations: size %ld, %ld elements, "
-          "%f collisions\n", (long) htab_size (decl_specializations),
-          (long) htab_elements (decl_specializations),
-          htab_collisions (decl_specializations));
+          "%f collisions\n", (long) decl_specializations->size (),
+          (long) decl_specializations->elements (),
+          decl_specializations->collisions ());
   fprintf (stderr, "type_specializations: size %ld, %ld elements, "
   fprintf (stderr, "type_specializations: size %ld, %ld elements, "
-          "%f collisions\n", (long) htab_size (type_specializations),
-          (long) htab_elements (type_specializations),
-          htab_collisions (type_specializations));
+          "%f collisions\n", (long) type_specializations->size (),
+          (long) type_specializations->elements (),
+          type_specializations->collisions ());
 }
 
 #include "gt-cp-pt.h"
 }
 
 #include "gt-cp-pt.h"