CWG Issue 215 (original) (raw)
This is an unofficial snapshot of the ISO/IEC JTC1 SC22 WG21 Core Issues List revision 118e. See http://www.open-std.org/jtc1/sc22/wg21/ for the official list.
2025-11-05
215. Template parameters are not allowed in _nested-name-specifier_s
Section: 13.2 [temp.param]Status: CD1Submitter: Martin von LoewisDate: 13 Mar 2000
[Voted into WP at April, 2007 meeting.]
According to 13.2 [temp.param] paragraph 3, the following fragment is ill-formed:
template <class T>
class X{
friend void T::foo();
};In the friend declaration, the T:: part is a_nested-name-specifier_ (9.3 [dcl.decl] paragraph 4), and T must be a class-name or a namespace-name(_N4567_.5.1.1 [expr.prim.general] paragraph 7). However, according to 13.2 [temp.param] paragraph 3, it is only a_type-name_. The fragment should be well-formed, and instantiations of the template allowed as long as the actual template argument is a class which provides a function member foo. As a result of this defect, any usage of template parameters in nested names is ill-formed, e.g., in the example of 13.8 [temp.res] paragraph 2.
Notes from 04/00 meeting:
The discussion at the meeting revealed a self-contradiction in the current IS in the description of _nested-name-specifier_s. According to the grammar in _N4567_.5.1.1 [expr.prim.general] paragraph 7, the components of a nested-name-specifier must be either_class-name_s or namespace-name_s, i.e., the constraint is syntactic rather than semantic. On the other hand, 6.5.5 [basic.lookup.qual] paragraph 1 describes a semantic constraint: only object, function, and enumerator names are ignored in the lookup for the component, and the program is ill-formed if the lookup finds anything other than a class-name or namespace-name. It was generally agreed that the syntactic constraint should be eliminated, i.e., that the grammar ought to be changed not to use_class-or-namespace-name.
A related point is the explicit prohibition of use of template parameters in _elaborated-type-specifier_s in 9.2.9.5 [dcl.type.elab] paragraph 2. This rule was the result of an explicit Committee decision and should not be unintentionally voided by the resolution of this issue.
Proposed resolution (04/01):
Change _N4567_.5.1.1 [expr.prim.general] paragraph 7 and A.5 [gram.expr] from
nested-name-specifier: class-or-namespace-name :: nested-name-specifieropt class-or-namespace-name :: template nested-name-specifier class-or-namespace-name: class-name namespace-name
to
nested-name-specifier: type-or-namespace-name :: nested-name-specifieropt type-or-namespace-name :: template nested-name-specifier type-or-namespace-name: type-name namespace-name
This resolution depends on the resolutions for issues245 (to change the name lookup rules in_elaborated-type-specifier_s to include all _type-name_s) and 283 (to categorize template_type-parameter_s as _type-name_s).
Notes from 10/01 meeting:
There was some sentiment for going with simply _identifier_in front of the "::", and stronger sentiment for going with something with a more descriptive name if possible. See also issue 180.
Notes from April 2003 meeting:
This was partly resolved by the changes for issue 125. However, we also need to add a semantic check in 6.5.5 [basic.lookup.qual] to allow T::foo and we need to reword the first sentence of 6.5.5 [basic.lookup.qual].
Proposed resolution (October, 2004):
Change 6.5.5 [basic.lookup.qual] paragraph 1 as follows:
The name of a class or namespace member can be referred to after the :: scope resolution operator (_N4567_.5.1.1 [expr.prim.general]) applied to a nested-name-specifier that nominates its class or namespace. During the lookup for a name preceding the :: scope resolution operator, object, function, and enumerator names are ignored. If the name found
is not a class-name (Clause 11 [class]) or_namespace-name_ (9.9.2 [namespace.def])does not designate a class or namespace, the program is ill-formed. [...]
Notes from the April, 2005 meeting:
The 10/2004 resolution does not take into account the fact that template type parameters do not designate class types in the context of the template definition. Further drafting is required.
Proposed resolution (April, 2006):
Change 6.5.5 [basic.lookup.qual] paragraph 1 as follows:
The name of a class or namespace member can be referred to after the :: scope resolution operator (_N4567_.5.1.1 [expr.prim.general]) applied to a nested-name-specifier that nominates its class or namespace. During the lookup for a name preceding the :: scope resolution operator, object, function, and enumerator names are ignored. If the name found
is not a class-name (Clause 11 [class]) or_namespace-name_ (9.9.2 [namespace.def])does not designate a namespace or a class or dependent type, the program is ill-formed. [...]